X-TOUCH to djay bridge
Dependencies: mbed mbed-rtos FATFileSystem
Revision 1:0dac72ab5910, committed 2019-06-05
- Comitter:
- okini3939
- Date:
- Wed Jun 05 04:54:37 2019 +0000
- Parent:
- 0:0fd787d62a99
- Commit message:
- sample
Changed in this revision
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/CBuffer.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,79 @@ +/* Copyright (C) 2012 mbed.org, MIT License + * + * Permission is hereby granted, free of charge, to any person obtaining a copy of this software + * and associated documentation files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, merge, publish, distribute, + * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all copies or + * substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING + * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, + * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef CIRCBUFFER_H_ +#define CIRCBUFFER_H_ + +template <class T> +class CircBuffer { +public: + CircBuffer(int length) { + write = 0; + read = 0; + size = length + 1; + buf = new T[size * sizeof(T)]; +// buf = (T *)malloc(size * sizeof(T)); + if (buf == NULL) + error("Can't allocate memory"); + }; + + bool isFull() { + return (((write + 1) % size) == read); + }; + + bool isEmpty() { + return (read == write); + }; + + void queue(T k) { + if (isFull()) { +// read++; +// read %= size; + return; + } + buf[write++] = k; + write %= size; + } + + void flush() { + read = 0; + write = 0; + } + + + uint32_t available() { + return (write >= read) ? write - read : size - read + write; + }; + + bool dequeue(T * c) { + bool empty = isEmpty(); + if (!empty) { + *c = buf[read++]; + read %= size; + } + return(!empty); + }; + +private: + volatile uint32_t write; + volatile uint32_t read; + uint32_t size; + T * buf; +}; + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/MIDI/.hgignore Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,19 @@ +syntax: regexp +\.hgignore$ +\.git$ +\.svn$ +\.orig$ +\.msub$ +\.meta$ +\.ctags +\.uvproj$ +\.uvopt$ +\.project$ +\.cproject$ +\.launch$ +\.project$ +\.cproject$ +\.launch$ +Makefile$ +\.ewp$ +\.eww$ \ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/MIDI/MIDI.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,1159 @@ +/*! + * @file MIDI.cpp + * Project MIDI Library + * @brief MIDI Library for the Arduino + * @version 3.2 + * @author Francois Best + * @date 24/02/11 + * license GPL Forty Seven Effects - 2011 + */ +/* + * Ported for mbed by Hiroshi Suga + * Orignal: http://www.arduino.cc/playground/Main/MIDILibrary + */ + +#include "MIDI.h" +#include "mbed.h" + + + +/*! \brief Default constructor for MIDI. */ +MIDI::MIDI(PinName p_tx, PinName p_rx) : _midi(p_tx, p_rx) +{ + uart_in = new CircBuffer <byte>(80); + +#if USE_CALLBACKS + + // Initialise callbacks to NULL pointer + mNoteOffCallback = NULL; + mNoteOnCallback = NULL; + mAfterTouchPolyCallback = NULL; + mControlChangeCallback = NULL; + mProgramChangeCallback = NULL; + mAfterTouchChannelCallback = NULL; + mPitchBendCallback = NULL; + mSystemExclusiveCallback = NULL; + mTimeCodeQuarterFrameCallback = NULL; + mSongPositionCallback = NULL; + mSongSelectCallback = NULL; + mTuneRequestCallback = NULL; + mClockCallback = NULL; + mStartCallback = NULL; + mContinueCallback = NULL; + mStopCallback = NULL; + mActiveSensingCallback = NULL; + mSystemResetCallback = NULL; + +#endif + +} + + +/*! \brief Default destructor for MIDI. + + This is not really useful for the Arduino, as it is never called... + */ +MIDI::~MIDI() +{ + +} + + +void MIDI::isr_rx () { + uart_in->queue(USE_SERIAL_PORT.getc()); +} + +/*! \brief Call the begin method in the setup() function of the Arduino. + + All parameters are set to their default values: + - Input channel set to 1 if no value is specified + - Full thru mirroring + */ +void MIDI::begin(const byte inChannel) +{ + + // Initialise the Serial port + USE_SERIAL_PORT.baud(MIDI_BAUDRATE); + USE_SERIAL_PORT.attach(this, &MIDI::isr_rx, Serial::RxIrq); + + +#if COMPILE_MIDI_OUT + +#if USE_RUNNING_STATUS + + mRunningStatus_TX = InvalidType; + +#endif // USE_RUNNING_STATUS + +#endif // COMPILE_MIDI_OUT + + +#if COMPILE_MIDI_IN + + mInputChannel = inChannel; + mRunningStatus_RX = InvalidType; + mPendingMessageIndex = 0; + mPendingMessageExpectedLenght = 0; + + mMessage.valid = false; + mMessage.type = InvalidType; + mMessage.channel = 0; + mMessage.data1 = 0; + mMessage.data2 = 0; + +#endif // COMPILE_MIDI_IN + + +#if (COMPILE_MIDI_IN && COMPILE_MIDI_OUT && COMPILE_MIDI_THRU) // Thru + + mThruFilterMode = Full; + mThruActivated = true; + +#endif // Thru + +} + + +#if COMPILE_MIDI_OUT + +// Private method for generating a status byte from channel and type +byte MIDI::genstatus(const kMIDIType inType, + const byte inChannel) const +{ + + return ((byte)inType | ((inChannel-1) & 0x0F)); + +} + + +/*! \brief Generate and send a MIDI message from the values given. + \param type The message type (see type defines for reference) + \param data1 The first data byte. + \param data2 The second data byte (if the message contains only 1 data byte, set this one to 0). + \param channel The output channel on which the message will be sent (values from 1 to 16). Note: you cannot send to OMNI. + + This is an internal method, use it only if you need to send raw data from your code, at your own risks. + */ +void MIDI::send(kMIDIType type, + byte data1, + byte data2, + byte channel) +{ + + // Then test if channel is valid +// if (channel >= MIDI_CHANNEL_OFF || channel == MIDI_CHANNEL_OMNI || type < NoteOff) { + if (channel >= MIDI_CHANNEL_OFF || channel < MIDI_CHANNEL_OMNI || type < NoteOff) { + +#if USE_RUNNING_STATUS + mRunningStatus_TX = InvalidType; +#endif + + return; // Don't send anything + } + + if (type <= PitchBend) { + // Channel messages + + // Protection: remove MSBs on data + data1 &= 0x7F; + data2 &= 0x7F; + + byte statusbyte = genstatus(type,channel); + +#if USE_RUNNING_STATUS + // Check Running Status + if (mRunningStatus_TX != statusbyte) { + // New message, memorise and send header + mRunningStatus_TX = statusbyte; + USE_SERIAL_PORT.putc(mRunningStatus_TX); + } +#else + // Don't care about running status, send the Control byte. + USE_SERIAL_PORT.putc(statusbyte); +#endif + + // Then send data + USE_SERIAL_PORT.putc(data1); + if (type != ProgramChange && type != AfterTouchChannel) { + USE_SERIAL_PORT.putc(data2); + } + return; + } + if (type >= TuneRequest && type <= SystemReset) { + // System Real-time and 1 byte. + sendRealTime(type); + } + +} + + +/*! \brief Send a Note On message + \param NoteNumber Pitch value in the MIDI format (0 to 127). Take a look at the values, names and frequencies of notes here: http://www.phys.unsw.edu.au/jw/notes.html\n + \param Velocity Note attack velocity (0 to 127). A NoteOn with 0 velocity is considered as a NoteOff. + \param Channel The channel on which the message will be sent (1 to 16). + */ +void MIDI::sendNoteOn(byte NoteNumber, + byte Velocity, + byte Channel) +{ + + send(NoteOn,NoteNumber,Velocity,Channel); + +} + + +/*! \brief Send a Note Off message (a real Note Off, not a Note On with null velocity) + \param NoteNumber Pitch value in the MIDI format (0 to 127). Take a look at the values, names and frequencies of notes here: http://www.phys.unsw.edu.au/jw/notes.html\n + \param Velocity Release velocity (0 to 127). + \param Channel The channel on which the message will be sent (1 to 16). + */ +void MIDI::sendNoteOff(byte NoteNumber, + byte Velocity, + byte Channel) +{ + + send(NoteOff,NoteNumber,Velocity,Channel); + +} + + +/*! \brief Send a Program Change message + \param ProgramNumber The Program to select (0 to 127). + \param Channel The channel on which the message will be sent (1 to 16). + */ +void MIDI::sendProgramChange(byte ProgramNumber, + byte Channel) +{ + + send(ProgramChange,ProgramNumber,0,Channel); + +} + + +/*! \brief Send a Control Change message + \param ControlNumber The controller number (0 to 127). See the detailed description here: http://www.somascape.org/midi/tech/spec.html#ctrlnums + \param ControlValue The value for the specified controller (0 to 127). + \param Channel The channel on which the message will be sent (1 to 16). + */ +void MIDI::sendControlChange(byte ControlNumber, + byte ControlValue, + byte Channel) +{ + + send(ControlChange,ControlNumber,ControlValue,Channel); + +} + + +/*! \brief Send a Polyphonic AfterTouch message (applies to only one specified note) + \param NoteNumber The note to apply AfterTouch to (0 to 127). + \param Pressure The amount of AfterTouch to apply (0 to 127). + \param Channel The channel on which the message will be sent (1 to 16). + */ +void MIDI::sendPolyPressure(byte NoteNumber, + byte Pressure, + byte Channel) +{ + + send(AfterTouchPoly,NoteNumber,Pressure,Channel); + +} + + +/*! \brief Send a MonoPhonic AfterTouch message (applies to all notes) + \param Pressure The amount of AfterTouch to apply to all notes. + \param Channel The channel on which the message will be sent (1 to 16). + */ +void MIDI::sendAfterTouch(byte Pressure, + byte Channel) +{ + + send(AfterTouchChannel,Pressure,0,Channel); + +} + + +/*! \brief Send a Pitch Bend message using a signed integer value. + \param PitchValue The amount of bend to send (in a signed integer format), between -8192 (maximum downwards bend) and 8191 (max upwards bend), center value is 0. + \param Channel The channel on which the message will be sent (1 to 16). + */ +void MIDI::sendPitchBend(int PitchValue, + byte Channel) +{ + + unsigned int bend = PitchValue + 8192; + sendPitchBend(bend,Channel); + +} + + +/*! \brief Send a Pitch Bend message using an unsigned integer value. + \param PitchValue The amount of bend to send (in a signed integer format), between 0 (maximum downwards bend) and 16383 (max upwards bend), center value is 8192. + \param Channel The channel on which the message will be sent (1 to 16). + */ +void MIDI::sendPitchBend(unsigned int PitchValue, + byte Channel) +{ + + send(PitchBend,(PitchValue & 0x7F),(PitchValue >> 7) & 0x7F,Channel); + +} + + +/*! \brief Send a Pitch Bend message using a floating point value. + \param PitchValue The amount of bend to send (in a floating point format), between -1.0f (maximum downwards bend) and +1.0f (max upwards bend), center value is 0.0f. + \param Channel The channel on which the message will be sent (1 to 16). + */ +void MIDI::sendPitchBend(double PitchValue, + byte Channel) +{ + + unsigned int pitchval = (PitchValue+1.f)*8192; + if (pitchval > 16383) pitchval = 16383; // overflow protection + sendPitchBend(pitchval,Channel); + +} + + +/*! \brief Generate and send a System Exclusive frame. + \param length The size of the array to send + \param array The byte array containing the data to send + \param ArrayContainsBoundaries When set to 'true', 0xF0 & 0xF7 bytes (start & stop SysEx) will NOT be sent (and therefore must be included in the array). + default value is set to 'false' for compatibility with previous versions of the library. + */ +void MIDI::sendSysEx(int length, + const byte *const array, + bool ArrayContainsBoundaries) +{ + + if (ArrayContainsBoundaries == false) { + + USE_SERIAL_PORT.putc(0xF0); + + for (int i=0;i<length;++i) { + + USE_SERIAL_PORT.putc(array[i]); + + } + + USE_SERIAL_PORT.putc(0xF7); + + } + else { + + for (int i=0;i<length;++i) { + + USE_SERIAL_PORT.putc(array[i]); + + } + + } + +#if USE_RUNNING_STATUS + mRunningStatus_TX = InvalidType; +#endif + +} + + +/*! \brief Send a Tune Request message. + + When a MIDI unit receives this message, it should tune its oscillators (if equipped with any) + */ +void MIDI::sendTuneRequest() +{ + + sendRealTime(TuneRequest); + +} + + +/*! \brief Send a MIDI Time Code Quarter Frame. + + See MIDI Specification for more information. + \param TypeNibble MTC type + \param ValuesNibble MTC data + */ +void MIDI::sendTimeCodeQuarterFrame(byte TypeNibble, byte ValuesNibble) +{ + + byte data = ( ((TypeNibble & 0x07) << 4) | (ValuesNibble & 0x0F) ); + sendTimeCodeQuarterFrame(data); + +} + + +/*! \brief Send a MIDI Time Code Quarter Frame. + + See MIDI Specification for more information. + \param data if you want to encode directly the nibbles in your program, you can send the byte here. + */ +void MIDI::sendTimeCodeQuarterFrame(byte data) +{ + + USE_SERIAL_PORT.putc((byte)TimeCodeQuarterFrame); + USE_SERIAL_PORT.putc(data); + +#if USE_RUNNING_STATUS + mRunningStatus_TX = InvalidType; +#endif + +} + + +/*! \brief Send a Song Position Pointer message. + \param Beats The number of beats since the start of the song. + */ +void MIDI::sendSongPosition(unsigned int Beats) +{ + + USE_SERIAL_PORT.putc((byte)SongPosition); + USE_SERIAL_PORT.putc(Beats & 0x7F); + USE_SERIAL_PORT.putc((Beats >> 7) & 0x7F); + +#if USE_RUNNING_STATUS + mRunningStatus_TX = InvalidType; +#endif + +} + + +/*! \brief Send a Song Select message */ +void MIDI::sendSongSelect(byte SongNumber) +{ + + USE_SERIAL_PORT.putc((byte)SongSelect); + USE_SERIAL_PORT.putc(SongNumber & 0x7F); + +#if USE_RUNNING_STATUS + mRunningStatus_TX = InvalidType; +#endif + +} + + +/*! \brief Send a Real Time (one byte) message. + + \param Type The available Real Time types are: Start, Stop, Continue, Clock, ActiveSensing and SystemReset. + You can also send a Tune Request with this method. + @see kMIDIType + */ +void MIDI::sendRealTime(kMIDIType Type) +{ + switch (Type) { + case TuneRequest: // Not really real-time, but one byte anyway. + case Clock: + case Start: + case Stop: + case Continue: + case ActiveSensing: + case SystemReset: + USE_SERIAL_PORT.putc((byte)Type); + break; + default: + // Invalid Real Time marker + break; + } + + // Do not cancel Running Status for real-time messages as they can be interleaved within any message. + // Though, TuneRequest can be sent here, and as it is a System Common message, it must reset Running Status. +#if USE_RUNNING_STATUS + if (Type == TuneRequest) mRunningStatus_TX = InvalidType; +#endif + +} + +#endif // COMPILE_MIDI_OUT + + + +#if COMPILE_MIDI_IN + +/*! \brief Read a MIDI message from the serial port using the main input channel (see setInputChannel() for reference). + + Returned value: true if any valid message has been stored in the structure, false if not. + A valid message is a message that matches the input channel. \n\n + If the Thru is enabled and the messages matches the filter, it is sent back on the MIDI output. + */ +bool MIDI::read() +{ + + return read(mInputChannel); + +} + + +/*! \brief Reading/thru-ing method, the same as read() with a given input channel to read on. */ +bool MIDI::read(const byte inChannel) +{ + + if (inChannel >= MIDI_CHANNEL_OFF) return false; // MIDI Input disabled. + + if (parse(inChannel)) { + + if (input_filter(inChannel)) { + +#if (COMPILE_MIDI_OUT && COMPILE_MIDI_THRU) + thru_filter(inChannel); +#endif + +#if USE_CALLBACKS + launchCallback(); +#endif + + return true; + } + + } + + return false; + +} + + +// Private method: MIDI parser +bool MIDI::parse(byte inChannel) +{ + +// const int bytes_available = USE_SERIAL_PORT.readable(); + const int bytes_available = !uart_in->isEmpty(); + + if (bytes_available <= 0) { + // No data available. + return false; + } + + // If the buffer is full -> Don't Panic! Call the Vogons to destroy it. + if (bytes_available == 128) { +// USE_SERIAL_PORT.flush(); + } + else { + + /* Parsing algorithm: + Get a byte from the serial buffer. + * If there is no pending message to be recomposed, start a new one. + - Find type and channel (if pertinent) + - Look for other bytes in buffer, call parser recursively, until the message is assembled or the buffer is empty. + * Else, add the extracted byte to the pending message, and check validity. When the message is done, store it. + */ + + +// const byte extracted = USE_SERIAL_PORT.getc(); + byte extracted; + uart_in->dequeue(&extracted); + + if (mPendingMessageIndex == 0) { // Start a new pending message + mPendingMessage[0] = extracted; + + // Check for running status first + switch (getTypeFromStatusByte(mRunningStatus_RX)) { + // Only these types allow Running Status: + case NoteOff: + case NoteOn: + case AfterTouchPoly: + case ControlChange: + case ProgramChange: + case AfterTouchChannel: + case PitchBend: + + // If the status byte is not received, prepend it to the pending message + if (extracted < 0x80) { + mPendingMessage[0] = mRunningStatus_RX; + mPendingMessage[1] = extracted; + mPendingMessageIndex = 1; + } + // Else: well, we received another status byte, so the running status does not apply here. + // It will be updated upon completion of this message. + + break; + + default: + // No running status + break; + } + + + switch (getTypeFromStatusByte(mPendingMessage[0])) { + + // 1 byte messages + case Start: + case Continue: + case Stop: + case Clock: + case ActiveSensing: + case SystemReset: + case TuneRequest: + // Handle the message type directly here. + mMessage.type = getTypeFromStatusByte(mPendingMessage[0]); + mMessage.channel = 0; + mMessage.data1 = 0; + mMessage.data2 = 0; + mMessage.valid = true; + + // \fix Running Status broken when receiving Clock messages. + // Do not reset all input attributes, Running Status must remain unchanged. + //reset_input_attributes(); + + // We still need to reset these + mPendingMessageIndex = 0; + mPendingMessageExpectedLenght = 0; + + return true; + + // 2 bytes messages + case ProgramChange: + case AfterTouchChannel: + case TimeCodeQuarterFrame: + case SongSelect: + mPendingMessageExpectedLenght = 2; + break; + + // 3 bytes messages + case NoteOn: + case NoteOff: + case ControlChange: + case PitchBend: + case AfterTouchPoly: + case SongPosition: + mPendingMessageExpectedLenght = 3; + break; + + case SystemExclusive: + mPendingMessageExpectedLenght = MIDI_SYSEX_ARRAY_SIZE; // As the message can be any lenght between 3 and MIDI_SYSEX_ARRAY_SIZE bytes + mRunningStatus_RX = InvalidType; + break; + + case InvalidType: + default: + // This is obviously wrong. Let's get the hell out'a here. + reset_input_attributes(); + return false; + } + + // Then update the index of the pending message. + mPendingMessageIndex++; + +#if USE_1BYTE_PARSING + // Message is not complete. + return false; +#else + // Call the parser recursively + // to parse the rest of the message. + return parse(inChannel); +#endif + + } + else { + + // First, test if this is a status byte + if (extracted >= 0x80) { + + // Reception of status bytes in the middle of an uncompleted message + // are allowed only for interleaved Real Time message or EOX + switch (extracted) { + case Clock: + case Start: + case Continue: + case Stop: + case ActiveSensing: + case SystemReset: + + /* + This is tricky. Here we will have to extract the one-byte message, + pass it to the structure for being read outside the MIDI class, + and recompose the message it was interleaved into. + + Oh, and without killing the running status.. + + This is done by leaving the pending message as is, it will be completed on next calls. + */ + + mMessage.type = (kMIDIType)extracted; + mMessage.data1 = 0; + mMessage.data2 = 0; + mMessage.channel = 0; + mMessage.valid = true; + return true; + + // End of Exclusive + case 0xF7: + if (getTypeFromStatusByte(mPendingMessage[0]) == SystemExclusive) { + + // Store System Exclusive array in midimsg structure + for (byte i=0;i<MIDI_SYSEX_ARRAY_SIZE;i++) { + mMessage.sysex_array[i] = mPendingMessage[i]; + } + + mMessage.type = SystemExclusive; + + // Get length + mMessage.data1 = (mPendingMessageIndex+1) & 0xFF; + mMessage.data2 = (mPendingMessageIndex+1) >> 8; + + mMessage.channel = 0; + mMessage.valid = true; + + reset_input_attributes(); + + return true; + } + else { + // Well well well.. error. + reset_input_attributes(); + return false; + } + + default: + break; + } + + + + } + + + // Add extracted data byte to pending message + mPendingMessage[mPendingMessageIndex] = extracted; + + + // Now we are going to check if we have reached the end of the message + if (mPendingMessageIndex >= (mPendingMessageExpectedLenght-1)) { + + // "FML" case: fall down here with an overflown SysEx.. + // This means we received the last possible data byte that can fit the buffer. + // If this happens, try increasing MIDI_SYSEX_ARRAY_SIZE. + if (getTypeFromStatusByte(mPendingMessage[0]) == SystemExclusive) { + reset_input_attributes(); + return false; + } + + + mMessage.type = getTypeFromStatusByte(mPendingMessage[0]); + mMessage.channel = (mPendingMessage[0] & 0x0F)+1; // Don't check if it is a Channel Message + + mMessage.data1 = mPendingMessage[1]; + + // Save data2 only if applicable + if (mPendingMessageExpectedLenght == 3) mMessage.data2 = mPendingMessage[2]; + else mMessage.data2 = 0; + + // Reset local variables + mPendingMessageIndex = 0; + mPendingMessageExpectedLenght = 0; + + mMessage.valid = true; + + // Activate running status (if enabled for the received type) + switch (mMessage.type) { + case NoteOff: + case NoteOn: + case AfterTouchPoly: + case ControlChange: + case ProgramChange: + case AfterTouchChannel: + case PitchBend: + // Running status enabled: store it from received message + mRunningStatus_RX = mPendingMessage[0]; + break; + + default: + // No running status + mRunningStatus_RX = InvalidType; + break; + } + return true; + } + else { + // Then update the index of the pending message. + mPendingMessageIndex++; + +#if USE_1BYTE_PARSING + // Message is not complete. + return false; +#else + // Call the parser recursively + // to parse the rest of the message. + return parse(inChannel); +#endif + + } + + } + + } + + // What are our chances to fall here? + return false; +} + + +// Private method: check if the received message is on the listened channel +bool MIDI::input_filter(byte inChannel) +{ + + + // This method handles recognition of channel (to know if the message is destinated to the Arduino) + + + if (mMessage.type == InvalidType) return false; + + + // First, check if the received message is Channel + if (mMessage.type >= NoteOff && mMessage.type <= PitchBend) { + + // Then we need to know if we listen to it + if ((mMessage.channel == mInputChannel) || (mInputChannel == MIDI_CHANNEL_OMNI)) { + return true; + + } + else { + // We don't listen to this channel + return false; + } + + } + else { + + // System messages are always received + return true; + } + +} + + +// Private method: reset input attributes +void MIDI::reset_input_attributes() +{ + + mPendingMessageIndex = 0; + mPendingMessageExpectedLenght = 0; + mRunningStatus_RX = InvalidType; + +} + + +// Getters +/*! \brief Get the last received message's type + + Returns an enumerated type. @see kMIDIType + */ +kMIDIType MIDI::getType() const +{ + + return mMessage.type; + +} + + +/*! \brief Get the channel of the message stored in the structure. + + Channel range is 1 to 16. For non-channel messages, this will return 0. + */ +byte MIDI::getChannel() const +{ + + return mMessage.channel; + +} + + +/*! \brief Get the first data byte of the last received message. */ +byte MIDI::getData1() const +{ + + return mMessage.data1; + +} + + +/*! \brief Get the second data byte of the last received message. */ +byte MIDI::getData2() const +{ + + return mMessage.data2; + +} + + +/*! \brief Get the System Exclusive byte array. + + @see getSysExArrayLength to get the array's length in bytes. + */ +const byte * MIDI::getSysExArray() const +{ + + return mMessage.sysex_array; + +} + +/*! \brief Get the lenght of the System Exclusive array. + + It is coded using data1 as LSB and data2 as MSB. + \return The array's length, in bytes. + */ +unsigned int MIDI::getSysExArrayLength() const +{ + + unsigned int coded_size = ((unsigned int)(mMessage.data2) << 8) | mMessage.data1; + + return (coded_size > MIDI_SYSEX_ARRAY_SIZE) ? MIDI_SYSEX_ARRAY_SIZE : coded_size; + +} + + +/*! \brief Check if a valid message is stored in the structure. */ +bool MIDI::check() const +{ + + return mMessage.valid; + +} + + +// Setters +/*! \brief Set the value for the input MIDI channel + \param Channel the channel value. Valid values are 1 to 16, + MIDI_CHANNEL_OMNI if you want to listen to all channels, and MIDI_CHANNEL_OFF to disable MIDI input. + */ +void MIDI::setInputChannel(const byte Channel) +{ + + mInputChannel = Channel; + +} + + +#if USE_CALLBACKS + +void MIDI::setHandleNoteOff(void (*fptr)(byte channel, byte note, byte velocity)) { mNoteOffCallback = fptr; } +void MIDI::setHandleNoteOn(void (*fptr)(byte channel, byte note, byte velocity)) { mNoteOnCallback = fptr; } +void MIDI::setHandleAfterTouchPoly(void (*fptr)(byte channel, byte note, byte pressure)) { mAfterTouchPolyCallback = fptr; } +void MIDI::setHandleControlChange(void (*fptr)(byte channel, byte number, byte value)) { mControlChangeCallback = fptr; } +void MIDI::setHandleProgramChange(void (*fptr)(byte channel, byte number)) { mProgramChangeCallback = fptr; } +void MIDI::setHandleAfterTouchChannel(void (*fptr)(byte channel, byte pressure)) { mAfterTouchChannelCallback = fptr; } +void MIDI::setHandlePitchBend(void (*fptr)(byte channel, int bend)) { mPitchBendCallback = fptr; } +void MIDI::setHandleSystemExclusive(void (*fptr)(byte * array, byte size)) { mSystemExclusiveCallback = fptr; } +void MIDI::setHandleTimeCodeQuarterFrame(void (*fptr)(byte data)) { mTimeCodeQuarterFrameCallback = fptr; } +void MIDI::setHandleSongPosition(void (*fptr)(unsigned int beats)) { mSongPositionCallback = fptr; } +void MIDI::setHandleSongSelect(void (*fptr)(byte songnumber)) { mSongSelectCallback = fptr; } +void MIDI::setHandleTuneRequest(void (*fptr)(void)) { mTuneRequestCallback = fptr; } +void MIDI::setHandleClock(void (*fptr)(void)) { mClockCallback = fptr; } +void MIDI::setHandleStart(void (*fptr)(void)) { mStartCallback = fptr; } +void MIDI::setHandleContinue(void (*fptr)(void)) { mContinueCallback = fptr; } +void MIDI::setHandleStop(void (*fptr)(void)) { mStopCallback = fptr; } +void MIDI::setHandleActiveSensing(void (*fptr)(void)) { mActiveSensingCallback = fptr; } +void MIDI::setHandleSystemReset(void (*fptr)(void)) { mSystemResetCallback = fptr; } + + +/*! \brief Detach an external function from the given type. + + Use this method to cancel the effects of setHandle********. + \param Type The type of message to unbind. When a message of this type is received, no function will be called. + */ +void MIDI::disconnectCallbackFromType(kMIDIType Type) +{ + + switch (Type) { + case NoteOff: mNoteOffCallback = NULL; break; + case NoteOn: mNoteOnCallback = NULL; break; + case AfterTouchPoly: mAfterTouchPolyCallback = NULL; break; + case ControlChange: mControlChangeCallback = NULL; break; + case ProgramChange: mProgramChangeCallback = NULL; break; + case AfterTouchChannel: mAfterTouchChannelCallback = NULL; break; + case PitchBend: mPitchBendCallback = NULL; break; + case SystemExclusive: mSystemExclusiveCallback = NULL; break; + case TimeCodeQuarterFrame: mTimeCodeQuarterFrameCallback = NULL; break; + case SongPosition: mSongPositionCallback = NULL; break; + case SongSelect: mSongSelectCallback = NULL; break; + case TuneRequest: mTuneRequestCallback = NULL; break; + case Clock: mClockCallback = NULL; break; + case Start: mStartCallback = NULL; break; + case Continue: mContinueCallback = NULL; break; + case Stop: mStopCallback = NULL; break; + case ActiveSensing: mActiveSensingCallback = NULL; break; + case SystemReset: mSystemResetCallback = NULL; break; + default: + break; + } + +} + + +// Private - launch callback function based on received type. +void MIDI::launchCallback() +{ + + // The order is mixed to allow frequent messages to trigger their callback faster. + + switch (mMessage.type) { + // Notes + case NoteOff: if (mNoteOffCallback != NULL) mNoteOffCallback(mMessage.channel,mMessage.data1,mMessage.data2); break; + case NoteOn: if (mNoteOnCallback != NULL) mNoteOnCallback(mMessage.channel,mMessage.data1,mMessage.data2); break; + + // Real-time messages + case Clock: if (mClockCallback != NULL) mClockCallback(); break; + case Start: if (mStartCallback != NULL) mStartCallback(); break; + case Continue: if (mContinueCallback != NULL) mContinueCallback(); break; + case Stop: if (mStopCallback != NULL) mStopCallback(); break; + case ActiveSensing: if (mActiveSensingCallback != NULL) mActiveSensingCallback(); break; + + // Continuous controllers + case ControlChange: if (mControlChangeCallback != NULL) mControlChangeCallback(mMessage.channel,mMessage.data1,mMessage.data2); break; + case PitchBend: if (mPitchBendCallback != NULL) mPitchBendCallback(mMessage.channel,(int)((mMessage.data1 & 0x7F) | ((mMessage.data2 & 0x7F)<< 7)) - 8192); break; // TODO: check this + case AfterTouchPoly: if (mAfterTouchPolyCallback != NULL) mAfterTouchPolyCallback(mMessage.channel,mMessage.data1,mMessage.data2); break; + case AfterTouchChannel: if (mAfterTouchChannelCallback != NULL) mAfterTouchChannelCallback(mMessage.channel,mMessage.data1); break; + + case ProgramChange: if (mProgramChangeCallback != NULL) mProgramChangeCallback(mMessage.channel,mMessage.data1); break; + case SystemExclusive: if (mSystemExclusiveCallback != NULL) mSystemExclusiveCallback(mMessage.sysex_array,mMessage.data1); break; + + // Occasional messages + case TimeCodeQuarterFrame: if (mTimeCodeQuarterFrameCallback != NULL) mTimeCodeQuarterFrameCallback(mMessage.data1); break; + case SongPosition: if (mSongPositionCallback != NULL) mSongPositionCallback((mMessage.data1 & 0x7F) | ((mMessage.data2 & 0x7F)<< 7)); break; + case SongSelect: if (mSongSelectCallback != NULL) mSongSelectCallback(mMessage.data1); break; + case TuneRequest: if (mTuneRequestCallback != NULL) mTuneRequestCallback(); break; + + case SystemReset: if (mSystemResetCallback != NULL) mSystemResetCallback(); break; + case InvalidType: + default: + break; + } + +} + + +#endif // USE_CALLBACKS + + +#endif // COMPILE_MIDI_IN + + + + +#if (COMPILE_MIDI_IN && COMPILE_MIDI_OUT && COMPILE_MIDI_THRU) // Thru + +/*! \brief Set the filter for thru mirroring + \param inThruFilterMode a filter mode + + @see kThruFilterMode + */ +void MIDI::setThruFilterMode(kThruFilterMode inThruFilterMode) +{ + + mThruFilterMode = inThruFilterMode; + if (mThruFilterMode != Off) mThruActivated = true; + else mThruActivated = false; + +} + + +/*! \brief Setter method: turn message mirroring on. */ +void MIDI::turnThruOn(kThruFilterMode inThruFilterMode) +{ + + mThruActivated = true; + mThruFilterMode = inThruFilterMode; + +} + + +/*! \brief Setter method: turn message mirroring off. */ +void MIDI::turnThruOff() +{ + + mThruActivated = false; + mThruFilterMode = Off; + +} + + +// This method is called upon reception of a message and takes care of Thru filtering and sending. +void MIDI::thru_filter(byte inChannel) +{ + + /* + This method handles Soft-Thru filtering. + + Soft-Thru filtering: + - All system messages (System Exclusive, Common and Real Time) are passed to output unless filter is set to Off + - Channel messages are passed to the output whether their channel is matching the input channel and the filter setting + + */ + + // If the feature is disabled, don't do anything. + if (!mThruActivated || (mThruFilterMode == Off)) return; + + + // First, check if the received message is Channel + if (mMessage.type >= NoteOff && mMessage.type <= PitchBend) { + + const bool filter_condition = ((mMessage.channel == mInputChannel) || (mInputChannel == MIDI_CHANNEL_OMNI)); + + // Now let's pass it to the output + switch (mThruFilterMode) { + case Full: + send(mMessage.type,mMessage.data1,mMessage.data2,mMessage.channel); + return; + case SameChannel: + if (filter_condition) { + send(mMessage.type,mMessage.data1,mMessage.data2,mMessage.channel); + return; + } + break; + case DifferentChannel: + if (!filter_condition) { + send(mMessage.type,mMessage.data1,mMessage.data2,mMessage.channel); + return; + } + break; + case Off: + // Do nothing. + // Technically it's impossible to get there because the case was already tested earlier. + break; + default: + break; + } + + } + else { + + // Send the message to the output + switch (mMessage.type) { + // Real Time and 1 byte + case Clock: + case Start: + case Stop: + case Continue: + case ActiveSensing: + case SystemReset: + case TuneRequest: + sendRealTime(mMessage.type); + return; + + case SystemExclusive: + // Send SysEx (0xF0 and 0xF7 are included in the buffer) + sendSysEx(mMessage.data1,mMessage.sysex_array,true); + return; + + case SongSelect: + sendSongSelect(mMessage.data1); + return; + + case SongPosition: + sendSongPosition(mMessage.data1 | ((unsigned)mMessage.data2<<7)); + return; + + case TimeCodeQuarterFrame: + sendTimeCodeQuarterFrame(mMessage.data1,mMessage.data2); + return; + + default: + break; + + } + + } + +} + + +#endif // Thru
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/MIDI/MIDI.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,322 @@ +/*! + * @file MIDI.h + * Project MIDI Library + * @brief MIDI Library for the Arduino + * Version 3.2 + * @author Francois Best + * @date 24/02/11 + * License GPL Forty Seven Effects - 2011 + */ +/* + * Ported for mbed by Hiroshi Suga + * Orignal: http://www.arduino.cc/playground/Main/MIDILibrary + */ + +#ifndef LIB_MIDI_H_ +#define LIB_MIDI_H_ + +#include "mbed.h" +#include "CBuffer.h" + + +/* + ############################################################### + # # + # CONFIGURATION AREA # + # # + # Here are a few settings you can change to customize # + # the library for your own project. You can for example # + # choose to compile only parts of it so you gain flash # + # space and optimise the speed of your sketch. # + # # + ############################################################### + */ + + +#define COMPILE_MIDI_IN 1 // Set this setting to 1 to use the MIDI input. +#define COMPILE_MIDI_OUT 1 // Set this setting to 1 to use the MIDI output. +#define COMPILE_MIDI_THRU 1 // Set this setting to 1 to use the MIDI Soft Thru feature + // Please note that the Thru will work only when both COMPILE_MIDI_IN and COMPILE_MIDI_OUT set to 1. + + +#define USE_SERIAL_PORT _midi // Change the number (to Serial1 for example) if you want + // to use a different serial port for MIDI I/O. + + +#define USE_RUNNING_STATUS 0 // Running status enables short messages when sending multiple values + // of the same type and channel. + // Set to 0 if you have troubles with controlling you hardware. + + +#define USE_CALLBACKS 1 // Set this to 1 if you want to use callback handlers (to bind your functions to the library). + // To use the callbacks, you need to have COMPILE_MIDI_IN set to 1 + +#define USE_1BYTE_PARSING 1 // Each call to MIDI.read will only parse one byte (might be faster). + + +// END OF CONFIGURATION AREA +// (do not modify anything under this line unless you know what you are doing) + + +#define MIDI_BAUDRATE 31250 + +#define MIDI_CHANNEL_OMNI 0 +#define MIDI_CHANNEL_OFF 17 // and over + +#define MIDI_SYSEX_ARRAY_SIZE 255 // Maximum size is 65535 bytes. + +/*! Type definition for practical use (because "unsigned char" is a bit long to write.. )*/ +typedef uint8_t byte; +typedef uint16_t word; + +/*! Enumeration of MIDI types */ +enum kMIDIType { + NoteOff = 0x80, ///< Note Off + NoteOn = 0x90, ///< Note On + AfterTouchPoly = 0xA0, ///< Polyphonic AfterTouch + ControlChange = 0xB0, ///< Control Change / Channel Mode + ProgramChange = 0xC0, ///< Program Change + AfterTouchChannel = 0xD0, ///< Channel (monophonic) AfterTouch + PitchBend = 0xE0, ///< Pitch Bend + SystemExclusive = 0xF0, ///< System Exclusive + TimeCodeQuarterFrame = 0xF1, ///< System Common - MIDI Time Code Quarter Frame + SongPosition = 0xF2, ///< System Common - Song Position Pointer + SongSelect = 0xF3, ///< System Common - Song Select + TuneRequest = 0xF6, ///< System Common - Tune Request + Clock = 0xF8, ///< System Real Time - Timing Clock + Start = 0xFA, ///< System Real Time - Start + Continue = 0xFB, ///< System Real Time - Continue + Stop = 0xFC, ///< System Real Time - Stop + ActiveSensing = 0xFE, ///< System Real Time - Active Sensing + SystemReset = 0xFF, ///< System Real Time - System Reset + InvalidType = 0x00 ///< For notifying errors +}; + +/*! Enumeration of Thru filter modes */ +enum kThruFilterMode { + Off = 0, ///< Thru disabled (nothing passes through). + Full = 1, ///< Fully enabled Thru (every incoming message is sent back). + SameChannel = 2, ///< Only the messages on the Input Channel will be sent back. + DifferentChannel = 3 ///< All the messages but the ones on the Input Channel will be sent back. +}; + + +/*! The midimsg structure contains decoded data of a MIDI message read from the serial port with read() or thru(). \n */ +struct midimsg { + /*! The MIDI channel on which the message was recieved. \n Value goes from 1 to 16. */ + byte channel; + /*! The type of the message (see the define section for types reference) */ + kMIDIType type; + /*! The first data byte.\n Value goes from 0 to 127.\n */ + byte data1; + /*! The second data byte. If the message is only 2 bytes long, this one is null.\n Value goes from 0 to 127. */ + byte data2; + /*! System Exclusive dedicated byte array. \n Array length is stocked on 16 bits, in data1 (LSB) and data2 (MSB) */ + byte sysex_array[MIDI_SYSEX_ARRAY_SIZE]; + /*! This boolean indicates if the message is valid or not. There is no channel consideration here, validity means the message respects the MIDI norm. */ + bool valid; +}; + + + + +/*! \brief The main class for MIDI handling.\n + See member descriptions to know how to use it, + or check out the examples supplied with the library. + */ +class MIDI { + + +public: + // Constructor and Destructor + MIDI(PinName p_tx, PinName p_rx); + ~MIDI(); + + + void begin(const byte inChannel = 1); + + + + +/* ####### OUTPUT COMPILATION BLOCK ####### */ +#if COMPILE_MIDI_OUT + +public: + + void sendNoteOn(byte NoteNumber,byte Velocity,byte Channel); + void sendNoteOff(byte NoteNumber,byte Velocity,byte Channel); + void sendProgramChange(byte ProgramNumber,byte Channel); + void sendControlChange(byte ControlNumber, byte ControlValue,byte Channel); + void sendPitchBend(int PitchValue,byte Channel); + void sendPitchBend(unsigned int PitchValue,byte Channel); + void sendPitchBend(double PitchValue,byte Channel); + void sendPolyPressure(byte NoteNumber,byte Pressure,byte Channel); + void sendAfterTouch(byte Pressure,byte Channel); + void sendSysEx(int length, const byte *const array,bool ArrayContainsBoundaries = false); + void sendTimeCodeQuarterFrame(byte TypeNibble, byte ValuesNibble); + void sendTimeCodeQuarterFrame(byte data); + void sendSongPosition(unsigned int Beats); + void sendSongSelect(byte SongNumber); + void sendTuneRequest(); + void sendRealTime(kMIDIType Type); + + void send(kMIDIType type, byte param1, byte param2, byte channel); + +private: + + RawSerial _midi; + byte genstatus(const kMIDIType inType,const byte inChannel) const; + + + // Attributes +#if USE_RUNNING_STATUS + byte mRunningStatus_TX; +#endif // USE_RUNNING_STATUS + +#endif // COMPILE_MIDI_OUT + + + +/* ####### INPUT COMPILATION BLOCK ####### */ +#if COMPILE_MIDI_IN + +public: + + bool read(); + bool read(const byte Channel); + + // Getters + kMIDIType getType() const; + byte getChannel() const; + byte getData1() const; + byte getData2() const; + const byte * getSysExArray() const; + unsigned int getSysExArrayLength() const; + bool check() const; + + byte getInputChannel() const + { + return mInputChannel; + } + + // Setters + void setInputChannel(const byte Channel); + + /*! \brief Extract an enumerated MIDI type from a status byte. + + This is a utility static method, used internally, made public so you can handle kMIDITypes more easily. + */ + static inline kMIDIType getTypeFromStatusByte(const byte inStatus) + { + if ((inStatus < 0x80) + || (inStatus == 0xF4) + || (inStatus == 0xF5) + || (inStatus == 0xF9) + || (inStatus == 0xFD)) return InvalidType; // data bytes and undefined. + if (inStatus < 0xF0) return (kMIDIType)(inStatus & 0xF0); // Channel message, remove channel nibble. + else return (kMIDIType)inStatus; + } + + +#if USE_CALLBACKS + + void setHandleNoteOff(void (*fptr)(byte channel, byte note, byte velocity)); + void setHandleNoteOn(void (*fptr)(byte channel, byte note, byte velocity)); + void setHandleAfterTouchPoly(void (*fptr)(byte channel, byte note, byte pressure)); + void setHandleControlChange(void (*fptr)(byte channel, byte number, byte value)); + void setHandleProgramChange(void (*fptr)(byte channel, byte number)); + void setHandleAfterTouchChannel(void (*fptr)(byte channel, byte pressure)); + void setHandlePitchBend(void (*fptr)(byte channel, int bend)); + void setHandleSystemExclusive(void (*fptr)(byte * array, byte size)); + void setHandleTimeCodeQuarterFrame(void (*fptr)(byte data)); + void setHandleSongPosition(void (*fptr)(unsigned int beats)); + void setHandleSongSelect(void (*fptr)(byte songnumber)); + void setHandleTuneRequest(void (*fptr)(void)); + void setHandleClock(void (*fptr)(void)); + void setHandleStart(void (*fptr)(void)); + void setHandleContinue(void (*fptr)(void)); + void setHandleStop(void (*fptr)(void)); + void setHandleActiveSensing(void (*fptr)(void)); + void setHandleSystemReset(void (*fptr)(void)); + + void disconnectCallbackFromType(kMIDIType Type); + +#endif // USE_CALLBACKS + + +private: + + bool input_filter(byte inChannel); + bool parse(byte inChannel); + void reset_input_attributes(); + + // Attributes + byte mRunningStatus_RX; + byte mInputChannel; + + byte mPendingMessage[MIDI_SYSEX_ARRAY_SIZE]; + unsigned int mPendingMessageExpectedLenght; + unsigned int mPendingMessageIndex; // Extended to unsigned int for larger sysex payloads. + + midimsg mMessage; + +#if USE_CALLBACKS + + void launchCallback(); + + void (*mNoteOffCallback)(byte channel, byte note, byte velocity); + void (*mNoteOnCallback)(byte channel, byte note, byte velocity); + void (*mAfterTouchPolyCallback)(byte channel, byte note, byte velocity); + void (*mControlChangeCallback)(byte channel, byte, byte); + void (*mProgramChangeCallback)(byte channel, byte); + void (*mAfterTouchChannelCallback)(byte channel, byte); + void (*mPitchBendCallback)(byte channel, int); + void (*mSystemExclusiveCallback)(byte * array, byte size); + void (*mTimeCodeQuarterFrameCallback)(byte data); + void (*mSongPositionCallback)(unsigned int beats); + void (*mSongSelectCallback)(byte songnumber); + void (*mTuneRequestCallback)(void); + void (*mClockCallback)(void); + void (*mStartCallback)(void); + void (*mContinueCallback)(void); + void (*mStopCallback)(void); + void (*mActiveSensingCallback)(void); + void (*mSystemResetCallback)(void); + +#endif // USE_CALLBACKS + + +#endif // COMPILE_MIDI_IN + + +/* ####### THRU COMPILATION BLOCK ####### */ +#if (COMPILE_MIDI_IN && COMPILE_MIDI_OUT && COMPILE_MIDI_THRU) // Thru + +public: + + // Getters + kThruFilterMode getFilterMode() const { return mThruFilterMode; } + bool getThruState() const { return mThruActivated; } + + + // Setters + void turnThruOn(kThruFilterMode inThruFilterMode = Full); + void turnThruOff(); + + void setThruFilterMode(const kThruFilterMode inThruFilterMode); + + +private: + + void thru_filter(byte inChannel); + void isr_rx(); + + bool mThruActivated; + kThruFilterMode mThruFilterMode; + CircBuffer <byte>*uart_in; + +#endif // Thru + +}; + +#endif // LIB_MIDI_H_
--- a/USBHost.lib Wed Jan 03 08:07:31 2018 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1 +0,0 @@ -https://os.mbed.com/users/mbed_official/code/USBHost/#7c3b59bb364e
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/FATFileSystem.lib Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,1 @@ +https://developer.mbed.org/teams/mbed-official/code/FATFileSystem/#28e685e5ff7f
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost/IUSBEnumerator.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,36 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 IUSBENUMERATOR_H_ +#define IUSBENUMERATOR_H_ + +#include "stdint.h" +#include "USBEndpoint.h" + +/* +Generic interface to implement for "smart" USB enumeration +*/ + +class IUSBEnumerator +{ +public: + virtual void setVidPid(uint16_t vid, uint16_t pid) = 0; + virtual bool parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) = 0; //Must return true if the interface should be parsed + virtual bool useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir) = 0; //Must return true if the endpoint will be used +}; + +#endif /*IUSBENUMERATOR_H_*/ +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost/USBDeviceConnected.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,124 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 "USBDeviceConnected.h" +#include "dbg.h" + +USBDeviceConnected::USBDeviceConnected() { + init(); +} + +void USBDeviceConnected::init() { + hub_nb = 0; + port = 0; + vid = 0; + pid = 0; + nb_interf = 0; + enumerated = false; + activeAddr = false; + sizeControlEndpoint = 8; + device_class = 0; + device_subclass = 0; + proto = 0; + speed = false; + for (int i = 0; i < MAX_INTF; i++) { + memset((void *)&intf[i], 0, sizeof(INTERFACE)); + intf[i].in_use = false; + for (int j = 0; j < MAX_ENDPOINT_PER_INTERFACE; j++) { + intf[i].ep[j] = NULL; + strcpy(intf[i].name, "Unknown"); + } + } + hub_parent = NULL; + hub = NULL; + nb_interf = 0; +} + +INTERFACE * USBDeviceConnected::getInterface(uint8_t index) { + if (index >= MAX_INTF) + return NULL; + + if (intf[index].in_use) + return &intf[index]; + + return NULL; +} + +bool USBDeviceConnected::addInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) { + if ((intf_nb >= MAX_INTF) || (intf[intf_nb].in_use)) { + return false; + } + intf[intf_nb].in_use = true; + intf[intf_nb].intf_class = intf_class; + intf[intf_nb].intf_subclass = intf_subclass; + intf[intf_nb].intf_protocol = intf_protocol; + intf[intf_nb].nb_endpoint = 0; + return true; +} + +bool USBDeviceConnected::addEndpoint(uint8_t intf_nb, USBEndpoint * ept) { + if ((intf_nb >= MAX_INTF) || (intf[intf_nb].in_use == false) || (intf[intf_nb].nb_endpoint >= MAX_ENDPOINT_PER_INTERFACE)) { + return false; + } + intf[intf_nb].nb_endpoint++; + + for (int i = 0; i < MAX_ENDPOINT_PER_INTERFACE; i++) { + if (intf[intf_nb].ep[i] == NULL) { + intf[intf_nb].ep[i] = ept; + return true; + } + } + return false; +} + +void USBDeviceConnected::init(uint8_t hub_, uint8_t port_, bool lowSpeed_) { + USB_DBG("init dev: %p", this); + init(); + hub_nb = hub_; + port = port_; + speed = lowSpeed_; +} + +void USBDeviceConnected::disconnect() { + for(int i = 0; i < MAX_INTF; i++) { + if (intf[i].detach) intf[i].detach.call(); + } + init(); +} + + +USBEndpoint * USBDeviceConnected::getEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir, uint8_t index) { + if (intf_nb >= MAX_INTF) { + return NULL; + } + for (int i = 0; i < MAX_ENDPOINT_PER_INTERFACE; i++) { + if ((intf[intf_nb].ep[i]->getType() == type) && (intf[intf_nb].ep[i]->getDir() == dir)) { + if(index) { + index--; + } else { + return intf[intf_nb].ep[i]; + } + } + } + return NULL; +} + +USBEndpoint * USBDeviceConnected::getEndpoint(uint8_t intf_nb, uint8_t index) { + if ((intf_nb >= MAX_INTF) || (index >= MAX_ENDPOINT_PER_INTERFACE)) { + return NULL; + } + return intf[intf_nb].ep[index]; +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost/USBDeviceConnected.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,186 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBDEVICECONNECTED_H +#define USBDEVICECONNECTED_H + +#include "stdint.h" +#include "USBEndpoint.h" +#include "USBHostConf.h" +#include "rtos.h" +#include "Callback.h" + +class USBHostHub; + +typedef struct { + bool in_use; + uint8_t nb_endpoint; + uint8_t intf_class; + uint8_t intf_subclass; + uint8_t intf_protocol; + USBEndpoint * ep[MAX_ENDPOINT_PER_INTERFACE]; + Callback<void()> detach; + char name[10]; +} INTERFACE; + +/** +* USBDeviceConnected class +*/ +class USBDeviceConnected +{ +public: + + /** + * Constructor + */ + USBDeviceConnected(); + + /** + * Attach an USBEndpoint to this device + * + * @param intf_nb interface number + * @param ep pointeur on the USBEndpoint which will be attached + * @returns true if successful, false otherwise + */ + bool addEndpoint(uint8_t intf_nb, USBEndpoint * ep); + + /** + * Retrieve an USBEndpoint by its TYPE and DIRECTION + * + * @param intf_nb the interface on which to lookup the USBEndpoint + * @param type type of the USBEndpoint looked for + * @param dir direction of the USBEndpoint looked for + * @param index the index of the USBEndpoint whitin the interface + * @returns pointer on the USBEndpoint if found, NULL otherwise + */ + USBEndpoint * getEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir, uint8_t index = 0); + + /** + * Retrieve an USBEndpoint by its index + * + * @param intf_nb interface number + * @param index index of the USBEndpoint + * @returns pointer on the USBEndpoint if found, NULL otherwise + */ + USBEndpoint * getEndpoint(uint8_t intf_nb, uint8_t index); + + /** + * Add a new interface to this device + * + * @param intf_nb interface number + * @param intf_class interface class + * @param intf_subclass interface subclass + * @param intf_protocol interface protocol + * @returns true if successful, false otherwise + */ + bool addInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol); + + /** + * Get a specific interface + * + * @param index index of the interface to be fetched + * @returns interface + */ + INTERFACE * getInterface(uint8_t index); + + /** + * Attach a member function to call when a the device has been disconnected + * + * @param intf_nb interface number + * @param tptr pointer to the object to call the member function on + * @param mptr pointer to the member function to be called + */ + template<typename T> + inline void onDisconnect(uint8_t intf_nb, T* tptr, void (T::*mptr)(void)) { + if ((mptr != NULL) && (tptr != NULL)) { + intf[intf_nb].detach.attach(tptr, mptr); + } + } + + /** + * Attach a callback called when the device has been disconnected + * + * @param intf_nb interface number + * @param fn function pointer + */ + inline void onDisconnect(uint8_t intf_nb, void (*fn)(void)) { + if (fn != NULL) { + intf[intf_nb].detach.attach(fn); + } + } + + /** + * Disconnect the device by calling a callback function registered by a driver + */ + void disconnect(); + + // setters + void init(uint8_t hub, uint8_t port, bool lowSpeed); + inline void setAddress(uint8_t addr_) { addr = addr_; }; + inline void setVid(uint16_t vid_) { vid = vid_; }; + inline void setPid(uint16_t pid_) { pid = pid_; }; + inline void setClass(uint8_t device_class_) { device_class = device_class_; }; + inline void setSubClass(uint8_t device_subclass_) { device_subclass = device_subclass_; }; + inline void setProtocol(uint8_t pr) { proto = pr; }; + inline void setSizeControlEndpoint(uint32_t size) { sizeControlEndpoint = size; }; + inline void activeAddress(bool active) { activeAddr = active; }; + inline void setEnumerated() { enumerated = true; }; + inline void setNbIntf(uint8_t nb_intf) {nb_interf = nb_intf; }; + inline void setHubParent(USBHostHub * hub) { hub_parent = hub; }; + inline void setName(const char * name_, uint8_t intf_nb) { strcpy(intf[intf_nb].name, name_); }; + + //getters + inline uint8_t getPort() { return port; }; + inline uint8_t getHub() { return hub_nb; }; + inline uint8_t getAddress() { return addr; }; + inline uint16_t getVid() { return vid; }; + inline uint16_t getPid() { return pid; }; + inline uint8_t getClass() { return device_class; }; + inline uint8_t getSubClass() { return device_subclass; }; + inline uint8_t getProtocol() { return proto; }; + inline bool getSpeed() { return speed; }; + inline uint32_t getSizeControlEndpoint() { return sizeControlEndpoint; }; + inline bool isActiveAddress() { return activeAddr; }; + inline bool isEnumerated() { return enumerated; }; + inline USBHostHub * getHubParent() { return hub_parent; }; + inline uint8_t getNbIntf() { return nb_interf; }; + inline const char * getName(uint8_t intf_nb) { return intf[intf_nb].name; }; + + // in case this device is a hub + USBHostHub * hub; + +private: + USBHostHub * hub_parent; + + INTERFACE intf[MAX_INTF]; + uint32_t sizeControlEndpoint; + uint8_t hub_nb; + uint8_t port; + uint16_t vid; + uint16_t pid; + uint8_t addr; + uint8_t device_class; + uint8_t device_subclass; + uint8_t proto; + bool speed; + volatile bool activeAddr; + volatile bool enumerated; + uint8_t nb_interf; + + void init(); +}; + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost/USBEndpoint.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,163 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 "dbg.h" +#include "USBEndpoint.h" +#if !defined(USBHOST_OTHER) +void USBEndpoint::init(HCED * hced_, ENDPOINT_TYPE type_, ENDPOINT_DIRECTION dir_, uint32_t size, uint8_t ep_number, HCTD* td_list_[2]) +{ + hced = hced_; + type = type_; + dir = dir_; + setup = (type == CONTROL_ENDPOINT) ? true : false; + + //TDs have been allocated by the host + memcpy((HCTD**)td_list, td_list_, sizeof(HCTD*)*2); //TODO: Maybe should add a param for td_list size... at least a define + memset(td_list_[0], 0, sizeof(HCTD)); + memset(td_list_[1], 0, sizeof(HCTD)); + + td_list[0]->ep = this; + td_list[1]->ep = this; + + hced->control = 0; + //Empty queue + hced->tailTD = td_list[0]; + hced->headTD = td_list[0]; + hced->nextED = 0; + + address = (ep_number & 0x7F) | ((dir - 1) << 7); + + hced->control = ((ep_number & 0x7F) << 7) // Endpoint address + | (type != CONTROL_ENDPOINT ? ( dir << 11) : 0 ) // direction : Out = 1, 2 = In + | ((size & 0x3ff) << 16); // MaxPkt Size + + transfer_len = 0; + transferred = 0; + buf_start = 0; + nextEp = NULL; + + td_current = td_list[0]; + td_next = td_list[1]; + + intf_nb = 0; + + state = USB_TYPE_IDLE; +} + +void USBEndpoint::setSize(uint32_t size) +{ + hced->control &= ~(0x3ff << 16); + hced->control |= (size << 16); +} + + +void USBEndpoint::setDeviceAddress(uint8_t addr) +{ + hced->control &= ~(0x7f); + hced->control |= (addr & 0x7F); +} + +void USBEndpoint::setSpeed(uint8_t speed) +{ + hced->control &= ~(1 << 13); + hced->control |= (speed << 13); +} +#endif + +//Only for control Eps +void USBEndpoint::setNextToken(uint32_t token) +{ + switch (token) { + case TD_SETUP: + dir = OUT; + setup = true; + break; + case TD_IN: + dir = IN; + setup = false; + break; + case TD_OUT: + dir = OUT; + setup = false; + break; + } +} +struct { + USB_TYPE type; + const char * str; +} static type_string[] = { +/*0*/ {USB_TYPE_OK, "USB_TYPE_OK"}, + {USB_TYPE_CRC_ERROR, "USB_TYPE_CRC_ERROR"}, + {USB_TYPE_BIT_STUFFING_ERROR, "USB_TYPE_BIT_STUFFING_ERROR"}, + {USB_TYPE_DATA_TOGGLE_MISMATCH_ERROR, "USB_TYPE_DATA_TOGGLE_MISMATCH_ERROR"}, + {USB_TYPE_STALL_ERROR, "USB_TYPE_STALL_ERROR"}, +/*5*/ {USB_TYPE_DEVICE_NOT_RESPONDING_ERROR, "USB_TYPE_DEVICE_NOT_RESPONDING_ERROR"}, + {USB_TYPE_PID_CHECK_FAILURE_ERROR, "USB_TYPE_PID_CHECK_FAILURE_ERROR"}, + {USB_TYPE_UNEXPECTED_PID_ERROR, "USB_TYPE_UNEXPECTED_PID_ERROR"}, + {USB_TYPE_DATA_OVERRUN_ERROR, "USB_TYPE_DATA_OVERRUN_ERROR"}, + {USB_TYPE_DATA_UNDERRUN_ERROR, "USB_TYPE_DATA_UNDERRUN_ERROR"}, +/*10*/ {USB_TYPE_ERROR, "USB_TYPE_ERROR"}, + {USB_TYPE_ERROR, "USB_TYPE_ERROR"}, + {USB_TYPE_BUFFER_OVERRUN_ERROR, "USB_TYPE_BUFFER_OVERRUN_ERROR"}, + {USB_TYPE_BUFFER_UNDERRUN_ERROR, "USB_TYPE_BUFFER_UNDERRUN_ERROR"}, + {USB_TYPE_DISCONNECTED, "USB_TYPE_DISCONNECTED"}, +/*15*/ {USB_TYPE_FREE, "USB_TYPE_FREE"}, + {USB_TYPE_IDLE, "USB_TYPE_IDLE"}, + {USB_TYPE_PROCESSING, "USB_TYPE_PROCESSING"}, + {USB_TYPE_ERROR, "USB_TYPE_ERROR"} +}; +const char * USBEndpoint::getStateString() { + return type_string[state].str; +} + +#if !defined(USBHOST_OTHER) +void USBEndpoint::setState(uint8_t st) { + if (st > 18) + return; + state = type_string[st].type; +} + +USB_TYPE USBEndpoint::queueTransfer() +{ + transfer_len = (uint32_t)td_current->bufEnd - (uint32_t)td_current->currBufPtr + 1; + transferred = transfer_len; + buf_start = (uint8_t *)td_current->currBufPtr; + + //Now add this free TD at this end of the queue + state = USB_TYPE_PROCESSING; + td_current->nextTD = (hcTd*)td_next; + hced->tailTD = td_next; + return USB_TYPE_PROCESSING; +} + +void USBEndpoint::unqueueTransfer(volatile HCTD * td) +{ + td->control=0; + td->currBufPtr=0; + td->bufEnd=0; + td->nextTD=0; + hced->headTD = (HCTD *)((uint32_t)hced->tailTD | ((uint32_t)hced->headTD & 0x2)); //Carry bit + td_current = td_next; + td_next = td; +} + +void USBEndpoint::queueEndpoint(USBEndpoint * ed) +{ + nextEp = ed; + hced->nextED = (ed == NULL) ? 0 : (hcEd*)(ed->getHCED()); +} +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost/USBEndpoint.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,191 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBENDPOINT_H +#define USBENDPOINT_H + +#include "Callback.h" +#include "USBHostTypes.h" +#include "rtos.h" + +class USBDeviceConnected; + +/** +* USBEndpoint class +*/ +class USBEndpoint +{ +public: + /** + * Constructor + */ + USBEndpoint() { +#ifdef USBHOST_OTHER + speed = false; +#endif + state = USB_TYPE_FREE; + nextEp = NULL; + }; + + /** + * Initialize an endpoint + * + * @param hced hced associated to the endpoint + * @param type endpoint type + * @param dir endpoint direction + * @param size endpoint size + * @param ep_number endpoint number + * @param td_list array of two allocated transfer descriptors + */ + + void init(HCED * hced, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir, uint32_t size, uint8_t ep_number, HCTD* td_list[2]); + + /** + * Set next token. Warning: only useful for the control endpoint + * + * @param token IN, OUT or SETUP token + */ + void setNextToken(uint32_t token); + + /** + * Queue an endpoint + * + * @param endpoint endpoint which will be queued in the linked list + */ + void queueEndpoint(USBEndpoint * endpoint); + + + /** + * Queue a transfer on the endpoint + */ + USB_TYPE queueTransfer(); + + /** + * Unqueue a transfer from the endpoint + * + * @param td hctd which will be unqueued + */ + void unqueueTransfer(volatile HCTD * td); + + /** + * Attach a member function to call when a transfer is finished + * + * @param tptr pointer to the object to call the member function on + * @param mptr pointer to the member function to be called + */ + template<typename T> + inline void attach(T* tptr, void (T::*mptr)(void)) { + if((mptr != NULL) && (tptr != NULL)) { + rx.attach(tptr, mptr); + } + } + + /** + * Attach a callback called when a transfer is finished + * + * @param fptr function pointer + */ + inline void attach(void (*fptr)(void)) { + if(fptr != NULL) { + rx.attach(fptr); + } + } + + /** + * Call the handler associted to the end of a transfer + */ + inline void call() { + if (rx) + rx.call(); + }; + + + // setters +#ifdef USBHOST_OTHER + void setState(USB_TYPE st); +#else + inline void setState(USB_TYPE st) { state = st; } +#endif + void setState(uint8_t st); + void setDeviceAddress(uint8_t addr); + inline void setLengthTransferred(int len) { transferred = len; }; + void setSpeed(uint8_t speed); + void setSize(uint32_t size); + inline void setDir(ENDPOINT_DIRECTION d) { dir = d; } + inline void setIntfNb(uint8_t intf_nb_) { intf_nb = intf_nb_; }; + + // getters + const char * getStateString(); + inline USB_TYPE getState() { return state; } + inline ENDPOINT_TYPE getType() { return type; }; +#ifdef USBHOST_OTHER + inline uint8_t getDeviceAddress() { return device_address; }; + inline uint32_t getSize() { return size; }; +#else + inline uint8_t getDeviceAddress() { return hced->control & 0x7f; }; + inline uint32_t getSize() { return (hced->control >> 16) & 0x3ff; }; + inline volatile HCTD * getHeadTD() { return (volatile HCTD*) ((uint32_t)hced->headTD & ~0xF); }; +#endif + inline int getLengthTransferred() { return transferred; } + inline uint8_t * getBufStart() { return buf_start; } + inline uint8_t getAddress(){ return address; }; + inline volatile HCTD** getTDList() { return td_list; }; + inline volatile HCED * getHCED() { return hced; }; + inline ENDPOINT_DIRECTION getDir() { return dir; } + inline volatile HCTD * getProcessedTD() { return td_current; }; + inline volatile HCTD* getNextTD() { return td_current; }; + inline bool isSetup() { return setup; } + inline USBEndpoint * nextEndpoint() { return (USBEndpoint*)nextEp; }; + inline uint8_t getIntfNb() { return intf_nb; }; + + USBDeviceConnected * dev; + + Queue<uint8_t, 1> ep_queue; + +private: + ENDPOINT_TYPE type; + volatile USB_TYPE state; + ENDPOINT_DIRECTION dir; +#ifdef USBHOST_OTHER + uint32_t size; + uint32_t ep_number; + uint32_t speed; + uint8_t device_address; +#endif + bool setup; + + uint8_t address; + + int transfer_len; + int transferred; + uint8_t * buf_start; + + Callback<void()> rx; + + USBEndpoint* nextEp; + + // USBEndpoint descriptor + volatile HCED * hced; + + volatile HCTD * td_list[2]; + volatile HCTD * td_current; + volatile HCTD * td_next; + + uint8_t intf_nb; + +}; + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost/USBHALHost.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,173 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBHALHOST_H +#define USBHALHOST_H + +#include "USBHostTypes.h" +#include "USBHostConf.h" + +class USBHostHub; + +/** +* USBHALHost class +*/ +class USBHALHost { +protected: + + /** + * Constructor + * init variables and memory where will be stored HCCA, ED and TD + */ + USBHALHost(); + + /** + * Initialize host controller. Enable USB interrupts. This part is not in the constructor because, + * this function calls a virtual method if a device is already connected + */ + void init(); + + /** + * reset the root hub + */ + void resetRootHub(); + + /** + * return the value contained in the control HEAD ED register + * + * @returns address of the control Head ED + */ + uint32_t controlHeadED(); + + /** + * return the value contained in the bulk HEAD ED register + * + * @returns address of the bulk head ED + */ + uint32_t bulkHeadED(); + + /** + * return the value of the head interrupt ED contained in the HCCA + * + * @returns address of the head interrupt ED contained in the HCCA + */ + uint32_t interruptHeadED(); + + /** + * Update the head ED for control transfers + */ + void updateControlHeadED(uint32_t addr); + + /** + * Update the head ED for bulk transfers + */ + void updateBulkHeadED(uint32_t addr); + + /** + * Update the head ED for interrupt transfers + */ + void updateInterruptHeadED(uint32_t addr); + + /** + * Enable List for the specified endpoint type + * + * @param type enable the list of ENDPOINT_TYPE type + */ + void enableList(ENDPOINT_TYPE type); + + /** + * Disable List for the specified endpoint type + * + * @param type disable the list of ENDPOINT_TYPE type + */ + bool disableList(ENDPOINT_TYPE type); + + /** + * Virtual method called when a device has been connected + * + * @param hub hub number of the device + * @param port port number of the device + * @param lowSpeed 1 if low speed, 0 otherwise + * @param hub_parent reference to the hub where the device is connected (NULL if the hub parent is the root hub) + */ + virtual void deviceConnected(int hub, int port, bool lowSpeed, USBHostHub * hub_parent = NULL) = 0; + + /** + * Virtual method called when a device has been disconnected + * + * @param hub hub number of the device + * @param port port number of the device + * @param hub_parent reference to the hub where the device is connected (NULL if the hub parent is the root hub) + * @param addr list of the TDs which have been completed to dequeue freed TDs + */ + virtual void deviceDisconnected(int hub, int port, USBHostHub * hub_parent, volatile uint32_t addr) = 0; + + /** + * Virtual method called when a transfer has been completed + * + * @param addr list of the TDs which have been completed + */ + virtual void transferCompleted(volatile uint32_t addr) = 0; + + /** + * Find a memory section for a new ED + * + * @returns the address of the new ED + */ + volatile uint8_t * getED(); + + /** + * Find a memory section for a new TD + * + * @returns the address of the new TD + */ + volatile uint8_t * getTD(); + + /** + * Release a previous memory section reserved for an ED + * + * @param ed address of the ED + */ + void freeED(volatile uint8_t * ed); + + /** + * Release a previous memory section reserved for an TD + * + * @param td address of the TD + */ + void freeTD(volatile uint8_t * td); + +private: + static void _usbisr(void); + void UsbIrqhandler(); + + void memInit(); + + HCCA volatile * usb_hcca; //256 bytes aligned + uint8_t volatile * usb_edBuf; //4 bytes aligned + uint8_t volatile * usb_tdBuf; //4 bytes aligned + + static USBHALHost * instHost; + + bool volatile edBufAlloc[MAX_ENDPOINT]; + bool volatile tdBufAlloc[MAX_TD]; +#ifdef USBHOST_OTHER + int control_disable; +#endif + +}; + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost/USBHost.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,1295 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 "USBHost.h" +#include "USBHostHub.h" + +USBHost * USBHost::instHost = NULL; + +#define DEVICE_CONNECTED_EVENT (1 << 0) +#define DEVICE_DISCONNECTED_EVENT (1 << 1) +#define TD_PROCESSED_EVENT (1 << 2) + +#define MAX_TRY_ENUMERATE_HUB 3 + +#define MIN(a, b) ((a > b) ? b : a) + +/** +* How interrupts are processed: +* - new device connected: +* - a message is queued in queue_usb_event with the id DEVICE_CONNECTED_EVENT +* - when the usb_thread receives the event, it: +* - resets the device +* - reads the device descriptor +* - sets the address of the device +* - if it is a hub, enumerates it +* - device disconnected: +* - a message is queued in queue_usb_event with the id DEVICE_DISCONNECTED_EVENT +* - when the usb_thread receives the event, it: +* - free the device and all its children (hub) +* - td processed +* - a message is queued in queue_usb_event with the id TD_PROCESSED_EVENT +* - when the usb_thread receives the event, it: +* - call the callback attached to the endpoint where the td is attached +*/ +void USBHost::usb_process() +{ + + bool controlListState; + bool bulkListState; + bool interruptListState; + USBEndpoint * ep; + uint8_t i, j, res, timeout_set_addr = 10; + uint8_t buf[8]; + bool too_many_hub; + int idx; + +#if DEBUG_TRANSFER + uint8_t * buf_transfer; +#endif + +#if MAX_HUB_NB + uint8_t k; +#endif + + while(1) { + osEvent evt = mail_usb_event.get(); + + if (evt.status == osEventMail) { + + message_t * usb_msg = (message_t*)evt.value.p; + + switch (usb_msg->event_id) { + + // a new device has been connected + case DEVICE_CONNECTED_EVENT: + too_many_hub = false; + buf[4] = 0; + + do { + Lock lock(this); + bool hub_unplugged = true; + + int idx = findDevice(usb_msg->hub, usb_msg->port, (USBHostHub *)(usb_msg->hub_parent)); + /* check that hub is connected to root port */ + if (usb_msg->hub_parent) { + /* a hub device must be present */ + for (k = 0; k < MAX_HUB_NB; k++) { + if ((&hubs[k] == usb_msg->hub_parent) && (hub_in_use[k])) { + hub_unplugged=false; + } + } + } else { + hub_unplugged = false; + } + + if (((idx!=-1) && deviceInUse[idx] ) || ((idx == -1) && hub_unplugged)) { + break; + } + + for (i =0 ; i < MAX_DEVICE_CONNECTED; i++) { + if (!deviceInUse[i]) { + USB_DBG_EVENT("new device connected: %p\r\n", &devices[i]); + devices[i].init(usb_msg->hub, usb_msg->port, usb_msg->lowSpeed); + deviceReset[i] = false; + deviceInited[i] = true; + break; + } + } + + if (i == MAX_DEVICE_CONNECTED) { + USB_ERR("Too many device connected!!\r\n"); + continue; + } + + if (!controlEndpointAllocated) { + control = newEndpoint(CONTROL_ENDPOINT, OUT, 0x08, 0x00); + addEndpoint(NULL, 0, (USBEndpoint*)control); + controlEndpointAllocated = true; + } + +#if MAX_HUB_NB + if (usb_msg->hub_parent) { + devices[i].setHubParent((USBHostHub *)(usb_msg->hub_parent)); + } +#endif + + for (j = 0; j < timeout_set_addr; j++) { + + resetDevice(&devices[i]); + + // set size of control endpoint + devices[i].setSizeControlEndpoint(8); + + devices[i].activeAddress(false); + + // get first 8 bit of device descriptor + // and check if we deal with a hub + USB_DBG("usb_thread read device descriptor on dev: %p\r\n", &devices[i]); + res = getDeviceDescriptor(&devices[i], buf, 8); + + if (res != USB_TYPE_OK) { + USB_ERR("usb_thread could not read dev descr"); + continue; + } + + // set size of control endpoint + devices[i].setSizeControlEndpoint(buf[7]); + + // second step: set an address to the device + res = setAddress(&devices[i], devices[i].getAddress()); + + if (res != USB_TYPE_OK) { + USB_ERR("SET ADDR FAILED"); + continue; + } + devices[i].activeAddress(true); + USB_DBG("Address of %p: %d", &devices[i], devices[i].getAddress()); + + // try to read again the device descriptor to check if the device + // answers to its new address + res = getDeviceDescriptor(&devices[i], buf, 8); + + if (res == USB_TYPE_OK) { + break; + } + + Thread::wait(100); + } + + USB_INFO("New device connected: %p [hub: %d - port: %d]", &devices[i], usb_msg->hub, usb_msg->port); + +#if MAX_HUB_NB + if (buf[4] == HUB_CLASS) { + for (k = 0; k < MAX_HUB_NB; k++) { + if (hub_in_use[k] == false) { + for (uint8_t j = 0; j < MAX_TRY_ENUMERATE_HUB; j++) { + if (hubs[k].connect(&devices[i])) { + devices[i].hub = &hubs[k]; + hub_in_use[k] = true; + break; + } + } + if (hub_in_use[k] == true) { + break; + } + } + } + + if (k == MAX_HUB_NB) { + USB_ERR("Too many hubs connected!!\r\n"); + too_many_hub = true; + } + } + + if (usb_msg->hub_parent) { + ((USBHostHub *)(usb_msg->hub_parent))->deviceConnected(&devices[i]); + } +#endif + + if ((i < MAX_DEVICE_CONNECTED) && !too_many_hub) { + deviceInUse[i] = true; + } + + } while(0); + + break; + + // a device has been disconnected + case DEVICE_DISCONNECTED_EVENT: + + do { + Lock lock(this); + + controlListState = disableList(CONTROL_ENDPOINT); + bulkListState = disableList(BULK_ENDPOINT); + interruptListState = disableList(INTERRUPT_ENDPOINT); + + idx = findDevice(usb_msg->hub, usb_msg->port, (USBHostHub *)(usb_msg->hub_parent)); + if (idx != -1) { + freeDevice((USBDeviceConnected*)&devices[idx]); + deviceInited[idx]=false; + } + + if (controlListState) { + enableList(CONTROL_ENDPOINT); + } + if (bulkListState) { + enableList(BULK_ENDPOINT); + } + if (interruptListState) { + enableList(INTERRUPT_ENDPOINT); + } + + } while(0); + + break; + + // a td has been processed + // call callback on the ed associated to the td + // we are not in ISR -> users can use printf in their callback method + case TD_PROCESSED_EVENT: + ep = (USBEndpoint *) ((HCTD *)usb_msg->td_addr)->ep; + if (usb_msg->td_state == USB_TYPE_IDLE) { + USB_DBG_EVENT("call callback on td %p [ep: %p state: %s - dev: %p - %s]", usb_msg->td_addr, ep, ep->getStateString(), ep->dev, ep->dev->getName(ep->getIntfNb())); + +#if DEBUG_TRANSFER + if (ep->getDir() == IN) { + buf_transfer = ep->getBufStart(); + printf("READ SUCCESS [%d bytes transferred - td: 0x%08X] on ep: [%p - addr: %02X]: ", ep->getLengthTransferred(), usb_msg->td_addr, ep, ep->getAddress()); + for (int i = 0; i < ep->getLengthTransferred(); i++) { + printf("%02X ", buf_transfer[i]); + } + printf("\r\n\r\n"); + } +#endif + ep->call(); + } else { + idx = findDevice(ep->dev); + if (idx != -1) { + if (deviceInUse[idx]) { + USB_WARN("td %p processed but not in idle state: %s [ep: %p - dev: %p - %s]", usb_msg->td_addr, ep->getStateString(), ep, ep->dev, ep->dev->getName(ep->getIntfNb())); + ep->setState(USB_TYPE_IDLE); + /* as error, on interrupt endpoint can be + * reported, call the call back registered , + * if device still in use, this call back + * shall ask again an interrupt request. + */ + ep->call(); + } + } + } + break; + } + + mail_usb_event.free(usb_msg); + } + } +} + +USBHost::USBHost() : usbThread(osPriorityNormal, USB_THREAD_STACK) +{ +#ifndef USBHOST_OTHER + headControlEndpoint = NULL; + headBulkEndpoint = NULL; + headInterruptEndpoint = NULL; + tailControlEndpoint = NULL; + tailBulkEndpoint = NULL; + tailInterruptEndpoint = NULL; +#endif + lenReportDescr = 0; + + controlEndpointAllocated = false; + + for (uint8_t i = 0; i < MAX_DEVICE_CONNECTED; i++) { + deviceInUse[i] = false; + devices[i].setAddress(i + 1); + deviceReset[i] = false; + deviceInited[i] = false; + for (uint8_t j = 0; j < MAX_INTF; j++) { + deviceAttachedDriver[i][j] = false; + } + } + +#if MAX_HUB_NB + for (uint8_t i = 0; i < MAX_HUB_NB; i++) { + hubs[i].setHost(this); + hub_in_use[i] = false; + } +#endif + + usbThread.start(this, &USBHost::usb_process); +} + +USBHost::Lock::Lock(USBHost* pHost) : m_pHost(pHost) +{ + m_pHost->usb_mutex.lock(); +} + +USBHost::Lock::~Lock() +{ + m_pHost->usb_mutex.unlock(); +} + +void USBHost::transferCompleted(volatile uint32_t addr) +{ + uint8_t state; + + if(addr == 0) { + return; + } + + volatile HCTD* tdList = NULL; + + //First we must reverse the list order and dequeue each TD + do { + volatile HCTD* td = (volatile HCTD*)addr; + addr = (uint32_t)td->nextTD; //Dequeue from physical list + td->nextTD = (hcTd*)tdList; //Enqueue into reversed list + tdList = td; + } while(addr); + + while(tdList != NULL) { + volatile HCTD* td = tdList; + tdList = (volatile HCTD*)td->nextTD; //Dequeue element now as it could be modified below + if (td->ep != NULL) { + USBEndpoint * ep = (USBEndpoint *)(td->ep); + +#ifdef USBHOST_OTHER + state = ((HCTD *)td)->state; + if (state == USB_TYPE_IDLE) { + ep->setLengthTransferred((uint32_t)td->currBufPtr - (uint32_t)ep->getBufStart()); + } + +#else + if (((HCTD *)td)->control >> 28) { + state = ((HCTD *)td)->control >> 28; + } else { + if (td->currBufPtr) { + ep->setLengthTransferred((uint32_t)td->currBufPtr - (uint32_t)ep->getBufStart()); + } + state = 16 /*USB_TYPE_IDLE*/; + } +#endif + if (state == USB_TYPE_IDLE) { + ep->setLengthTransferred((uint32_t)td->currBufPtr - (uint32_t)ep->getBufStart()); + } + + ep->unqueueTransfer(td); + + if (ep->getType() != CONTROL_ENDPOINT) { + // callback on the processed td will be called from the usb_thread (not in ISR) + message_t * usb_msg = mail_usb_event.alloc(); + usb_msg->event_id = TD_PROCESSED_EVENT; + usb_msg->td_addr = (void *)td; + usb_msg->td_state = state; + mail_usb_event.put(usb_msg); + } + ep->setState((USB_TYPE)state); + ep->ep_queue.put((uint8_t*)1); + } + } +} + +USBHost * USBHost::getHostInst() +{ + if (instHost == NULL) { + instHost = new USBHost(); + instHost->init(); + } + return instHost; +} + + +/* + * Called when a device has been connected + * Called in ISR!!!! (no printf) + */ +/* virtual */ void USBHost::deviceConnected(int hub, int port, bool lowSpeed, USBHostHub * hub_parent) +{ + // be sure that the new device connected is not already connected... + int idx = findDevice(hub, port, hub_parent); + if (idx != -1) { + if (deviceInited[idx]) { + return; + } + } + + message_t * usb_msg = mail_usb_event.alloc(); + usb_msg->event_id = DEVICE_CONNECTED_EVENT; + usb_msg->hub = hub; + usb_msg->port = port; + usb_msg->lowSpeed = lowSpeed; + usb_msg->hub_parent = hub_parent; + mail_usb_event.put(usb_msg); +} + +/* + * Called when a device has been disconnected + * Called in ISR!!!! (no printf) + */ +/* virtual */ void USBHost::deviceDisconnected(int hub, int port, USBHostHub * hub_parent, volatile uint32_t addr) +{ + // be sure that the device disconnected is connected... + int idx = findDevice(hub, port, hub_parent); + if (idx != -1) { + if (!deviceInUse[idx]) { + return; + } + } else { + return; + } + + message_t * usb_msg = mail_usb_event.alloc(); + usb_msg->event_id = DEVICE_DISCONNECTED_EVENT; + usb_msg->hub = hub; + usb_msg->port = port; + usb_msg->hub_parent = hub_parent; + mail_usb_event.put(usb_msg); +} + +void USBHost::freeDevice(USBDeviceConnected * dev) +{ + USBEndpoint * ep = NULL; + HCED * ed = NULL; + +#if MAX_HUB_NB + if (dev->getClass() == HUB_CLASS) { + if (dev->hub == NULL) { + USB_ERR("HUB NULL!!!!!\r\n"); + } else { + dev->hub->hubDisconnected(); + for (uint8_t i = 0; i < MAX_HUB_NB; i++) { + if (dev->hub == &hubs[i]) { + hub_in_use[i] = false; + break; + } + } + } + } + + // notify hub parent that this device has been disconnected + if (dev->getHubParent()) { + dev->getHubParent()->deviceDisconnected(dev); + } + +#endif + + int idx = findDevice(dev); + if (idx != -1) { + deviceInUse[idx] = false; + deviceReset[idx] = false; + + for (uint8_t j = 0; j < MAX_INTF; j++) { + deviceAttachedDriver[idx][j] = false; + if (dev->getInterface(j) != NULL) { + USB_DBG("FREE INTF %d on dev: %p, %p, nb_endpot: %d, %s", j, (void *)dev->getInterface(j), dev, dev->getInterface(j)->nb_endpoint, dev->getName(j)); + for (int i = 0; i < dev->getInterface(j)->nb_endpoint; i++) { + if ((ep = dev->getEndpoint(j, i)) != NULL) { +#ifndef USBHOST_OTHER + ed = (HCED *)ep->getHCED(); + ed->control |= (1 << 14); //sKip bit +#endif + unqueueEndpoint(ep); + + freeTD((volatile uint8_t*)ep->getTDList()[0]); + freeTD((volatile uint8_t*)ep->getTDList()[1]); + + freeED((uint8_t *)ep->getHCED()); + } + printList(BULK_ENDPOINT); + printList(INTERRUPT_ENDPOINT); + } + USB_INFO("Device disconnected [%p - %s - hub: %d - port: %d]", dev, dev->getName(j), dev->getHub(), dev->getPort()); + } + } + dev->disconnect(); + } +} + + +void USBHost::unqueueEndpoint(USBEndpoint * ep) +{ +#ifdef USBHOST_OTHER + ep->setState(USB_TYPE_FREE); +#else + USBEndpoint * prec = NULL; + USBEndpoint * current = NULL; + + for (int i = 0; i < 2; i++) { + current = (i == 0) ? (USBEndpoint*)headBulkEndpoint : (USBEndpoint*)headInterruptEndpoint; + prec = current; + while (current != NULL) { + if (current == ep) { + if (current->nextEndpoint() != NULL) { + prec->queueEndpoint(current->nextEndpoint()); + if (current == headBulkEndpoint) { + updateBulkHeadED((uint32_t)current->nextEndpoint()->getHCED()); + headBulkEndpoint = current->nextEndpoint(); + } else if (current == headInterruptEndpoint) { + updateInterruptHeadED((uint32_t)current->nextEndpoint()->getHCED()); + headInterruptEndpoint = current->nextEndpoint(); + } + } + // here we are dequeuing the queue of ed + // we need to update the tail pointer + else { + prec->queueEndpoint(NULL); + if (current == headBulkEndpoint) { + updateBulkHeadED(0); + headBulkEndpoint = current->nextEndpoint(); + } else if (current == headInterruptEndpoint) { + updateInterruptHeadED(0); + headInterruptEndpoint = current->nextEndpoint(); + } + + // modify tail + switch (current->getType()) { + case BULK_ENDPOINT: + tailBulkEndpoint = prec; + break; + case INTERRUPT_ENDPOINT: + tailInterruptEndpoint = prec; + break; + default: + break; + } + } + current->setState(USB_TYPE_FREE); + return; + } + prec = current; + current = current->nextEndpoint(); + } + } +#endif +} + + +USBDeviceConnected * USBHost::getDevice(uint8_t index) +{ + if ((index >= MAX_DEVICE_CONNECTED) || (!deviceInUse[index])) { + return NULL; + } + return (USBDeviceConnected*)&devices[index]; +} + +// create an USBEndpoint descriptor. the USBEndpoint is not linked +USBEndpoint * USBHost::newEndpoint(ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir, uint32_t size, uint8_t addr) +{ + int i = 0; + HCED * ed = (HCED *)getED(); + HCTD* td_list[2] = { (HCTD*)getTD(), (HCTD*)getTD() }; + + memset((void *)td_list[0], 0x00, sizeof(HCTD)); + memset((void *)td_list[1], 0x00, sizeof(HCTD)); + + // search a free USBEndpoint + for (i = 0; i < MAX_ENDPOINT; i++) { + if (endpoints[i].getState() == USB_TYPE_FREE) { + endpoints[i].init(ed, type, dir, size, addr, td_list); + USB_DBG("USBEndpoint created (%p): type: %d, dir: %d, size: %d, addr: %d, state: %s", &endpoints[i], type, dir, size, addr, endpoints[i].getStateString()); + return &endpoints[i]; + } + } + USB_ERR("could not allocate more endpoints!!!!"); + return NULL; +} + + +USB_TYPE USBHost::resetDevice(USBDeviceConnected * dev) +{ + int index = findDevice(dev); + if (index != -1) { + USB_DBG("Resetting hub %d, port %d\n", dev->getHub(), dev->getPort()); + Thread::wait(100); + if (dev->getHub() == 0) { + resetRootHub(); + } +#if MAX_HUB_NB + else { + dev->getHubParent()->portReset(dev->getPort()); + } +#endif + Thread::wait(100); + deviceReset[index] = true; + return USB_TYPE_OK; + } + + return USB_TYPE_ERROR; +} + +// link the USBEndpoint to the linked list and attach an USBEndpoint to a device +bool USBHost::addEndpoint(USBDeviceConnected * dev, uint8_t intf_nb, USBEndpoint * ep) +{ + + if (ep == NULL) { + return false; + } + +#ifndef USBHOST_OTHER + HCED * prevEd; + +#endif + // set device address in the USBEndpoint descriptor + if (dev == NULL) { + ep->setDeviceAddress(0); + } else { + ep->setDeviceAddress(dev->getAddress()); + } + + if ((dev != NULL) && dev->getSpeed()) { + ep->setSpeed(dev->getSpeed()); + } + + ep->setIntfNb(intf_nb); + +#ifndef USBHOST_OTHER + // queue the new USBEndpoint on the ED list + switch (ep->getType()) { + + case CONTROL_ENDPOINT: + prevEd = ( HCED*) controlHeadED(); + if (!prevEd) { + updateControlHeadED((uint32_t) ep->getHCED()); + USB_DBG_TRANSFER("First control USBEndpoint: %08X", (uint32_t) ep->getHCED()); + headControlEndpoint = ep; + tailControlEndpoint = ep; + return true; + } + tailControlEndpoint->queueEndpoint(ep); + tailControlEndpoint = ep; + return true; + + case BULK_ENDPOINT: + prevEd = ( HCED*) bulkHeadED(); + if (!prevEd) { + updateBulkHeadED((uint32_t) ep->getHCED()); + USB_DBG_TRANSFER("First bulk USBEndpoint: %08X\r\n", (uint32_t) ep->getHCED()); + headBulkEndpoint = ep; + tailBulkEndpoint = ep; + break; + } + USB_DBG_TRANSFER("Queue BULK Ed %p after %p\r\n",ep->getHCED(), prevEd); + tailBulkEndpoint->queueEndpoint(ep); + tailBulkEndpoint = ep; + break; + + case INTERRUPT_ENDPOINT: + prevEd = ( HCED*) interruptHeadED(); + if (!prevEd) { + updateInterruptHeadED((uint32_t) ep->getHCED()); + USB_DBG_TRANSFER("First interrupt USBEndpoint: %08X\r\n", (uint32_t) ep->getHCED()); + headInterruptEndpoint = ep; + tailInterruptEndpoint = ep; + break; + } + USB_DBG_TRANSFER("Queue INTERRUPT Ed %p after %p\r\n",ep->getHCED(), prevEd); + tailInterruptEndpoint->queueEndpoint(ep); + tailInterruptEndpoint = ep; + break; + default: + return false; + } + +#endif + ep->dev = dev; + dev->addEndpoint(intf_nb, ep); + + return true; +} + + +int USBHost::findDevice(USBDeviceConnected * dev) +{ + for (int i = 0; i < MAX_DEVICE_CONNECTED; i++) { + if (dev == &devices[i]) { + return i; + } + } + return -1; +} + +int USBHost::findDevice(uint8_t hub, uint8_t port, USBHostHub * hub_parent) +{ + for (int i = 0; i < MAX_DEVICE_CONNECTED; i++) { + if (devices[i].getHub() == hub && devices[i].getPort() == port) { + if (hub_parent != NULL) { + if (hub_parent == devices[i].getHubParent()) { + return i; + } + } else { + return i; + } + } + } + return -1; +} + +void USBHost::printList(ENDPOINT_TYPE type) +{ +#if DEBUG_EP_STATE && !defined(USBHOST_OTHER) + volatile HCED * hced; + switch(type) { + case CONTROL_ENDPOINT: + hced = (HCED *)controlHeadED(); + break; + case BULK_ENDPOINT: + hced = (HCED *)bulkHeadED(); + break; + case INTERRUPT_ENDPOINT: + hced = (HCED *)interruptHeadED(); + break; + } + volatile HCTD * hctd = NULL; + const char * type_str = (type == BULK_ENDPOINT) ? "BULK" : + ((type == INTERRUPT_ENDPOINT) ? "INTERRUPT" : + ((type == CONTROL_ENDPOINT) ? "CONTROL" : "ISOCHRONOUS")); + printf("State of %s:\r\n", type_str); + while (hced != NULL) { + uint8_t dir = ((hced->control & (3 << 11)) >> 11); + printf("hced: %p [ADDR: %d, DIR: %s, EP_NB: 0x%X]\r\n", hced, + hced->control & 0x7f, + (dir == 1) ? "OUT" : ((dir == 0) ? "FROM_TD":"IN"), + (hced->control & (0xf << 7)) >> 7); + hctd = (HCTD *)((uint32_t)(hced->headTD) & ~(0xf)); + while (hctd != hced->tailTD) { + printf("\thctd: %p [DIR: %s]\r\n", hctd, ((hctd->control & (3 << 19)) >> 19) == 1 ? "OUT" : "IN"); + hctd = hctd->nextTD; + } + printf("\thctd: %p\r\n", hctd); + hced = hced->nextED; + } + printf("\r\n\r\n"); +#endif +} + + +// add a transfer on the TD linked list +USB_TYPE USBHost::addTransfer(USBEndpoint * ed, uint8_t * buf, uint32_t len) +{ + USB_TYPE ret=USB_TYPE_PROCESSING; + td_mutex.lock(); + + // allocate a TD which will be freed in TDcompletion + volatile HCTD * td = ed->getNextTD(); + if (td == NULL) { + return USB_TYPE_ERROR; + } + +#ifndef USBHOST_OTHER + uint32_t token = (ed->isSetup() ? TD_SETUP : ( (ed->getDir() == IN) ? TD_IN : TD_OUT )); + + uint32_t td_toggle; + + if (ed->getType() == CONTROL_ENDPOINT) { + if (ed->isSetup()) { + td_toggle = TD_TOGGLE_0; + } else { + td_toggle = TD_TOGGLE_1; + } + } else { + td_toggle = 0; + } + + td->control = (TD_ROUNDING | token | TD_DELAY_INT(0) | td_toggle | TD_CC); + td->currBufPtr = buf; + td->bufEnd = (buf + (len - 1)); + + ENDPOINT_TYPE type = ed->getType(); + + disableList(type); + ed->queueTransfer(); + printList(type); + enableList(type); +#else + /* call method specific for endpoint */ + td->currBufPtr = buf; + td->size = len; + ret = ed->queueTransfer(); +#endif + + td_mutex.unlock(); + + return ret; +} + + + +USB_TYPE USBHost::getDeviceDescriptor(USBDeviceConnected * dev, uint8_t * buf, uint16_t max_len_buf, uint16_t * len_dev_descr) +{ + USB_TYPE t = controlRead( dev, + USB_DEVICE_TO_HOST | USB_RECIPIENT_DEVICE, + GET_DESCRIPTOR, + (DEVICE_DESCRIPTOR << 8) | (0), + 0, buf, MIN(DEVICE_DESCRIPTOR_LENGTH, max_len_buf)); + if (len_dev_descr) { + *len_dev_descr = MIN(DEVICE_DESCRIPTOR_LENGTH, max_len_buf); + } + + return t; +} + +USB_TYPE USBHost::getConfigurationDescriptor(USBDeviceConnected * dev, uint8_t * buf, uint16_t max_len_buf, uint16_t * len_conf_descr) +{ + USB_TYPE res; + uint16_t total_conf_descr_length = 0; + + // fourth step: get the beginning of the configuration descriptor to have the total length of the conf descr + res = controlRead( dev, + USB_DEVICE_TO_HOST | USB_RECIPIENT_DEVICE, + GET_DESCRIPTOR, + (CONFIGURATION_DESCRIPTOR << 8) | (0), + 0, buf, CONFIGURATION_DESCRIPTOR_LENGTH); + + if (res != USB_TYPE_OK) { + USB_ERR("GET CONF 1 DESCR FAILED"); + return res; + } + total_conf_descr_length = buf[2] | (buf[3] << 8); + total_conf_descr_length = MIN(max_len_buf, total_conf_descr_length); + + if (len_conf_descr) { + *len_conf_descr = total_conf_descr_length; + } + + USB_DBG("TOTAL_LENGTH: %d \t NUM_INTERF: %d", total_conf_descr_length, buf[4]); + + return controlRead( dev, + USB_DEVICE_TO_HOST | USB_RECIPIENT_DEVICE, + GET_DESCRIPTOR, + (CONFIGURATION_DESCRIPTOR << 8) | (0), + 0, buf, total_conf_descr_length); +} + + +USB_TYPE USBHost::setAddress(USBDeviceConnected * dev, uint8_t address) +{ + return controlWrite( dev, + USB_HOST_TO_DEVICE | USB_RECIPIENT_DEVICE, + SET_ADDRESS, + address, + 0, NULL, 0); + +} + +USB_TYPE USBHost::setConfiguration(USBDeviceConnected * dev, uint8_t conf) +{ + return controlWrite( dev, + USB_HOST_TO_DEVICE | USB_RECIPIENT_DEVICE, + SET_CONFIGURATION, + conf, + 0, NULL, 0); +} + +uint8_t USBHost::numberDriverAttached(USBDeviceConnected * dev) +{ + int index = findDevice(dev); + uint8_t cnt = 0; + if (index == -1) { + return 0; + } + for (uint8_t i = 0; i < MAX_INTF; i++) { + if (deviceAttachedDriver[index][i]) { + cnt++; + } + } + return cnt; +} + +// enumerate a device with the control USBEndpoint +USB_TYPE USBHost::enumerate(USBDeviceConnected * dev, IUSBEnumerator* pEnumerator) +{ + uint16_t total_conf_descr_length = 0; + USB_TYPE res; + + do { + Lock lock(this); + + // don't enumerate a device which all interfaces are registered to a specific driver + int index = findDevice(dev); + + if (index == -1) { + return USB_TYPE_ERROR; + } + + uint8_t nb_intf_attached = numberDriverAttached(dev); + USB_DBG("dev: %p nb_intf: %d", dev, dev->getNbIntf()); + USB_DBG("dev: %p nb_intf_attached: %d", dev, nb_intf_attached); + if ((nb_intf_attached != 0) && (dev->getNbIntf() == nb_intf_attached)) { + USB_DBG("Don't enumerate dev: %p because all intf are registered with a driver", dev); + return USB_TYPE_OK; + } + + USB_DBG("Enumerate dev: %p", dev); + + // third step: get the whole device descriptor to see vid, pid + res = getDeviceDescriptor(dev, data, DEVICE_DESCRIPTOR_LENGTH); + + if (res != USB_TYPE_OK) { + USB_DBG("GET DEV DESCR FAILED"); + return res; + } + + dev->setClass(data[4]); + dev->setSubClass(data[5]); + dev->setProtocol(data[6]); + dev->setVid(data[8] | (data[9] << 8)); + dev->setPid(data[10] | (data[11] << 8)); + USB_DBG("CLASS: %02X \t VID: %04X \t PID: %04X", data[4], data[8] | (data[9] << 8), data[10] | (data[11] << 8)); + + pEnumerator->setVidPid( data[8] | (data[9] << 8), data[10] | (data[11] << 8) ); + + res = getConfigurationDescriptor(dev, data, sizeof(data), &total_conf_descr_length); + if (res != USB_TYPE_OK) { + return res; + } + +#if (DEBUG > 3) + USB_DBG("CONFIGURATION DESCRIPTOR:\r\n"); + for (int i = 0; i < total_conf_descr_length; i++) { + printf("%02X ", data[i]); + } + printf("\r\n\r\n"); +#endif + + // Parse the configuration descriptor + parseConfDescr(dev, data, total_conf_descr_length, pEnumerator); + + // only set configuration if not enumerated before + if (!dev->isEnumerated()) { + + USB_DBG("Set configuration 1 on dev: %p", dev); + // sixth step: set configuration (only 1 supported) + res = setConfiguration(dev, 1); + + if (res != USB_TYPE_OK) { + USB_DBG("SET CONF FAILED"); + return res; + } + } + + dev->setEnumerated(); + + // Now the device is enumerated! + USB_DBG("dev %p is enumerated\r\n", dev); + + } while(0); + + // Some devices may require this delay + Thread::wait(100); + + return USB_TYPE_OK; +} +// this method fills the USBDeviceConnected object: class,.... . It also add endpoints found in the descriptor. +void USBHost::parseConfDescr(USBDeviceConnected * dev, uint8_t * conf_descr, uint32_t len, IUSBEnumerator* pEnumerator) +{ + uint32_t index = 0; + uint32_t len_desc = 0; + uint8_t id = 0; + int nb_endpoints_used = 0; + USBEndpoint * ep = NULL; + uint8_t intf_nb = 0; + bool parsing_intf = false; + uint8_t current_intf = 0; + + while (index < len) { + len_desc = conf_descr[index]; + id = conf_descr[index+1]; + switch (id) { + case CONFIGURATION_DESCRIPTOR: + USB_DBG("dev: %p has %d intf", dev, conf_descr[4]); + dev->setNbIntf(conf_descr[4]); + break; + case INTERFACE_DESCRIPTOR: + if(pEnumerator->parseInterface(conf_descr[index + 2], conf_descr[index + 5], conf_descr[index + 6], conf_descr[index + 7])) { + if (intf_nb++ <= MAX_INTF) { + current_intf = conf_descr[index + 2]; + dev->addInterface(current_intf, conf_descr[index + 5], conf_descr[index + 6], conf_descr[index + 7]); + nb_endpoints_used = 0; + USB_DBG("ADD INTF %d on device %p: class: %d, subclass: %d, proto: %d", current_intf, dev, conf_descr[index + 5],conf_descr[index + 6],conf_descr[index + 7]); + } else { + USB_DBG("Drop intf..."); + } + parsing_intf = true; + } else { + parsing_intf = false; + } + break; + case ENDPOINT_DESCRIPTOR: + if (parsing_intf && (intf_nb <= MAX_INTF) ) { + if (nb_endpoints_used < MAX_ENDPOINT_PER_INTERFACE) { + if( pEnumerator->useEndpoint(current_intf, (ENDPOINT_TYPE)(conf_descr[index + 3] & 0x03), (ENDPOINT_DIRECTION)((conf_descr[index + 2] >> 7) + 1)) ) { + // if the USBEndpoint is isochronous -> skip it (TODO: fix this) + if ((conf_descr[index + 3] & 0x03) != ISOCHRONOUS_ENDPOINT) { + ep = newEndpoint((ENDPOINT_TYPE)(conf_descr[index+3] & 0x03), + (ENDPOINT_DIRECTION)((conf_descr[index + 2] >> 7) + 1), + conf_descr[index + 4] | (conf_descr[index + 5] << 8), + conf_descr[index + 2] & 0x0f); + USB_DBG("ADD USBEndpoint %p, on interf %d on device %p", ep, current_intf, dev); + if (ep != NULL && dev != NULL) { + addEndpoint(dev, current_intf, ep); + } else { + USB_DBG("EP NULL"); + } + nb_endpoints_used++; + } else { + USB_DBG("ISO USBEndpoint NOT SUPPORTED"); + } + } + } + } + break; + case HID_DESCRIPTOR: + lenReportDescr = conf_descr[index + 7] | (conf_descr[index + 8] << 8); + break; + default: + break; + } + index += len_desc; + } +} + + +USB_TYPE USBHost::bulkWrite(USBDeviceConnected * dev, USBEndpoint * ep, uint8_t * buf, uint32_t len, bool blocking) +{ + return generalTransfer(dev, ep, buf, len, blocking, BULK_ENDPOINT, true); +} + +USB_TYPE USBHost::bulkRead(USBDeviceConnected * dev, USBEndpoint * ep, uint8_t * buf, uint32_t len, bool blocking) +{ + return generalTransfer(dev, ep, buf, len, blocking, BULK_ENDPOINT, false); +} + +USB_TYPE USBHost::interruptWrite(USBDeviceConnected * dev, USBEndpoint * ep, uint8_t * buf, uint32_t len, bool blocking) +{ + return generalTransfer(dev, ep, buf, len, blocking, INTERRUPT_ENDPOINT, true); +} + +USB_TYPE USBHost::interruptRead(USBDeviceConnected * dev, USBEndpoint * ep, uint8_t * buf, uint32_t len, bool blocking) +{ + return generalTransfer(dev, ep, buf, len, blocking, INTERRUPT_ENDPOINT, false); +} + +USB_TYPE USBHost::generalTransfer(USBDeviceConnected * dev, USBEndpoint * ep, uint8_t * buf, uint32_t len, bool blocking, ENDPOINT_TYPE type, bool write) +{ + +#if DEBUG_TRANSFER + const char * type_str = (type == BULK_ENDPOINT) ? "BULK" : ((type == INTERRUPT_ENDPOINT) ? "INTERRUPT" : "ISOCHRONOUS"); + USB_DBG_TRANSFER("----- %s %s [dev: %p - %s - hub: %d - port: %d - addr: %d - ep: %02X]------", type_str, (write) ? "WRITE" : "READ", dev, dev->getName(ep->getIntfNb()), dev->getHub(), dev->getPort(), dev->getAddress(), ep->getAddress()); +#endif + + Lock lock(this); + + USB_TYPE res; + ENDPOINT_DIRECTION dir = (write) ? OUT : IN; + + if (dev == NULL) { + USB_ERR("dev NULL"); + return USB_TYPE_ERROR; + } + + if (ep == NULL) { + USB_ERR("ep NULL"); + return USB_TYPE_ERROR; + } + + if (ep->getState() != USB_TYPE_IDLE) { + USB_WARN("[ep: %p - dev: %p - %s] NOT IDLE: %s", ep, ep->dev, ep->dev->getName(ep->getIntfNb()), ep->getStateString()); + return ep->getState(); + } + + if ((ep->getDir() != dir) || (ep->getType() != type)) { + USB_ERR("[ep: %p - dev: %p] wrong dir or bad USBEndpoint type", ep, ep->dev); + return USB_TYPE_ERROR; + } + + if (dev->getAddress() != ep->getDeviceAddress()) { + USB_ERR("[ep: %p - dev: %p] USBEndpoint addr and device addr don't match", ep, ep->dev); + return USB_TYPE_ERROR; + } + +#if DEBUG_TRANSFER + if (write) { + USB_DBG_TRANSFER("%s WRITE buffer", type_str); + for (int i = 0; i < ep->getLengthTransferred(); i++) { + printf("%02X ", buf[i]); + } + printf("\r\n\r\n"); + } +#endif + res = addTransfer(ep, buf, len); + + if ((blocking)&& (res == USB_TYPE_PROCESSING)) { +#ifdef USBHOST_OTHER + osEvent event = ep->ep_queue.get(TD_TIMEOUT); + if (event.status == osEventTimeout) { + /* control endpoint is confusing for merge on b */ + disableList(CONTROL_ENDPOINT); + ep->setState(USB_TYPE_ERROR); + ep->ep_queue.get(0); + ep->unqueueTransfer(ep->getProcessedTD()); + enableList(CONTROL_ENDPOINT); + } +#else + ep->ep_queue.get(); +#endif + res = ep->getState(); + + USB_DBG_TRANSFER("%s TRANSFER res: %s on ep: %p\r\n", type_str, ep->getStateString(), ep); + + if (res != USB_TYPE_IDLE) { + return res; + } + + return USB_TYPE_OK; + } + + return res; + +} + + +USB_TYPE USBHost::controlRead(USBDeviceConnected * dev, uint8_t requestType, uint8_t request, uint32_t value, uint32_t index, uint8_t * buf, uint32_t len) +{ + return controlTransfer(dev, requestType, request, value, index, buf, len, false); +} + +USB_TYPE USBHost::controlWrite(USBDeviceConnected * dev, uint8_t requestType, uint8_t request, uint32_t value, uint32_t index, uint8_t * buf, uint32_t len) +{ + return controlTransfer(dev, requestType, request, value, index, buf, len, true); +} + +USB_TYPE USBHost::controlTransfer(USBDeviceConnected * dev, uint8_t requestType, uint8_t request, uint32_t value, uint32_t index, uint8_t * buf, uint32_t len, bool write) +{ + Lock lock(this); + USB_DBG_TRANSFER("----- CONTROL %s [dev: %p - hub: %d - port: %d] ------", (write) ? "WRITE" : "READ", dev, dev->getHub(), dev->getPort()); + + int length_transfer = len; + USB_TYPE res; + uint32_t token; + + control->setSpeed(dev->getSpeed()); + control->setSize(dev->getSizeControlEndpoint()); + if (dev->isActiveAddress()) { + control->setDeviceAddress(dev->getAddress()); + } else { + control->setDeviceAddress(0); + } + + USB_DBG_TRANSFER("Control transfer on device: %d\r\n", control->getDeviceAddress()); + fillControlBuf(requestType, request, value, index, len); + +#if DEBUG_TRANSFER + USB_DBG_TRANSFER("SETUP PACKET: "); + for (int i = 0; i < 8; i++) { + printf("%01X ", setupPacket[i]); + } + printf("\r\n"); +#endif + + control->setNextToken(TD_SETUP); + res = addTransfer(control, (uint8_t*)setupPacket, 8); + + if (res == USB_TYPE_PROCESSING) +#ifdef USBHOST_OTHER + { + osEvent event = control->ep_queue.get(TD_TIMEOUT_CTRL); + if (event.status == osEventTimeout) { + disableList(CONTROL_ENDPOINT); + control->setState(USB_TYPE_ERROR); + control->ep_queue.get(0); + control->unqueueTransfer(control->getProcessedTD()); + enableList(CONTROL_ENDPOINT); + } + } +#else + control->ep_queue.get(); +#endif + res = control->getState(); + + USB_DBG_TRANSFER("CONTROL setup stage %s", control->getStateString()); + + if (res != USB_TYPE_IDLE) { + return res; + } + + if (length_transfer) { + token = (write) ? TD_OUT : TD_IN; + control->setNextToken(token); + res = addTransfer(control, (uint8_t *)buf, length_transfer); + + if (res == USB_TYPE_PROCESSING) +#ifdef USBHOST_OTHER + { + osEvent event = control->ep_queue.get(TD_TIMEOUT_CTRL); + if (event.status == osEventTimeout) { + disableList(CONTROL_ENDPOINT); + control->setState(USB_TYPE_ERROR); + control->ep_queue.get(0); + control->unqueueTransfer(control->getProcessedTD()); + enableList(CONTROL_ENDPOINT); + } + } +#else + control->ep_queue.get(); +#endif + res = control->getState(); + +#if DEBUG_TRANSFER + USB_DBG_TRANSFER("CONTROL %s stage %s", (write) ? "WRITE" : "READ", control->getStateString()); + if (write) { + USB_DBG_TRANSFER("CONTROL WRITE buffer"); + for (int i = 0; i < control->getLengthTransferred(); i++) { + printf("%02X ", buf[i]); + } + printf("\r\n\r\n"); + } else { + USB_DBG_TRANSFER("CONTROL READ SUCCESS [%d bytes transferred]", control->getLengthTransferred()); + for (int i = 0; i < control->getLengthTransferred(); i++) { + printf("%02X ", buf[i]); + } + printf("\r\n\r\n"); + } +#endif + + if (res != USB_TYPE_IDLE) { + return res; + } + } + + token = (write) ? TD_IN : TD_OUT; + control->setNextToken(token); + res = addTransfer(control, NULL, 0); + if (res == USB_TYPE_PROCESSING) +#ifdef USBHOST_OTHER + { + osEvent event = control->ep_queue.get(TD_TIMEOUT_CTRL); + if (event.status == osEventTimeout) { + disableList(CONTROL_ENDPOINT); + control->setState(USB_TYPE_ERROR); + control->ep_queue.get(0); + control->unqueueTransfer(control->getProcessedTD()); + enableList(CONTROL_ENDPOINT); + } + } +#else + control->ep_queue.get(); +#endif + res = control->getState(); + + USB_DBG_TRANSFER("CONTROL ack stage %s", control->getStateString()); + + if (res != USB_TYPE_IDLE) { + return res; + } + + return USB_TYPE_OK; +} + + +void USBHost::fillControlBuf(uint8_t requestType, uint8_t request, uint16_t value, uint16_t index, int len) +{ + setupPacket[0] = requestType; + setupPacket[1] = request; + setupPacket[2] = (uint8_t) value; + setupPacket[3] = (uint8_t) (value >> 8); + setupPacket[4] = (uint8_t) index; + setupPacket[5] = (uint8_t) (index >> 8); + setupPacket[6] = (uint8_t) len; + setupPacket[7] = (uint8_t) (len >> 8); +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost/USBHost.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,396 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBHOST_H +#define USBHOST_H +#ifdef TARGET_STM +#include "mbed.h" +#endif +#include "USBHALHost.h" +#include "USBDeviceConnected.h" +#include "IUSBEnumerator.h" +#include "USBHostConf.h" +#include "rtos.h" +#include "dbg.h" +#include "USBHostHub.h" + +/** +* USBHost class +* This class is a singleton. All drivers have a reference on the static USBHost instance +*/ +class USBHost : public USBHALHost { +public: + /** + * Static method to create or retrieve the single USBHost instance + */ + static USBHost * getHostInst(); + + /** + * Control read: setup stage, data stage and status stage + * + * @param dev the control read will be done for this device + * @param requestType request type + * @param request request + * @param value value + * @param index index + * @param buf pointer on a buffer where will be store the data received + * @param len length of the transfer + * + * @returns status of the control read + */ + USB_TYPE controlRead(USBDeviceConnected * dev, uint8_t requestType, uint8_t request, uint32_t value, uint32_t index, uint8_t * buf, uint32_t len); + + /** + * Control write: setup stage, data stage and status stage + * + * @param dev the control write will be done for this device + * @param requestType request type + * @param request request + * @param value value + * @param index index + * @param buf pointer on a buffer which will be written + * @param len length of the transfer + * + * @returns status of the control write + */ + USB_TYPE controlWrite(USBDeviceConnected * dev, uint8_t requestType, uint8_t request, uint32_t value, uint32_t index, uint8_t * buf, uint32_t len); + + /** + * Bulk read + * + * @param dev the bulk transfer will be done for this device + * @param ep USBEndpoint which will be used to read a packet + * @param buf pointer on a buffer where will be store the data received + * @param len length of the transfer + * @param blocking if true, the read is blocking (wait for completion) + * + * @returns status of the bulk read + */ + USB_TYPE bulkRead(USBDeviceConnected * dev, USBEndpoint * ep, uint8_t * buf, uint32_t len, bool blocking = true); + + /** + * Bulk write + * + * @param dev the bulk transfer will be done for this device + * @param ep USBEndpoint which will be used to write a packet + * @param buf pointer on a buffer which will be written + * @param len length of the transfer + * @param blocking if true, the write is blocking (wait for completion) + * + * @returns status of the bulk write + */ + USB_TYPE bulkWrite(USBDeviceConnected * dev, USBEndpoint * ep, uint8_t * buf, uint32_t len, bool blocking = true); + + /** + * Interrupt read + * + * @param dev the bulk transfer will be done for this device + * @param ep USBEndpoint which will be used to write a packet + * @param buf pointer on a buffer which will be written + * @param len length of the transfer + * @param blocking if true, the read is blocking (wait for completion) + * + * @returns status of the interrupt read + */ + USB_TYPE interruptRead(USBDeviceConnected * dev, USBEndpoint * ep, uint8_t * buf, uint32_t len, bool blocking = true); + + /** + * Interrupt write + * + * @param dev the bulk transfer will be done for this device + * @param ep USBEndpoint which will be used to write a packet + * @param buf pointer on a buffer which will be written + * @param len length of the transfer + * @param blocking if true, the write is blocking (wait for completion) + * + * @returns status of the interrupt write + */ + USB_TYPE interruptWrite(USBDeviceConnected * dev, USBEndpoint * ep, uint8_t * buf, uint32_t len, bool blocking = true); + + /** + * Enumerate a device. + * + * @param dev device which will be enumerated + * + * @returns status of the enumeration + */ + USB_TYPE enumerate(USBDeviceConnected * dev, IUSBEnumerator* pEnumerator); + + /** + * reset a specific device + * + * @param dev device which will be resetted + */ + USB_TYPE resetDevice(USBDeviceConnected * dev); + + /** + * Get a device + * + * @param index index of the device which will be returned + * + * @returns pointer on the "index" device + */ + USBDeviceConnected * getDevice(uint8_t index); + + /* + * If there is a HID device connected, the host stores the length of the report descriptor. + * This avoid to the driver to re-ask the configuration descriptor to request the report descriptor + * + * @returns length of the report descriptor + */ + inline uint16_t getLengthReportDescr() { + return lenReportDescr; + }; + + /** + * register a driver into the host associated with a callback function called when the device is disconnected + * + * @param dev device + * @param intf interface number + * @param tptr pointer to the object to call the member function on + * @param mptr pointer to the member function to be called + */ + template<typename T> + inline void registerDriver(USBDeviceConnected * dev, uint8_t intf, T* tptr, void (T::*mptr)(void)) { + int index = findDevice(dev); + if ((index != -1) && (mptr != NULL) && (tptr != NULL)) { + USB_DBG("register driver for dev: %p on intf: %d", dev, intf); + deviceAttachedDriver[index][intf] = true; + dev->onDisconnect(intf, tptr, mptr); + } + } + + /** + * register a driver into the host associated with a callback function called when the device is disconnected + * + * @param dev device + * @param intf interface number + * @param fn callback called when the specified device has been disconnected + */ + inline void registerDriver(USBDeviceConnected * dev, uint8_t intf, void (*fn)(void)) { + int index = findDevice(dev); + if ((index != -1) && (fn != NULL)) { + USB_DBG("register driver for dev: %p on intf: %d", dev, intf); + deviceAttachedDriver[index][intf] = true; + dev->onDisconnect(intf, fn); + } + } + + /** + * Instantiate to protect USB thread from accessing shared objects (USBConnectedDevices and Interfaces) + */ + class Lock + { + public: + Lock(USBHost* pHost); + ~Lock(); + private: + USBHost* m_pHost; + }; + + friend class USBHostHub; + +protected: + + /** + * Virtual method called when a transfer has been completed + * + * @param addr list of the TDs which have been completed + */ + virtual void transferCompleted(volatile uint32_t addr); + + /** + * Virtual method called when a device has been connected + * + * @param hub hub number of the device + * @param port port number of the device + * @param lowSpeed 1 if low speed, 0 otherwise + * @param hub_parent reference on the parent hub + */ + virtual void deviceConnected(int hub, int port, bool lowSpeed, USBHostHub * hub_parent = NULL); + + /** + * Virtuel method called when a device has been disconnected + * + * @param hub hub number of the device + * @param port port number of the device + * @param addr list of the TDs which have been completed to dequeue freed TDs + */ + virtual void deviceDisconnected(int hub, int port, USBHostHub * hub_parent, volatile uint32_t addr); + + +private: + // singleton class -> constructor is private + USBHost(); + static USBHost * instHost; + uint16_t lenReportDescr; + + // endpoints + void unqueueEndpoint(USBEndpoint * ep) ; + USBEndpoint endpoints[MAX_ENDPOINT]; + USBEndpoint* volatile control; + + USBEndpoint* volatile headControlEndpoint; + USBEndpoint* volatile headBulkEndpoint; + USBEndpoint* volatile headInterruptEndpoint; + + USBEndpoint* volatile tailControlEndpoint; + USBEndpoint* volatile tailBulkEndpoint; + USBEndpoint* volatile tailInterruptEndpoint; + + bool controlEndpointAllocated; + + // devices connected + USBDeviceConnected devices[MAX_DEVICE_CONNECTED]; + bool deviceInUse[MAX_DEVICE_CONNECTED]; + bool deviceAttachedDriver[MAX_DEVICE_CONNECTED][MAX_INTF]; + bool deviceReset[MAX_DEVICE_CONNECTED]; + bool deviceInited[MAX_DEVICE_CONNECTED]; + +#if MAX_HUB_NB + USBHostHub hubs[MAX_HUB_NB]; + bool hub_in_use[MAX_HUB_NB]; +#endif + + // to store a setup packet + uint8_t setupPacket[8]; + + typedef struct { + uint8_t event_id; + void * td_addr; + uint8_t hub; + uint8_t port; + uint8_t lowSpeed; + uint8_t td_state; + void * hub_parent; + } message_t; + + Thread usbThread; + void usb_process(); + Mail<message_t, 10> mail_usb_event; + Mutex usb_mutex; + Mutex td_mutex; + + // buffer for conf descriptor + uint8_t data[415]; + + /** + * Add a transfer on the TD linked list associated to an ED + * + * @param ed the transfer is associated to this ed + * @param buf pointer on a buffer where will be read/write data to send or receive + * @param len transfer length + * + * @return status of the transfer + */ + USB_TYPE addTransfer(USBEndpoint * ed, uint8_t * buf, uint32_t len) ; + + /** + * Link the USBEndpoint to the linked list and attach an USBEndpoint this USBEndpoint to a device + * + * @param dev pointer on a USBDeviceConnected object + * @param ep pointer on the USBEndpoint which will be added + * + * return true if successful + */ + bool addEndpoint(USBDeviceConnected * dev, uint8_t intf_nb, USBEndpoint * ep) ; + + /** + * Create an USBEndpoint descriptor. Warning: the USBEndpoint is not linked. + * + * @param type USBEndpoint type (CONTROL_ENDPOINT, BULK_ENDPOINT, INTERRUPT_ENDPOINT) + * @param dir USBEndpoint direction (no meaning for CONTROL_ENDPOINT) + * @param size USBEndpoint max packet size + * @param addr USBEndpoint address + * + * @returns pointer on the USBEndpoint created + */ + USBEndpoint * newEndpoint(ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir, uint32_t size, uint8_t addr) ; + + /** + * Request the device descriptor + * + * @param dev request the device descriptor on this device + * @param buf buffer to store the device descriptor + * @param max_len_buf maximum size of buf + * @param len_dev_descr pointer to store the length of the packet transferred + */ + USB_TYPE getDeviceDescriptor(USBDeviceConnected * dev, uint8_t * buf, uint16_t max_len_buf, uint16_t * len_dev_descr = NULL); + + /** + * Request the configuration descriptor + * + * @param dev request the configuration descriptor on this device + * @param buf buffer to store the configuration descriptor + * @param max_len_buf maximum size of buf + * @param len_conf_descr pointer to store the length of the packet transferred + */ + USB_TYPE getConfigurationDescriptor(USBDeviceConnected * dev, uint8_t * buf, uint16_t max_len_buf, uint16_t * len_conf_descr = NULL); + + /** + * Set the address of a specific device + * + * @param dev device to set the address + * @param address address + */ + USB_TYPE setAddress(USBDeviceConnected * dev, uint8_t address); + + /** + * Set the configuration of a device + * + * @param dev device on which the specified configuration will be activated + * @param conf configuration number to activate (usually 1) + */ + USB_TYPE setConfiguration(USBDeviceConnected * dev, uint8_t conf); + + /** + * Free a specific device + * + * @param dev device to be freed + */ + void freeDevice(USBDeviceConnected * dev); + + USB_TYPE controlTransfer( USBDeviceConnected * dev, + uint8_t requestType, + uint8_t request, + uint32_t value, + uint32_t index, + uint8_t * buf, + uint32_t len, + bool write); + + USB_TYPE generalTransfer( USBDeviceConnected * dev, + USBEndpoint * ep, + uint8_t * buf, + uint32_t len, + bool blocking, + ENDPOINT_TYPE type, + bool write) ; + + void fillControlBuf(uint8_t requestType, uint8_t request, uint16_t value, uint16_t index, int len) ; + void parseConfDescr(USBDeviceConnected * dev, uint8_t * conf_descr, uint32_t len, IUSBEnumerator* pEnumerator) ; + int findDevice(USBDeviceConnected * dev) ; + int findDevice(uint8_t hub, uint8_t port, USBHostHub * hub_parent = NULL) ; + uint8_t numberDriverAttached(USBDeviceConnected * dev); + + ///////////////////////// + /// FOR DEBUG + ///////////////////////// + void printList(ENDPOINT_TYPE type); + +}; + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost/USBHostConf.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,154 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBHOST_CONF_H +#define USBHOST_CONF_H +#if defined(TARGET_STM) +/* +* Maximum number of devices that can be connected +* to the usb host +*/ +/* hub + 2 devices */ +#define MAX_DEVICE_CONNECTED 5 + +/* +* Maximum of Hub connected to the usb host +*/ +#define MAX_HUB_NB 3 + +/* +* Maximum number of ports on a USB hub +*/ +#define MAX_HUB_PORT 4 + +/* +* Enable USBHostMSD +*/ +#define USBHOST_MSD 1 + +/* +* Enable USBHostKeyboard +*/ +#define USBHOST_KEYBOARD 1 + +/* +* Enable USBHostMouse +*/ +#define USBHOST_MOUSE 1 + +/* +* Enable USBHostSerial or USBHostMultiSerial (if set > 1) +*/ +#define USBHOST_SERIAL 1 + +/* +* Enable USB3Gmodule +*/ +#define USBHOST_3GMODULE 1 + +/* +* Enable USB MIDI +*/ +#define USBHOST_MIDI 1 + +/* +* Maximum number of interfaces of a usb device +*/ +#define MAX_INTF 2 + +/* +* Maximum number of endpoints on each interface +*/ +#define MAX_ENDPOINT_PER_INTERFACE 2 + +/* +* Maximum number of endpoint descriptors that can be allocated +*/ +#define MAX_ENDPOINT 11 /* USB FS 11 channel */ + +#else +/* +* Maximum number of devices that can be connected +* to the usb host +*/ +#define MAX_DEVICE_CONNECTED 5 + +/* +* Maximum of Hub connected to the usb host +*/ +#define MAX_HUB_NB 2 + +/* +* Maximum number of ports on a USB hub +*/ +#define MAX_HUB_PORT 4 + +/* +* Enable USBHostMSD +*/ +#define USBHOST_MSD 1 + +/* +* Enable USBHostKeyboard +*/ +#define USBHOST_KEYBOARD 1 + +/* +* Enable USBHostMouse +*/ +#define USBHOST_MOUSE 1 + +/* +* Enable USBHostSerial or USBHostMultiSerial (if set > 1) +*/ +#define USBHOST_SERIAL 1 + +/* +* Enable USB3Gmodule +*/ +#define USBHOST_3GMODULE 1 + +/* +* Enable USB MIDI +*/ +#define USBHOST_MIDI 1 + +/* +* Maximum number of interfaces of a usb device +*/ +#define MAX_INTF 4 + +/* +* Maximum number of endpoints on each interface +*/ +#define MAX_ENDPOINT_PER_INTERFACE 3 + +/* +* Maximum number of endpoint descriptors that can be allocated +*/ +#define MAX_ENDPOINT (MAX_DEVICE_CONNECTED * MAX_INTF * MAX_ENDPOINT_PER_INTERFACE) +#endif +/* +* Maximum number of transfer descriptors that can be allocated +*/ +#define MAX_TD (MAX_ENDPOINT*2) + +/* +* usb_thread stack size +*/ +#define USB_THREAD_STACK (256*4 + 2*256*4) + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost/USBHostTypes.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,262 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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_INC_H +#define USB_INC_H + +#include "mbed.h" +#include "mbed_toolchain.h" + +enum USB_TYPE { + USB_TYPE_OK = 0, + + // completion code + USB_TYPE_CRC_ERROR = 1, + USB_TYPE_BIT_STUFFING_ERROR = 2, + USB_TYPE_DATA_TOGGLE_MISMATCH_ERROR = 3, + USB_TYPE_STALL_ERROR = 4, + USB_TYPE_DEVICE_NOT_RESPONDING_ERROR = 5, + USB_TYPE_PID_CHECK_FAILURE_ERROR = 6, + USB_TYPE_UNEXPECTED_PID_ERROR = 7, + USB_TYPE_DATA_OVERRUN_ERROR = 8, + USB_TYPE_DATA_UNDERRUN_ERROR = 9, + USB_TYPE_RESERVED = 9, + USB_TYPE_RESERVED_ = 10, + USB_TYPE_BUFFER_OVERRUN_ERROR = 12, + USB_TYPE_BUFFER_UNDERRUN_ERROR = 13, + + // general usb state + USB_TYPE_DISCONNECTED = 14, + USB_TYPE_FREE = 15, + USB_TYPE_IDLE = 16, + USB_TYPE_PROCESSING = 17, + + USB_TYPE_ERROR = 18, +}; + + +enum ENDPOINT_DIRECTION { + OUT = 1, + IN +}; + +enum ENDPOINT_TYPE { + CONTROL_ENDPOINT = 0, + ISOCHRONOUS_ENDPOINT, + BULK_ENDPOINT, + INTERRUPT_ENDPOINT +}; + +#define AUDIO_CLASS 0x01 +#define CDC_CLASS 0x02 +#define HID_CLASS 0x03 +#define MSD_CLASS 0x08 +#define HUB_CLASS 0x09 +#define SERIAL_CLASS 0x0A + +#if !defined(USBHOST_OTHER) +// ------------------ HcControl Register --------------------- +#define OR_CONTROL_PLE 0x00000004 +#define OR_CONTROL_CLE 0x00000010 +#define OR_CONTROL_BLE 0x00000020 +#define OR_CONTROL_HCFS 0x000000C0 +#define OR_CONTROL_HC_RSET 0x00000000 +#define OR_CONTROL_HC_RES 0x00000040 +#define OR_CONTROL_HC_OPER 0x00000080 +#define OR_CONTROL_HC_SUSP 0x000000C0 +// ----------------- HcCommandStatus Register ----------------- +#define OR_CMD_STATUS_HCR 0x00000001 +#define OR_CMD_STATUS_CLF 0x00000002 +#define OR_CMD_STATUS_BLF 0x00000004 +// --------------- HcInterruptStatus Register ----------------- +#define OR_INTR_STATUS_WDH 0x00000002 +#define OR_INTR_STATUS_RHSC 0x00000040 +#define OR_INTR_STATUS_UE 0x00000010 +// --------------- HcInterruptEnable Register ----------------- +#define OR_INTR_ENABLE_WDH 0x00000002 +#define OR_INTR_ENABLE_RHSC 0x00000040 +#define OR_INTR_ENABLE_MIE 0x80000000 +// ---------------- HcRhDescriptorA Register ------------------ +#define OR_RH_STATUS_LPSC 0x00010000 +#define OR_RH_STATUS_DRWE 0x00008000 +// -------------- HcRhPortStatus[1:NDP] Register -------------- +#define OR_RH_PORT_CCS 0x00000001 +#define OR_RH_PORT_PRS 0x00000010 +#define OR_RH_PORT_CSC 0x00010000 +#define OR_RH_PORT_PRSC 0x00100000 +#define OR_RH_PORT_LSDA 0x00000200 +#define OR_RH_PORT_PESC 0x00020000 +#define OR_RH_PORT_OCIC 0x00080000 + +#define FI 0x2EDF // 12000 bits per frame (-1) +#define DEFAULT_FMINTERVAL ((((6 * (FI - 210)) / 7) << 16) | FI) + +#define ED_SKIP (uint32_t) (0x00001000) // Skip this ep in queue + +#define TD_ROUNDING (uint32_t) (0x00040000) // Buffer Rounding +#define TD_SETUP (uint32_t)(0) // Direction of Setup Packet +#define TD_IN (uint32_t)(0x00100000) // Direction In +#define TD_OUT (uint32_t)(0x00080000) // Direction Out +#define TD_DELAY_INT(x) (uint32_t)((x) << 21) // Delay Interrupt +#define TD_TOGGLE_0 (uint32_t)(0x02000000) // Toggle 0 +#define TD_TOGGLE_1 (uint32_t)(0x03000000) // Toggle 1 +#define TD_CC (uint32_t)(0xF0000000) // Completion Code + +#else + +#define TD_TIMEOUT_CTRL 100 +#define TD_TIMEOUT 2000 +#define TD_SETUP (uint32_t)(0) // Direction of Setup Packet +#define TD_IN (uint32_t)(0x00100000) // Direction In +#define TD_OUT (uint32_t)(0x00080000) // Direction Out + +#endif +#define DEVICE_DESCRIPTOR (1) +#define CONFIGURATION_DESCRIPTOR (2) +#define INTERFACE_DESCRIPTOR (4) +#define ENDPOINT_DESCRIPTOR (5) +#define HID_DESCRIPTOR (33) + +// ----------- Control RequestType Fields ----------- +#define USB_DEVICE_TO_HOST 0x80 +#define USB_HOST_TO_DEVICE 0x00 +#define USB_REQUEST_TYPE_CLASS 0x20 +#define USB_REQUEST_TYPE_STANDARD 0x00 +#define USB_RECIPIENT_DEVICE 0x00 +#define USB_RECIPIENT_INTERFACE 0x01 +#define USB_RECIPIENT_ENDPOINT 0x02 + +// -------------- USB Standard Requests -------------- +#define SET_ADDRESS 0x05 +#define GET_DESCRIPTOR 0x06 +#define SET_CONFIGURATION 0x09 +#define SET_INTERFACE 0x0b +#define CLEAR_FEATURE 0x01 + +// -------------- USB Descriptor Length -------------- +#define DEVICE_DESCRIPTOR_LENGTH 0x12 +#define CONFIGURATION_DESCRIPTOR_LENGTH 0x09 + +// ------------ HostController Transfer Descriptor ------------ +#if defined(USBHOST_OTHER) + +typedef struct hcTd { + __IO uint32_t state; + __IO uint8_t * currBufPtr; // Physical address of current buffer pointer + __IO hcTd * nextTD; // Physical pointer to next Transfer Descriptor + __IO uint32_t size; // size of buffer + void * ep; // ep address where a td is linked in + __IO uint32_t retry; + __IO uint32_t setup; +} PACKED HCTD; +// ----------- HostController EndPoint Descriptor ------------- +typedef struct hcEd { + uint8_t ch_num; + void *hhcd; +} PACKED HCED; +// ----------- Host Controller Communication Area ------------ +#define HCCA void + + +#else +// -------------OHCI register -------------------------------- +// ------------ HostController Transfer Descriptor ------------ +typedef struct hcTd { + __IO uint32_t control; // Transfer descriptor control + __IO uint8_t * currBufPtr; // Physical address of current buffer pointer + __IO hcTd * nextTD; // Physical pointer to next Transfer Descriptor + __IO uint8_t * bufEnd; // Physical address of end of buffer + void * ep; // ep address where a td is linked in + uint32_t dummy[3]; // padding +} PACKED HCTD; +// ----------- HostController EndPoint Descriptor ------------- +typedef struct hcEd { + __IO uint32_t control; // Endpoint descriptor control + __IO HCTD * tailTD; // Physical address of tail in Transfer descriptor list + __IO HCTD * headTD; // Physcial address of head in Transfer descriptor list + __IO hcEd * nextED; // Physical address of next Endpoint descriptor +} PACKED HCED; +// ----------- Host Controller Communication Area ------------ +typedef struct hcca { + __IO uint32_t IntTable[32]; // Interrupt Table + __IO uint32_t FrameNumber; // Frame Number + __IO uint32_t DoneHead; // Done Head + volatile uint8_t Reserved[116]; // Reserved for future use + volatile uint8_t Unknown[4]; // Unused +} PACKED HCCA; +#endif + +typedef struct { + uint8_t bLength; + uint8_t bDescriptorType; + uint16_t bcdUSB; + uint8_t bDeviceClass; + uint8_t bDeviceSubClass; + uint8_t bDeviceProtocol; + uint8_t bMaxPacketSize; + uint16_t idVendor; + uint16_t idProduct; + uint16_t bcdDevice; + uint8_t iManufacturer; + uint8_t iProduct; + uint8_t iSerialNumber; + uint8_t bNumConfigurations; +} PACKED DeviceDescriptor; + +typedef struct { + uint8_t bLength; + uint8_t bDescriptorType; + uint16_t wTotalLength; + uint8_t bNumInterfaces; + uint8_t bConfigurationValue; + uint8_t iConfiguration; + uint8_t bmAttributes; + uint8_t bMaxPower; +} PACKED ConfigurationDescriptor; + +typedef struct { + uint8_t bLength; + uint8_t bDescriptorType; + uint8_t bInterfaceNumber; + uint8_t bAlternateSetting; + uint8_t bNumEndpoints; + uint8_t bInterfaceClass; + uint8_t bInterfaceSubClass; + uint8_t bInterfaceProtocol; + uint8_t iInterface; +} InterfaceDescriptor; + +typedef struct { + uint8_t bLength; + uint8_t bDescriptorType; + uint8_t bEndpointAddress; + uint8_t bmAttributes; + uint16_t wMaxPacketSize; + uint8_t bInterval; +} EndpointDescriptor; + +typedef struct { + uint8_t bDescLength; + uint8_t bDescriptorType; + uint8_t bNbrPorts; + uint16_t wHubCharacteristics; + uint8_t bPwrOn2PwrGood; + uint8_t bHubContrCurrent; + uint8_t DeviceRemovable; + uint8_t PortPweCtrlMak; +} HubDescriptor; + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost/dbg.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,66 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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_DEBUG_H +#define USB_DEBUG_H + +//Debug is disabled by default +#define DEBUG 3 /*INFO,ERR,WARN*/ +#define DEBUG_TRANSFER 0 +#define DEBUG_EP_STATE 0 +#define DEBUG_EVENT 0 + +#if (DEBUG > 3) +#define USB_DBG(x, ...) std::printf("[USB_DBG: %s:%d]" x "\r\n", __FILE__, __LINE__, ##__VA_ARGS__); +#else +#define USB_DBG(x, ...) +#endif + +#if (DEBUG > 2) +#define USB_INFO(x, ...) std::printf("[USB_INFO: %s:%d]" x "\r\n", __FILE__, __LINE__, ##__VA_ARGS__); +#else +#define USB_INFO(x, ...) +#endif + +#if (DEBUG > 1) +#define USB_WARN(x, ...) std::printf("[USB_WARNING: %s:%d]" x "\r\n", __FILE__, __LINE__, ##__VA_ARGS__); +#else +#define USB_WARN(x, ...) +#endif + +#if (DEBUG > 0) +#define USB_ERR(x, ...) std::printf("[USB_ERR: %s:%d]" x "\r\n", __FILE__, __LINE__, ##__VA_ARGS__); +#else +#define USB_ERR(x, ...) +#endif + +#if (DEBUG_TRANSFER) +#define USB_DBG_TRANSFER(x, ...) std::printf("[USB_TRANSFER: %s:%d]" x "\r\n", __FILE__, __LINE__, ##__VA_ARGS__); +#else +#define USB_DBG_TRANSFER(x, ...) +#endif + +#if (DEBUG_EVENT) +#define USB_DBG_EVENT(x, ...) std::printf("[USB_EVENT: %s:%d]" x "\r\n", __FILE__, __LINE__, ##__VA_ARGS__); +#else +#define USB_DBG_EVENT(x, ...) +#endif + + +#endif + + +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost3GModule/IUSBHostSerial.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,95 @@ +/* IUSBHostSerial.h */ +/* Copyright (c) 2010-2012 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#ifndef IUSBHOSTSERIAL_H_ +#define IUSBHOSTSERIAL_H_ + +/** + * Generic interface to abstract 3G dongles' impl + */ + +#include "USBHostConf.h" + +#ifdef USBHOST_3GMODULE + +#include "IUSBHostSerialListener.h" + +// This is needed by some versions of GCC +#undef putc +#undef getc + +class IUSBHostSerial { +public: + + enum IrqType { + RxIrq, + TxIrq + }; + + /* + * Get a char from the dongle's serial interface + */ + virtual int getc() = 0; + + /* + * Put a char to the dongle's serial interface + */ + virtual int putc(int c) = 0; + + /* + * Read a packet from the dongle's serial interface, to be called after multiple getc() calls + */ + virtual int readPacket() = 0; + + /* + * Write a packet to the dongle's serial interface, to be called after multiple putc() calls + */ + virtual int writePacket() = 0; + + /** + * Check the number of bytes available. + * + * @returns the number of bytes available + */ + virtual int readable() = 0; + + /** + * Check the free space in output. + * + * @returns the number of bytes available + */ + virtual int writeable() = 0; + + /** + * Attach a handler to call when a packet is received / when a packet has been transmitted. + * + * @param pListener instance of the listener deriving from the IUSBHostSerialListener + */ + virtual void attach(IUSBHostSerialListener* pListener) = 0; + + /** + * Enable or disable readable/writeable callbacks + */ + virtual void setupIrq(bool en, IrqType irq = RxIrq) = 0; + +}; + +#endif /* USBHOST_3GMODULE */ + +#endif /* IUSBHOSTSERIAL_H_ */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost3GModule/IUSBHostSerialListener.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,37 @@ +/* IUSBHostSerialListener.h */ +/* Copyright (c) 2010-2012 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + + +#ifndef IUSBHOSTSERIALLISTENER_H_ +#define IUSBHOSTSERIALLISTENER_H_ + +#include "USBHostConf.h" + +#ifdef USBHOST_3GMODULE + +class IUSBHostSerialListener +{ +public: + virtual void readable() = 0; //Called when new data is available + virtual void writeable() = 0; //Called when new space is available +}; + +#endif /* USBHOST_3GMODULE */ + +#endif /* IUSBHOSTSERIALLISTENER_H_ */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost3GModule/WANDongle.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,235 @@ +/* Copyright (c) 2010-2012 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#include "USBHostConf.h" + +#ifdef USBHOST_3GMODULE + +#include "dbg.h" +#include <stdint.h> +#include "rtos.h" + +#include "WANDongle.h" +#include "WANDongleInitializer.h" + +WANDongle::WANDongle() : m_pInitializer(NULL), m_serialCount(0), m_totalInitializers(0) +{ + host = USBHost::getHostInst(); + init(); +} + + +bool WANDongle::connected() { + return dev_connected; +} + +bool WANDongle::tryConnect() +{ + //FIXME should run on USB thread + + USB_DBG("Trying to connect device"); + + if (dev_connected) { + USB_DBG("Device is already connected!"); + return true; + } + + m_pInitializer = NULL; + + //Protect from concurrent access from USB thread + USBHost::Lock lock(host); + + for (int i = 0; i < MAX_DEVICE_CONNECTED; i++) + { + if ((dev = host->getDevice(i)) != NULL) + { + m_pInitializer = NULL; //Will be set in setVidPid callback + + USB_DBG("Enumerate"); + int ret = host->enumerate(dev, this); + if(ret) + { + return false; + } + + USB_DBG("Device has VID:%04x PID:%04x", dev->getVid(), dev->getPid()); + + if(m_pInitializer) //If an initializer has been found + { + USB_DBG("m_pInitializer=%p", m_pInitializer); + USB_DBG("m_pInitializer->getSerialVid()=%04x", m_pInitializer->getSerialVid()); + USB_DBG("m_pInitializer->getSerialPid()=%04x", m_pInitializer->getSerialPid()); + if ((dev->getVid() == m_pInitializer->getSerialVid()) && (dev->getPid() == m_pInitializer->getSerialPid())) + { + USB_DBG("The dongle is in virtual serial mode"); + host->registerDriver(dev, 0, this, &WANDongle::init); + m_serialCount = m_pInitializer->getSerialPortCount(); + if( m_serialCount > WANDONGLE_MAX_SERIAL_PORTS ) + { + m_serialCount = WANDONGLE_MAX_SERIAL_PORTS; + } + for(int j = 0; j < m_serialCount; j++) + { + USB_DBG("Connecting serial port #%d", j+1); + USB_DBG("Ep %p", m_pInitializer->getEp(dev, j, false)); + USB_DBG("Ep %p", m_pInitializer->getEp(dev, j, true)); + m_serial[j].connect( dev, m_pInitializer->getEp(dev, j, false), m_pInitializer->getEp(dev, j, true) ); + } + + USB_DBG("Device connected"); + + dev_connected = true; + + + return true; + } + else if ((dev->getVid() == m_pInitializer->getMSDVid()) && (dev->getPid() == m_pInitializer->getMSDPid())) + { + USB_DBG("Vodafone K3370 dongle detected in MSD mode"); + //Try to switch + if( m_pInitializer->switchMode(dev) ) + { + USB_DBG("Switched OK"); + return false; //Will be connected on a next iteration + } + else + { + USB_ERR("Could not switch mode"); + return false; + } + } + } //if() + } //if() + } //for() + return false; +} + +bool WANDongle::disconnect() +{ + dev_connected = false; + for(int i = 0; i < WANDONGLE_MAX_SERIAL_PORTS; i++) + { + m_serial[i].disconnect(); + } + return true; +} + +int WANDongle::getDongleType() +{ + if( m_pInitializer != NULL ) + { + return m_pInitializer->getType(); + } + else + { + return WAN_DONGLE_TYPE_UNKNOWN; + } +} + +IUSBHostSerial& WANDongle::getSerial(int index) +{ + return m_serial[index]; +} + +int WANDongle::getSerialCount() +{ + return m_serialCount; +} + +//Private methods +void WANDongle::init() +{ + m_pInitializer = NULL; + dev_connected = false; + for(int i = 0; i < WANDONGLE_MAX_SERIAL_PORTS; i++) + { + m_serial[i].init(host); + } +} + + +/*virtual*/ void WANDongle::setVidPid(uint16_t vid, uint16_t pid) +{ + WANDongleInitializer* initializer; + + for(int i = 0; i < m_totalInitializers; i++) + { + initializer = m_Initializers[i]; + USB_DBG("initializer=%p", initializer); + USB_DBG("initializer->getSerialVid()=%04x", initializer->getSerialVid()); + USB_DBG("initializer->getSerialPid()=%04x", initializer->getSerialPid()); + if ((dev->getVid() == initializer->getSerialVid()) && (dev->getPid() == initializer->getSerialPid())) + { + USB_DBG("The dongle is in virtual serial mode"); + m_pInitializer = initializer; + break; + } + else if ((dev->getVid() == initializer->getMSDVid()) && (dev->getPid() == initializer->getMSDPid())) + { + USB_DBG("Dongle detected in MSD mode"); + m_pInitializer = initializer; + break; + } + initializer++; + } //for + if(m_pInitializer) + { + m_pInitializer->setVidPid(vid, pid); + } +} + +/*virtual*/ bool WANDongle::parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) //Must return true if the interface should be parsed +{ + if(m_pInitializer) + { + return m_pInitializer->parseInterface(intf_nb, intf_class, intf_subclass, intf_protocol); + } + else + { + return false; + } +} + +/*virtual*/ bool WANDongle::useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir) //Must return true if the endpoint will be used +{ + if(m_pInitializer) + { + return m_pInitializer->useEndpoint(intf_nb, type, dir); + } + else + { + return false; + } +} + + +bool WANDongle::addInitializer(WANDongleInitializer* pInitializer) +{ + if (m_totalInitializers >= WANDONGLE_MAX_INITIALIZERS) + return false; + m_Initializers[m_totalInitializers++] = pInitializer; + return true; +} + +WANDongle::~WANDongle() +{ + for(int i = 0; i < m_totalInitializers; i++) + delete m_Initializers[i]; +} + +#endif /* USBHOST_3GMODULE */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost3GModule/WANDongle.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,108 @@ +/* Copyright (c) 2010-2012 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#ifndef WANDONGLE_H +#define WANDONGLE_H + +#include "USBHostConf.h" + +#ifdef USBHOST_3GMODULE + +#include "USBHost.h" +#include "IUSBHostSerial.h" + +#include "rtos.h" + +#include "WANDongleSerialPort.h" +#include "WANDongleInitializer.h" +#include "IUSBEnumerator.h" + +#define WANDONGLE_MAX_OUTEP_SIZE 64 +#define WANDONGLE_MAX_INEP_SIZE 64 + +/** A class to use a WAN (3G/LTE) access dongle + * + */ +class WANDongle : public IUSBEnumerator { +public: + /* + * Constructor + * + * @param rootdir mount name + */ + WANDongle(); + + /* + * Destructor + */ + virtual ~WANDongle(); + + /* + * Check if a serial port device is connected + * + * @return true if a serial device is connected + */ + bool connected(); + + /* + * Try to connect device + * + * * @return true if connection was successful + */ + bool tryConnect(); + + /* + * Disconnect device + * + * * @return true if disconnection was successful + */ + bool disconnect(); + + int getDongleType(); + + IUSBHostSerial& getSerial(int index); + int getSerialCount(); + bool addInitializer(WANDongleInitializer* pInitializer); + + //From IUSBEnumerator + + virtual void setVidPid(uint16_t vid, uint16_t pid); + + virtual bool parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol); //Must return true if the interface should be parsed + + virtual bool useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir); //Must return true if the endpoint will be used + +protected: + USBHost * host; + USBDeviceConnected * dev; + bool dev_connected; + + WANDongleInitializer* m_pInitializer; + + void init(); + + WANDongleSerialPort m_serial[WANDONGLE_MAX_SERIAL_PORTS]; + int m_serialCount; + + int m_totalInitializers; + WANDongleInitializer* m_Initializers[WANDONGLE_MAX_INITIALIZERS]; +}; + +#endif /* USBHOST_3GMODULE */ + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost3GModule/WANDongleInitializer.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,73 @@ +/* Copyright (c) 2010-2012 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#ifndef WANDONGLEINITIALIZER_H +#define WANDONGLEINITIALIZER_H + +#include "USBHostConf.h" + +#ifdef USBHOST_3GMODULE + +#include <stdint.h> + +#include "USBHost.h" +#include "IUSBEnumerator.h" + +// [TODO] move these declarations to a proper place +#define WANDONGLE_MAX_SERIAL_PORTS 2 +#define WANDONGLE_MAX_INITIALIZERS 6 + +#define WAN_DONGLE_TYPE_UNKNOWN (-1) + +class WANDongleInitializer : public IUSBEnumerator +{ +protected: + WANDongleInitializer(USBHost* pHost) { m_pHost = pHost; } + USBHost* m_pHost; + uint8_t m_serialIntfMap[WANDONGLE_MAX_SERIAL_PORTS]; + +public: + virtual ~WANDongleInitializer() {} + virtual uint16_t getMSDVid() = 0; + virtual uint16_t getMSDPid() = 0; + + virtual uint16_t getSerialVid() = 0; + virtual uint16_t getSerialPid() = 0; + + virtual bool switchMode(USBDeviceConnected* pDev) = 0; + + virtual USBEndpoint* getEp(USBDeviceConnected* pDev, int serialPortNumber, bool tx) { + return pDev->getEndpoint(m_serialIntfMap[serialPortNumber], BULK_ENDPOINT, tx ? OUT : IN, 0); + } + + virtual int getSerialPortCount() = 0; + + virtual void setVidPid(uint16_t vid, uint16_t pid) = 0; + + virtual bool parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) = 0; //Must return true if the interface should be parsed + + virtual bool useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir) = 0; //Must return true if the endpoint will be used + + virtual int getType() = 0; + + virtual uint8_t getSerialIntf(int index) { return m_serialIntfMap[index]; } +}; + +#endif /* USBHOST_3GMODULE */ + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost3GModule/WANDongleSerialPort.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,340 @@ +/* Copyright (c) 2010-2012 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#include "USBHostConf.h" + +#ifdef USBHOST_3GMODULE + +#define __DEBUG__ 0 +#ifndef __MODULE__ +#define __MODULE__ "WANDongleSerialPort.cpp" +#endif + +#include "dbg.h" +#include <stdint.h> +#include "rtos.h" + +#include "WANDongleSerialPort.h" + +WANDongleSerialPort::WANDongleSerialPort() : cb_tx_en(false), cb_rx_en(false), listener(NULL) +{ + reset(); +} + +void WANDongleSerialPort::init(USBHost* pHost) +{ + host = pHost; +} + +void WANDongleSerialPort::reset() +{ + tx_mtx.lock(); + rx_mtx.lock(); + + bulk_in = NULL; + bulk_out = NULL; + + buf_out_len = 0; + max_out_size = 0; + lock_tx = false; + cb_tx_pending = false; + + buf_in_len = 0; + buf_in_read_pos = 0; + lock_rx = false; + cb_rx_pending = false; + + tx_mtx.unlock(); + rx_mtx.unlock(); +} + +int WANDongleSerialPort::readPacket() +{ + USB_DBG("Read packet on %p", this); + rx_mtx.lock(); + if(lock_rx) + { + USB_ERR("Fail"); + rx_mtx.unlock(); + return -1; + } + + if( bulk_in == NULL ) + { + USB_WARN("Port is disconnected"); + rx_mtx.unlock(); + return -1; + } + + lock_rx = true; //Receiving + rx_mtx.unlock(); +// USB_DBG("readPacket"); + //lock_rx.lock(); + USB_TYPE res = host->bulkRead(dev, (USBEndpoint *)bulk_in, buf_in, ((USBEndpoint *)bulk_in)->getSize(), false); //Queue transfer + if(res != USB_TYPE_PROCESSING) + { + //lock_rx.unlock(); + USB_ERR("host->bulkRead() returned %d", res); + Thread::wait(100); + return -1; + } + return 0; +} + +int WANDongleSerialPort::writePacket() +{ + tx_mtx.lock(); + if(lock_tx) + { + USB_ERR("Fail"); + tx_mtx.unlock(); + return -1; + } + + if( bulk_out == NULL ) + { + USB_WARN("Port is disconnected"); + tx_mtx.unlock(); + return -1; + } + + lock_tx = true; //Transmitting + tx_mtx.unlock(); +// USB_DBG("writePacket"); + + //lock_tx.lock(); + USB_TYPE res = host->bulkWrite(dev, (USBEndpoint *)bulk_out, buf_out, buf_out_len, false); //Queue transfer + if(res != USB_TYPE_PROCESSING) + { + //lock_tx.unlock(); + USB_ERR("host->bulkWrite() returned %d", res); + Thread::wait(100); + return -1; + } + return 0; +} + +int WANDongleSerialPort::putc(int c) +{ + tx_mtx.lock(); + if(!lock_tx) + { + if(buf_out_len < max_out_size) + { + buf_out[buf_out_len] = (uint8_t)c; + buf_out_len++; + } + } + else + { + USB_ERR("CAN'T WRITE!"); + } + tx_mtx.unlock(); + return c; +} + +int WANDongleSerialPort::getc() +{ + rx_mtx.lock(); + int c = 0; + if(!lock_rx) + { + if(buf_in_read_pos < buf_in_len) + { + c = (int)buf_in[buf_in_read_pos]; + buf_in_read_pos++; + } + } + else + { + USB_ERR("CAN'T READ!"); + } + rx_mtx.unlock(); + return c; +} + +int WANDongleSerialPort::readable() +{ + rx_mtx.lock(); + if (lock_rx) + { + rx_mtx.unlock(); + return 0; + } + + /* if( !lock_rx.trylock() ) + { + return 0; + }*/ + int res = buf_in_len - buf_in_read_pos; + //lock_rx.unlock(); + rx_mtx.unlock(); + return res; +} + +int WANDongleSerialPort::writeable() +{ + tx_mtx.lock(); + if (lock_tx) + { + tx_mtx.unlock(); + return 0; + } + + /*if( !lock_tx.trylock() ) + { + return 0; + }*/ + int res = max_out_size - buf_out_len; + tx_mtx.unlock(); + //lock_tx.unlock(); + return res; +} + +void WANDongleSerialPort::attach(IUSBHostSerialListener* pListener) +{ + if(pListener == NULL) + { + setupIrq(false, RxIrq); + setupIrq(false, TxIrq); + } + listener = pListener; + if(pListener != NULL) + { + setupIrq(true, RxIrq); + setupIrq(true, TxIrq); + } +} + +void WANDongleSerialPort::setupIrq(bool en, IrqType irq /*= RxIrq*/) +{ + switch(irq) + { + case RxIrq: + rx_mtx.lock(); + cb_rx_en = en; + if(en && cb_rx_pending) + { + cb_rx_pending = false; + rx_mtx.unlock(); + listener->readable(); //Process the interrupt that was raised + } + else + { + rx_mtx.unlock(); + } + break; + case TxIrq: + tx_mtx.lock(); + cb_tx_en = en; + if(en && cb_tx_pending) + { + cb_tx_pending = false; + tx_mtx.unlock(); + listener->writeable(); //Process the interrupt that was raised + } + else + { + tx_mtx.unlock(); + } + break; + } +} + + +void WANDongleSerialPort::connect( USBDeviceConnected* pDev, USBEndpoint* pInEp, USBEndpoint* pOutEp ) +{ + dev = pDev; + bulk_in = pInEp; + bulk_out = pOutEp; + max_out_size = bulk_out->getSize(); + if( max_out_size > WANDONGLE_MAX_OUTEP_SIZE ) + { + max_out_size = WANDONGLE_MAX_OUTEP_SIZE; + } + bulk_in->attach(this, &WANDongleSerialPort::rxHandler); + bulk_out->attach(this, &WANDongleSerialPort::txHandler); + readPacket(); //Start receiving data +} + +void WANDongleSerialPort::disconnect( ) +{ + reset(); +} + +//Private methods + + +void WANDongleSerialPort::rxHandler() +{ + if (((USBEndpoint *) bulk_in)->getState() == USB_TYPE_IDLE) //Success + { + buf_in_read_pos = 0; + buf_in_len = ((USBEndpoint *) bulk_in)->getLengthTransferred(); //Update length + //lock_rx.unlock(); + rx_mtx.lock(); + lock_rx = false; //Transmission complete + if(cb_rx_en) + { + rx_mtx.unlock(); + listener->readable(); //Call handler from the IRQ context + //readPacket() should be called by the handler subsequently once the buffer has been emptied + } + else + { + cb_rx_pending = true; //Queue the callback + rx_mtx.unlock(); + } + + } + else //Error, try reading again + { + //lock_rx.unlock(); + USB_DBG("Trying again"); + readPacket(); + } +} + +void WANDongleSerialPort::txHandler() +{ + if (((USBEndpoint *) bulk_out)->getState() == USB_TYPE_IDLE) //Success + { + tx_mtx.lock(); + buf_out_len = 0; //Reset length + lock_tx = false; //Transmission complete + //lock_tx.unlock(); + if(cb_tx_en) + { + tx_mtx.unlock(); + listener->writeable(); //Call handler from the IRQ context + //writePacket() should be called by the handler subsequently once the buffer has been filled + } + else + { + cb_tx_pending = true; //Queue the callback + tx_mtx.unlock(); + } + } + else //Error, try reading again + { + //lock_tx.unlock(); + writePacket(); + } +} + +#endif /* USBHOST_3GMODULE */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHost3GModule/WANDongleSerialPort.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,133 @@ +/* Copyright (c) 2010-2012 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#ifndef WANDONGLESERIALPORT_H +#define WANDONGLESERIALPORT_H + +#include "USBHostConf.h" + +#ifdef USBHOST_3GMODULE + +#include "USBHost.h" +#include "IUSBHostSerial.h" + +#include "rtos.h" + + +#define WANDONGLE_MAX_OUTEP_SIZE 64 +#define WANDONGLE_MAX_INEP_SIZE 64 + +/** A class to use a WAN (3G/LTE) access dongle + * + */ +class WANDongleSerialPort : public IUSBHostSerial { +public: + /* + * Constructor + * + */ + WANDongleSerialPort(); + + void init( USBHost* pHost ); + + void connect( USBDeviceConnected* pDev, USBEndpoint* pInEp, USBEndpoint* pOutEp ); + + void disconnect( ); + + /* + * Get a char from the dongle's serial interface + */ + virtual int getc(); + + /* + * Put a char to the dongle's serial interface + */ + virtual int putc(int c); + + /* + * Read a packet from the dongle's serial interface, to be called after multiple getc() calls + */ + virtual int readPacket(); + + /* + * Write a packet to the dongle's serial interface, to be called after multiple putc() calls + */ + virtual int writePacket(); + + /** + * Check the number of bytes available. + * + * @returns the number of bytes available + */ + virtual int readable(); + + /** + * Check the free space in output. + * + * @returns the number of bytes available + */ + virtual int writeable(); + + /** + * Attach a handler to call when a packet is received / when a packet has been transmitted. + * + * @param pListener instance of the listener deriving from the IUSBHostSerialListener + */ + virtual void attach(IUSBHostSerialListener* pListener); + + /** + * Enable or disable readable/writeable callbacks + */ + virtual void setupIrq(bool en, IrqType irq = RxIrq); + + +protected: + USBEndpoint * bulk_in; + USBEndpoint * bulk_out; + USBHost * host; + USBDeviceConnected * dev; + + uint8_t buf_out[WANDONGLE_MAX_OUTEP_SIZE]; + volatile uint32_t buf_out_len; + uint32_t max_out_size; + volatile bool lock_tx; + volatile bool cb_tx_en; + volatile bool cb_tx_pending; + Mutex tx_mtx; + + uint8_t buf_in[WANDONGLE_MAX_INEP_SIZE]; + volatile uint32_t buf_in_len; + volatile uint32_t buf_in_read_pos; + volatile bool lock_rx; + volatile bool cb_rx_en; + volatile bool cb_rx_pending; + Mutex rx_mtx; + + IUSBHostSerialListener* listener; + + void reset(); + + void rxHandler(); + void txHandler(); + +}; + +#endif /* USBHOST_3GMODULE */ + +#endif +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostHID/USBHostKeyboard.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,207 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 "USBHostKeyboard.h" + +#if USBHOST_KEYBOARD + +static uint8_t keymap[4][0x39] = { + { + 0, 0, 0, 0, 'a', 'b' /*0x05*/, + 'c', 'd', 'e', 'f', 'g' /*0x0a*/, + 'h', 'i', 'j', 'k', 'l'/*0x0f*/, + 'm', 'n', 'o', 'p', 'q'/*0x14*/, + 'r', 's', 't', 'u', 'v'/*0x19*/, + 'w', 'x', 'y', 'z', '1'/*0x1E*/, + '2', '3', '4', '5', '6'/*0x23*/, + '7', '8', '9', '0', 0x0A /*enter*/, /*0x28*/ + 0x1B /*escape*/, 0x08 /*backspace*/, 0x09/*tab*/, 0x20/*space*/, '-', /*0x2d*/ + '=', '[', ']', '\\', '#', /*0x32*/ + ';', '\'', 0, ',', '.', /*0x37*/ + '/' + }, + + /* CTRL MODIFIER */ + { + 0, 0, 0, 0, 0, 0 /*0x05*/, + 0, 0, 0, 0, 0 /*0x0a*/, + 0, 0, 0, 0, 0/*0x0f*/, + 0, 0, 0, 0, 0/*0x14*/, + 0, 0, 0, 0, 0/*0x19*/, + 0, 0, 0, 0, 0/*0x1E*/, + 0, 0, 0, 0, 0/*0x23*/, + 0, 0, 0, 0, 0 /*enter*/, /*0x28*/ + 0, 0, 0, 0, 0, /*0x2d*/ + 0, 0, 0, 0, 0, /*0x32*/ + 0, 0, 0, 0, 0, /*0x37*/ + 0 + }, + + /* SHIFT MODIFIER */ + { + 0, 0, 0, 0, 'A', 'B' /*0x05*/, + 'C', 'D', 'E', 'F', 'G' /*0x0a*/, + 'H', 'I', 'J', 'K', 'L'/*0x0f*/, + 'M', 'N', 'O', 'P', 'Q'/*0x14*/, + 'R', 'S', 'T', 'U', 'V'/*0x19*/, + 'W', 'X', 'Y', 'Z', '!'/*0x1E*/, + '@', '#', '$', '%', '^'/*0x23*/, + '&', '*', '(', ')', 0, /*0x28*/ + 0, 0, 0, 0, 0, /*0x2d*/ + '+', '{', '}', '|', '~', /*0x32*/ + ':', '"', 0, '<', '>', /*0x37*/ + '?' + }, + + /* ALT MODIFIER */ + { + 0, 0, 0, 0, 0, 0 /*0x05*/, + 0, 0, 0, 0, 0 /*0x0a*/, + 0, 0, 0, 0, 0/*0x0f*/, + 0, 0, 0, 0, 0/*0x14*/, + 0, 0, 0, 0, 0/*0x19*/, + 0, 0, 0, 0, 0/*0x1E*/, + 0, 0, 0, 0, 0/*0x23*/, + 0, 0, 0, 0, 0 /*enter*/, /*0x28*/ + 0, 0, 0, 0, 0, /*0x2d*/ + 0, 0, 0, 0, 0, /*0x32*/ + 0, 0, 0, 0, 0, /*0x37*/ + 0 + } + +}; + + +USBHostKeyboard::USBHostKeyboard() +{ + host = USBHost::getHostInst(); + init(); +} + + +void USBHostKeyboard::init() +{ + dev = NULL; + int_in = NULL; + report_id = 0; + onKey = NULL; + onKeyCode = NULL; + dev_connected = false; + keyboard_intf = -1; + keyboard_device_found = false; +} + +bool USBHostKeyboard::connected() +{ + return dev_connected; +} + + +bool USBHostKeyboard::connect() +{ + + if (dev_connected) { + return true; + } + + for (uint8_t i = 0; i < MAX_DEVICE_CONNECTED; i++) { + if ((dev = host->getDevice(i)) != NULL) { + + if (host->enumerate(dev, this)) { + break; + } + + if (keyboard_device_found) { + { + /* As this is done in a specific thread + * this lock is taken to avoid to process the device + * disconnect in usb process during the device registering */ + USBHost::Lock Lock(host); + + int_in = dev->getEndpoint(keyboard_intf, INTERRUPT_ENDPOINT, IN); + + if (!int_in) { + break; + } + + USB_INFO("New Keyboard device: VID:%04x PID:%04x [dev: %p - intf: %d]", dev->getVid(), dev->getPid(), dev, keyboard_intf); + dev->setName("Keyboard", keyboard_intf); + host->registerDriver(dev, keyboard_intf, this, &USBHostKeyboard::init); + + int_in->attach(this, &USBHostKeyboard::rxHandler); + } + host->interruptRead(dev, int_in, report, int_in->getSize(), false); + + dev_connected = true; + return true; + } + } + } + init(); + return false; +} + +void USBHostKeyboard::rxHandler() +{ + int len = int_in->getLengthTransferred(); + int index = (len == 9) ? 1 : 0; + int len_listen = int_in->getSize(); + uint8_t key = 0; + if (len == 8 || len == 9) { + uint8_t modifier = (report[index] == 4) ? 3 : report[index]; + len_listen = len; + key = keymap[modifier][report[index + 2]]; + if (key && onKey) { + (*onKey)(key); + } + if ((report[index + 2] || modifier) && onKeyCode) { + (*onKeyCode)(report[index + 2], modifier); + } + } + if (dev && int_in) { + host->interruptRead(dev, int_in, report, len_listen, false); + } +} + +/*virtual*/ void USBHostKeyboard::setVidPid(uint16_t vid, uint16_t pid) +{ + // we don't check VID/PID for keyboard driver +} + +/*virtual*/ bool USBHostKeyboard::parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) //Must return true if the interface should be parsed +{ + if ((keyboard_intf == -1) && + (intf_class == HID_CLASS) && + (intf_subclass == 0x01) && + (intf_protocol == 0x01)) { + keyboard_intf = intf_nb; + return true; + } + return false; +} + +/*virtual*/ bool USBHostKeyboard::useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir) //Must return true if the endpoint will be used +{ + if (intf_nb == keyboard_intf) { + if (type == INTERRUPT_ENDPOINT && dir == IN) { + keyboard_device_found = true; + return true; + } + } + return false; +} + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostHID/USBHostKeyboard.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,105 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBHOSTKEYBOARD_H +#define USBHOSTKEYBOARD_H + +#include "USBHostConf.h" + +#if USBHOST_KEYBOARD + +#include "USBHost.h" + +/** + * A class to communicate a USB keyboard + */ +class USBHostKeyboard : public IUSBEnumerator +{ +public: + + /** + * Constructor + */ + USBHostKeyboard(); + + /** + * Try to connect a keyboard device + * + * @return true if connection was successful + */ + bool connect(); + + /** + * Check if a keyboard is connected + * + * @returns true if a keyboard is connected + */ + bool connected(); + + /** + * Attach a callback called when a keyboard event is received + * + * @param ptr function pointer + */ + inline void attach(void (*ptr)(uint8_t key)) + { + if (ptr != NULL) { + onKey = ptr; + } + } + + /** + * Attach a callback called when a keyboard event is received + * + * @param ptr function pointer + */ + inline void attach(void (*ptr)(uint8_t keyCode, uint8_t modifier)) + { + if (ptr != NULL) { + onKeyCode = ptr; + } + } + +protected: + //From IUSBEnumerator + virtual void setVidPid(uint16_t vid, uint16_t pid); + virtual bool parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol); //Must return true if the interface should be parsed + virtual bool useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir); //Must return true if the endpoint will be used + +private: + USBHost * host; + USBDeviceConnected * dev; + USBEndpoint * int_in; + uint8_t report[9]; + int keyboard_intf; + bool keyboard_device_found; + + bool dev_connected; + + void rxHandler(); + + void (*onKey)(uint8_t key); + void (*onKeyCode)(uint8_t key, uint8_t modifier); + + int report_id; + + void init(); + +}; + +#endif + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostHID/USBHostMouse.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,174 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 "USBHostMouse.h" + +#if USBHOST_MOUSE + +USBHostMouse::USBHostMouse() +{ + host = USBHost::getHostInst(); + init(); +} + +void USBHostMouse::init() +{ + dev = NULL; + int_in = NULL; + onUpdate = NULL; + onButtonUpdate = NULL; + onXUpdate = NULL; + onYUpdate = NULL; + onZUpdate = NULL; + report_id = 0; + dev_connected = false; + mouse_device_found = false; + mouse_intf = -1; + + buttons = 0; + x = 0; + y = 0; + z = 0; +} + +bool USBHostMouse::connected() +{ + return dev_connected; +} + +bool USBHostMouse::connect() +{ + int len_listen; + + if (dev_connected) { + return true; + } + + for (uint8_t i = 0; i < MAX_DEVICE_CONNECTED; i++) { + if ((dev = host->getDevice(i)) != NULL) { + + if(host->enumerate(dev, this)) { + break; + } + if (mouse_device_found) { + { + /* As this is done in a specific thread + * this lock is taken to avoid to process the device + * disconnect in usb process during the device registering */ + USBHost::Lock Lock(host); + int_in = dev->getEndpoint(mouse_intf, INTERRUPT_ENDPOINT, IN); + if (!int_in) { + break; + } + + USB_INFO("New Mouse device: VID:%04x PID:%04x [dev: %p - intf: %d]", dev->getVid(), dev->getPid(), dev, mouse_intf); + dev->setName("Mouse", mouse_intf); + host->registerDriver(dev, mouse_intf, this, &USBHostMouse::init); + + int_in->attach(this, &USBHostMouse::rxHandler); + len_listen = int_in->getSize(); + if (len_listen > sizeof(report)) { + len_listen = sizeof(report); + } + } + int ret=host->interruptRead(dev, int_in, report, len_listen, false); + MBED_ASSERT((ret==USB_TYPE_OK) || (ret ==USB_TYPE_PROCESSING) || (ret == USB_TYPE_FREE)); + if ((ret==USB_TYPE_OK) || (ret ==USB_TYPE_PROCESSING)) { + dev_connected = true; + } + if (ret == USB_TYPE_FREE) { + dev_connected = false; + } + return true; + } + } + } + init(); + return false; +} + +void USBHostMouse::rxHandler() +{ + int len_listen = int_in->getLengthTransferred(); + if (len_listen !=0) { + + if (onUpdate) { + (*onUpdate)(report[0] & 0x07, report[1], report[2], report[3]); + } + + if (onButtonUpdate && (buttons != (report[0] & 0x07))) { + (*onButtonUpdate)(report[0] & 0x07); + } + + if (onXUpdate && (x != report[1])) { + (*onXUpdate)(report[1]); + } + + if (onYUpdate && (y != report[2])) { + (*onYUpdate)(report[2]); + } + + if (onZUpdate && (z != report[3])) { + (*onZUpdate)(report[3]); + } + + // update mouse state + buttons = report[0] & 0x07; + x = report[1]; + y = report[2]; + z = report[3]; + } + /* set again the maximum value */ + len_listen = int_in->getSize(); + + if (len_listen > sizeof(report)) { + len_listen = sizeof(report); + } + + if (dev) { + host->interruptRead(dev, int_in, report, len_listen, false); + } +} + +/*virtual*/ void USBHostMouse::setVidPid(uint16_t vid, uint16_t pid) +{ + // we don't check VID/PID for mouse driver +} + +/*virtual*/ bool USBHostMouse::parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) //Must return true if the interface should be parsed +{ + if ((mouse_intf == -1) && + (intf_class == HID_CLASS) && + (intf_subclass == 0x01) && + (intf_protocol == 0x02)) { + mouse_intf = intf_nb; + return true; + } + return false; +} + +/*virtual*/ bool USBHostMouse::useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir) //Must return true if the endpoint will be used +{ + if (intf_nb == mouse_intf) { + if (type == INTERRUPT_ENDPOINT && dir == IN) { + mouse_device_found = true; + return true; + } + } + return false; +} + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostHID/USBHostMouse.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,144 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBHOSTMOUSE_H +#define USBHOSTMOUSE_H + +#include "USBHostConf.h" + +#if USBHOST_MOUSE + +#include "USBHost.h" + +/** + * A class to communicate a USB mouse + */ +class USBHostMouse : public IUSBEnumerator +{ +public: + + /** + * Constructor + */ + USBHostMouse(); + + /** + * Try to connect a mouse device + * + * @return true if connection was successful + */ + bool connect(); + + /** + * Check if a mouse is connected + * + * @returns true if a mouse is connected + */ + bool connected(); + + /** + * Attach a callback called when a mouse event is received + * + * @param ptr function pointer + */ + inline void attachEvent(void (*ptr)(uint8_t buttons, int8_t x, int8_t y, int8_t z)) + { + if (ptr != NULL) { + onUpdate = ptr; + } + } + + /** + * Attach a callback called when the button state changes + * + * @param ptr function pointer + */ + inline void attachButtonEvent(void (*ptr)(uint8_t buttons)) + { + if (ptr != NULL) { + onButtonUpdate = ptr; + } + } + + /** + * Attach a callback called when the X axis value changes + * + * @param ptr function pointer + */ + inline void attachXEvent(void (*ptr)(int8_t x)) + { + if (ptr != NULL) { + onXUpdate = ptr; + } + } + + /** + * Attach a callback called when the Y axis value changes + * + * @param ptr function pointer + */ + inline void attachYEvent(void (*ptr)(int8_t y)) + { + if (ptr != NULL) { + onYUpdate = ptr; + } + } + + /** + * Attach a callback called when the Z axis value changes (scrolling) + * + * @param ptr function pointer + */ + inline void attachZEvent(void (*ptr)(int8_t z)) + { + if (ptr != NULL) { + onZUpdate = ptr; + } + } + +protected: + //From IUSBEnumerator + virtual void setVidPid(uint16_t vid, uint16_t pid); + virtual bool parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol); //Must return true if the interface should be parsed + virtual bool useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir); //Must return true if the endpoint will be used + +private: + USBHost * host; + USBDeviceConnected * dev; + USBEndpoint * int_in; + uint8_t report[64]; + bool dev_connected; + bool mouse_device_found; + int mouse_intf; + + uint8_t buttons; + int8_t x; + int8_t y; + int8_t z; + + void rxHandler(); + void (*onUpdate)(uint8_t buttons, int8_t x, int8_t y, int8_t z); + void (*onButtonUpdate)(uint8_t buttons); + void (*onXUpdate)(int8_t x); + void (*onYUpdate)(int8_t y); + void (*onZUpdate)(int8_t z); + int report_id; + void init(); +}; + +#endif + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostHub/USBHostHub.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,291 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 "USBHostHub.h" + +#if MAX_HUB_NB + +#include "USBHost.h" +#include "dbg.h" + +#define GET_STATUS 0x00 +#define CLEAR_FEATURE 0x01 +#define GET_STATE 0x02 +#define SET_FEATURE 0x03 +#define GET_DESCRIPTOR 0x06 + +#define PORT_CONNECTION_FEATURE (0x00) +#define PORT_ENABLE_FEATURE (0x01) +#define PORT_RESET_FEATURE (0x04) +#define PORT_POWER_FEATURE (0x08) + +#define C_PORT_CONNECTION_FEATURE (16) +#define C_PORT_ENABLE_FEATURE (17) +#define C_PORT_RESET_FEATURE (20) + +#define PORT_CONNECTION (1 << 0) +#define PORT_ENABLE (1 << 1) +#define PORT_SUSPEND (1 << 2) +#define PORT_OVER_CURRENT (1 << 3) +#define PORT_RESET (1 << 4) +#define PORT_POWER (1 << 8) +#define PORT_LOW_SPEED (1 << 9) + +#define C_PORT_CONNECTION (1 << 16) +#define C_PORT_ENABLE (1 << 17) +#define C_PORT_SUSPEND (1 << 18) +#define C_PORT_OVER_CURRENT (1 << 19) +#define C_PORT_RESET (1 << 20) + +USBHostHub::USBHostHub() +{ + host = NULL; + init(); +} + +void USBHostHub::init() +{ + dev_connected = false; + dev = NULL; + int_in = NULL; + dev_connected = false; + hub_intf = -1; + hub_device_found = false; + nb_port = 0; + hub_characteristics = 0; + + for (int i = 0; i < MAX_HUB_PORT; i++) { + device_children[i] = NULL; + } +} + +void USBHostHub::setHost(USBHost * host_) +{ + host = host_; +} + +bool USBHostHub::connected() +{ + return dev_connected; +} + +bool USBHostHub::connect(USBDeviceConnected * dev) +{ + if (dev_connected) { + return true; + } + + if(host->enumerate(dev, this)) { + init(); + return false; + } + + if (hub_device_found) { + this->dev = dev; + + int_in = dev->getEndpoint(hub_intf, INTERRUPT_ENDPOINT, IN); + + if (!int_in) { + init(); + return false; + } + + USB_INFO("New HUB: VID:%04x PID:%04x [dev: %p - intf: %d]", dev->getVid(), dev->getPid(), dev, hub_intf); + dev->setName("Hub", hub_intf); + host->registerDriver(dev, hub_intf, this, &USBHostHub::disconnect); + + int_in->attach(this, &USBHostHub::rxHandler); + + // get HUB descriptor + host->controlRead( dev, + USB_DEVICE_TO_HOST | USB_REQUEST_TYPE_CLASS, + GET_DESCRIPTOR, + 0x29 << 8, 0, buf, sizeof(HubDescriptor)); + nb_port = buf[2]; + hub_characteristics = buf[3]; + + USB_DBG("Hub has %d port", nb_port); + + for (uint8_t j = 1; j <= nb_port; j++) { + setPortFeature(PORT_POWER_FEATURE, j); + } + wait_ms(buf[5]*2); + + host->interruptRead(dev, int_in, buf, 1, false); + dev_connected = true; + return true; + } + + return false; +} + +void USBHostHub::disconnect() +{ + init(); +} + +/*virtual*/ void USBHostHub::setVidPid(uint16_t vid, uint16_t pid) +{ + // we don't check VID/PID for MSD driver +} + +/*virtual*/ bool USBHostHub::parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) //Must return true if the interface should be parsed +{ + if ((hub_intf == -1) && + (intf_class == HUB_CLASS) && + (intf_subclass == 0) && + (intf_protocol == 0)) { + hub_intf = intf_nb; + return true; + } + return false; +} + +/*virtual*/ bool USBHostHub::useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir) //Must return true if the endpoint will be used +{ + if (intf_nb == hub_intf) { + if ((type == INTERRUPT_ENDPOINT) && (dir == IN)) { + hub_device_found = true; + return true; + } + } + return false; +} + +void USBHostHub::deviceConnected(USBDeviceConnected * dev) +{ + device_children[dev->getPort() - 1] = dev; +} + +void USBHostHub::deviceDisconnected(USBDeviceConnected * dev) +{ + device_children[dev->getPort() - 1] = NULL; +} + +void USBHostHub::hubDisconnected() +{ + for (uint8_t i = 0; i < MAX_HUB_PORT; i++) { + if (device_children[i] != NULL) { + host->freeDevice(device_children[i]); + } + } +} + +void USBHostHub::rxHandler() +{ + uint32_t status; + if (int_in) { + if ((int_in->getLengthTransferred())&&(int_in->getState() == USB_TYPE_IDLE)) { + for (int port = 1; port <= nb_port; port++) { + status = getPortStatus(port); + USB_DBG("[hub handler hub: %d] status port %d [hub: %p]: 0x%X", dev->getHub(), port, dev, status); + + // if connection status has changed + if (status & C_PORT_CONNECTION) { + if (status & PORT_CONNECTION) { + USB_DBG("[hub handler hub: %d - port: %d] new device connected", dev->getHub(), port); + host->deviceConnected(dev->getHub() + 1, port, status & PORT_LOW_SPEED, this); + } else { + USB_DBG("[hub handler hub: %d - port: %d] device disconnected", dev->getHub(), port); + host->deviceDisconnected(dev->getHub() + 1, port, this, 0); + } + + clearPortFeature(C_PORT_CONNECTION_FEATURE, port); + } + + if (status & C_PORT_RESET) { + clearPortFeature(C_PORT_RESET_FEATURE, port); + } + + if (status & C_PORT_ENABLE) { + clearPortFeature(C_PORT_ENABLE_FEATURE, port); + } + + if ((status & PORT_OVER_CURRENT)) { + USB_ERR("OVER CURRENT DETECTED\r\n"); + clearPortFeature(PORT_OVER_CURRENT, port); + host->deviceDisconnected(dev->getHub() + 1, port, this, 0); + } + } + } + host->interruptRead(dev, int_in, buf, 1, false); + } +} + +void USBHostHub::portReset(uint8_t port) +{ + // reset port + uint32_t status; + USB_DBG("reset port %d on hub: %p [this: %p]", port, dev, this) + setPortFeature(PORT_RESET_FEATURE, port); +#if defined(TARGET_RZ_A1H) + Thread::wait(50); // Reset release waiting for Hi-Speed check. +#endif + while(1) { + status = getPortStatus(port); + /* disconnection since reset request */ + if (!(status & PORT_CONNECTION)) { + break; + } + if (status & (PORT_ENABLE | PORT_RESET)) { + break; + } + if (status & PORT_OVER_CURRENT) { + USB_ERR("OVER CURRENT DETECTED\r\n"); + clearPortFeature(PORT_OVER_CURRENT, port); + host->deviceDisconnected(dev->getHub() + 1, port, this, 0); + break; + } + Thread::wait(10); + } +} + +void USBHostHub::setPortFeature(uint32_t feature, uint8_t port) +{ + host->controlWrite( dev, + USB_HOST_TO_DEVICE | USB_REQUEST_TYPE_CLASS | USB_RECIPIENT_INTERFACE | USB_RECIPIENT_ENDPOINT, + SET_FEATURE, + feature, + port, + NULL, + 0); +} + +void USBHostHub::clearPortFeature(uint32_t feature, uint8_t port) +{ + host->controlWrite( dev, + USB_HOST_TO_DEVICE | USB_REQUEST_TYPE_CLASS | USB_RECIPIENT_INTERFACE | USB_RECIPIENT_ENDPOINT, + CLEAR_FEATURE, + feature, + port, + NULL, + 0); +} + +uint32_t USBHostHub::getPortStatus(uint8_t port) +{ + uint32_t st; + host->controlRead( dev, + USB_DEVICE_TO_HOST | USB_REQUEST_TYPE_CLASS | USB_RECIPIENT_INTERFACE | USB_RECIPIENT_ENDPOINT, + GET_STATUS, + 0, + port, + (uint8_t *)&st, + 4); + return st; +} + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostHub/USBHostHub.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,126 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBHOSTHUB_H +#define USBHOSTHUB_H + +#include "USBHostConf.h" + +#if MAX_HUB_NB + +#include "USBHostTypes.h" +#include "IUSBEnumerator.h" + +class USBHost; +class USBDeviceConnected; +class USBEndpoint; + +/** + * A class to use a USB Hub + */ +class USBHostHub : public IUSBEnumerator +{ +public: + /** + * Constructor + */ + USBHostHub(); + + /** + * Check if a USB Hub is connected + * + * @return true if a serial device is connected + */ + bool connected(); + + /** + * Try to connect device + * + * @param dev device to connect + * @return true if connection was successful + */ + bool connect(USBDeviceConnected * dev); + + /** + * Automatically called by USBHost when a device + * has been enumerated by usb_thread + * + * @param dev device connected + */ + void deviceConnected(USBDeviceConnected * dev); + + /** + * Automatically called by USBHost when a device + * has been disconnected from this hub + * + * @param dev device disconnected + */ + void deviceDisconnected(USBDeviceConnected * dev); + + /** + * Rest a specific port + * + * @param port port number + */ + void portReset(uint8_t port); + + /* + * Called by USBHost to set the instance of USBHost + * + * @param host host instance + */ + void setHost(USBHost * host); + + /** + * Called by USBhost when a hub has been disconnected + */ + void hubDisconnected(); + +protected: + //From IUSBEnumerator + virtual void setVidPid(uint16_t vid, uint16_t pid); + virtual bool parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol); //Must return true if the interface should be parsed + virtual bool useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir); //Must return true if the endpoint will be used + +private: + USBHost * host; + USBDeviceConnected * dev; + bool dev_connected; + USBEndpoint * int_in; + uint8_t nb_port; + uint8_t hub_characteristics; + + void rxHandler(); + + uint8_t buf[sizeof(HubDescriptor)]; + + int hub_intf; + bool hub_device_found; + + void setPortFeature(uint32_t feature, uint8_t port); + void clearPortFeature(uint32_t feature, uint8_t port); + uint32_t getPortStatus(uint8_t port); + + USBDeviceConnected * device_children[MAX_HUB_PORT]; + + void init(); + void disconnect(); + +}; + +#endif + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostMIDI/USBHostMIDI.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,362 @@ +/* Copyright (c) 2014 mbed.org, MIT License + * + * Permission is hereby granted, free of charge, to any person obtaining a copy of this software + * and associated documentation files (the "Software"), to deal in the Software without + * restriction, including without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all copies or + * substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING + * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, + * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + */ + +#include "USBHostMIDI.h" + +#if USBHOST_MIDI + +#include "dbg.h" + +#define SET_LINE_CODING 0x20 + +USBHostMIDI::USBHostMIDI() { + host = USBHost::getHostInst(); + size_bulk_in = 0; + size_bulk_out = 0; + init(); +} + +void USBHostMIDI::init() { + dev = NULL; + bulk_in = NULL; + bulk_out = NULL; + dev_connected = false; + midi_intf = -1; + midi_device_found = false; + sysExBufferPos = 0; +} + +bool USBHostMIDI::connected() { + return dev_connected; +} + +bool USBHostMIDI::connect() { + if (dev_connected) { + return true; + } + + for (uint8_t i = 0; i < MAX_DEVICE_CONNECTED; i++) { + if ((dev = host->getDevice(i)) != NULL) { + + USB_DBG("Trying to connect MIDI device\r\n"); + + if (host->enumerate(dev, this)) { + break; + } + + if (midi_device_found) { + bulk_in = dev->getEndpoint(midi_intf, BULK_ENDPOINT, IN); + bulk_out = dev->getEndpoint(midi_intf, BULK_ENDPOINT, OUT); + + if (!bulk_in || !bulk_out) { + break; + } + + USB_INFO("New MIDI device: VID:%04x PID:%04x [dev: %p - intf: %d]", dev->getVid(), dev->getPid(), dev, midi_intf); + dev->setName("MIDI", midi_intf); + host->registerDriver(dev, midi_intf, this, &USBHostMIDI::init); + + size_bulk_in = bulk_in->getSize(); + size_bulk_out = bulk_out->getSize(); + + bulk_in->attach(this, &USBHostMIDI::rxHandler); + + host->bulkRead(dev, bulk_in, buf, size_bulk_in, false); + dev_connected = true; + return true; + } + } + } + + init(); + return false; +} + +void USBHostMIDI::rxHandler() { + uint8_t *midi; + if (bulk_in) { + int length = bulk_in->getLengthTransferred(); + if (bulk_in->getState() == USB_TYPE_IDLE || bulk_in->getState() == USB_TYPE_FREE) { + // MIDI event handling + for (int i = 0; i < length; i += 4) { + if (i + 4 > length) { + // length shortage, ignored. + break; + } + + // read each four bytes + midi = &buf[i]; + // process MIDI message + // switch by code index number + switch (midi[0] & 0xf) { + case 0: // miscellaneous function codes + miscellaneousFunctionCode(midi[1], midi[2], midi[3]); + break; + case 1: // cable events + cableEvent(midi[1], midi[2], midi[3]); + break; + case 2: // two bytes system common messages + systemCommonTwoBytes(midi[1], midi[2]); + break; + case 3: // three bytes system common messages + systemCommonThreeBytes(midi[1], midi[2], midi[3]); + break; + case 4: // SysEx starts or continues + sysExBuffer[sysExBufferPos++] = midi[1]; + if (sysExBufferPos >= 64) { + systemExclusive(sysExBuffer, sysExBufferPos, true); + sysExBufferPos = 0; + } + sysExBuffer[sysExBufferPos++] = midi[2]; + if (sysExBufferPos >= 64) { + systemExclusive(sysExBuffer, sysExBufferPos, true); + sysExBufferPos = 0; + } + sysExBuffer[sysExBufferPos++] = midi[3]; + // SysEx continues. don't send + break; + case 5: // SysEx ends with single byte + sysExBuffer[sysExBufferPos++] = midi[1]; + systemExclusive(sysExBuffer, sysExBufferPos, false); + sysExBufferPos = 0; + break; + case 6: // SysEx ends with two bytes + sysExBuffer[sysExBufferPos++] = midi[1]; + if (sysExBufferPos >= 64) { + systemExclusive(sysExBuffer, sysExBufferPos, true); + sysExBufferPos = 0; + } + sysExBuffer[sysExBufferPos++] = midi[2]; + systemExclusive(sysExBuffer, sysExBufferPos, false); + sysExBufferPos = 0; + break; + case 7: // SysEx ends with three bytes + sysExBuffer[sysExBufferPos++] = midi[1]; + if (sysExBufferPos >= 64) { + systemExclusive(sysExBuffer, sysExBufferPos, true); + sysExBufferPos = 0; + } + sysExBuffer[sysExBufferPos++] = midi[2]; + if (sysExBufferPos >= 64) { + systemExclusive(sysExBuffer, sysExBufferPos, true); + sysExBufferPos = 0; + } + sysExBuffer[sysExBufferPos++] = midi[3]; + systemExclusive(sysExBuffer, sysExBufferPos, false); + sysExBufferPos = 0; + break; + case 8: + noteOff(midi[1] & 0xf, midi[2], midi[3]); + break; + case 9: + if (midi[3]) { + noteOn(midi[1] & 0xf, midi[2], midi[3]); + } else { + noteOff(midi[1] & 0xf, midi[2], midi[3]); + } + break; + case 10: + polyKeyPress(midi[1] & 0xf, midi[2], midi[3]); + break; + case 11: + controlChange(midi[1] & 0xf, midi[2], midi[3]); + break; + case 12: + programChange(midi[1] & 0xf, midi[2]); + break; + case 13: + channelPressure(midi[1] & 0xf, midi[2]); + break; + case 14: + pitchBend(midi[1] & 0xf, midi[2] | (midi[3] << 7)); + break; + case 15: + singleByte(midi[1]); + break; + } + } + + // read another message + host->bulkRead(dev, bulk_in, buf, size_bulk_in, false); + } + } +} + +bool USBHostMIDI::sendMidiBuffer(uint8_t data0, uint8_t data1, uint8_t data2, uint8_t data3) { + if (bulk_out) { + uint8_t midi[4]; + + midi[0] = data0; + midi[1] = data1; + midi[2] = data2; + midi[3] = data3; + if (host->bulkWrite(dev, bulk_out, (uint8_t *)midi, 4) == USB_TYPE_OK) { + return true; + } + } + return false; +} + +bool USBHostMIDI::sendMiscellaneousFunctionCode(uint8_t data1, uint8_t data2, uint8_t data3) { + return sendMidiBuffer(0, data1, data2, data3); +} + +bool USBHostMIDI::sendCableEvent(uint8_t data1, uint8_t data2, uint8_t data3) { + return sendMidiBuffer(1, data1, data2, data3); +} + +bool USBHostMIDI::sendSystemCommmonTwoBytes(uint8_t data1, uint8_t data2) { + return sendMidiBuffer(2, data1, data2, 0); +} + +bool USBHostMIDI::sendSystemCommmonThreeBytes(uint8_t data1, uint8_t data2, uint8_t data3) { + return sendMidiBuffer(3, data1, data2, 0); +} + +bool USBHostMIDI::sendSystemExclusive(uint8_t *buffer, int length) { + uint8_t midi[64]; + int midiLength; + int midiPos; + if (bulk_out) { + for (int i = 0; i < length; i += 48) { + if (i + 48 >= length) { + // contains last data + midiLength = (((length - i) + 2) / 3) * 4; + for (int pos = i; pos < length; pos += 3) { + midiPos = (pos + 2) / 3 * 4; + if (pos + 3 >= length) { + // last data + switch (pos % 3) { + case 0: + midi[midiPos ] = 7; + midi[midiPos + 1] = buffer[pos ]; + midi[midiPos + 2] = buffer[pos + 1]; + midi[midiPos + 3] = buffer[pos + 2]; + break; + case 1: + midi[midiPos ] = 5; + midi[midiPos + 1] = buffer[pos ]; + midi[midiPos + 2] = 0; + midi[midiPos + 3] = 0; + break; + case 2: + midi[midiPos ] = 6; + midi[midiPos + 1] = buffer[pos ]; + midi[midiPos + 2] = buffer[pos + 1]; + midi[midiPos + 3] = 0; + break; + } + } else { + // has more data + midi[midiPos ] = 4; + midi[midiPos + 1] = buffer[pos ]; + midi[midiPos + 2] = buffer[pos + 1]; + midi[midiPos + 3] = buffer[pos + 2]; + } + } + } else { + // has more data + midiLength = 64; + for (int pos = i; pos < length; pos += 3) { + midiPos = (pos + 2) / 3 * 4; + midi[midiPos ] = 4; + midi[midiPos + 1] = buffer[pos ]; + midi[midiPos + 2] = buffer[pos + 1]; + midi[midiPos + 3] = buffer[pos + 2]; + } + } + + if (host->bulkWrite(dev, bulk_out, (uint8_t *)midi, midiLength) != USB_TYPE_OK) { + return false; + } + } + return true; + } + return false; +} + +bool USBHostMIDI::sendNoteOff(uint8_t channel, uint8_t note, uint8_t velocity) { + return sendMidiBuffer(8, channel & 0xf | 0x80, note & 0x7f, velocity & 0x7f); +} + +bool USBHostMIDI::sendNoteOn(uint8_t channel, uint8_t note, uint8_t velocity) { + return sendMidiBuffer(9, channel & 0xf | 0x90, note & 0x7f, velocity & 0x7f); +} + +bool USBHostMIDI::sendPolyKeyPress(uint8_t channel, uint8_t note, uint8_t pressure) { + return sendMidiBuffer(10, channel & 0xf | 0xa0, note & 0x7f, pressure & 0x7f); +} + +bool USBHostMIDI::sendControlChange(uint8_t channel, uint8_t key, uint8_t value) { + return sendMidiBuffer(11, channel & 0xf | 0xb0, key & 0x7f, value & 0x7f); +} + +bool USBHostMIDI::sendProgramChange(uint8_t channel, uint8_t program) { + return sendMidiBuffer(12, channel & 0xf | 0xc0, program & 0x7f, 0); +} + +bool USBHostMIDI::sendChannelPressure(uint8_t channel, uint8_t pressure) { + return sendMidiBuffer(13, channel & 0xf | 0xd0, pressure & 0x7f, 0); +} + +bool USBHostMIDI::sendPitchBend(uint8_t channel, uint16_t value) { + return sendMidiBuffer(14, channel & 0xf | 0xe0, value & 0x7f, (value >> 7) & 0x7f); +} + +bool USBHostMIDI::sendSingleByte(uint8_t data) { + return sendMidiBuffer(15, data, 0, 0); +} + +/*virtual*/ void USBHostMIDI::setVidPid(uint16_t vid, uint16_t pid) +{ + // we don't check VID/PID for this driver +} + +/*virtual*/ bool USBHostMIDI::parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) //Must return true if the interface should be parsed +{ + // USB MIDI class/subclass + if ((midi_intf == -1) && + (intf_class == AUDIO_CLASS) && + (intf_subclass == 0x03)) { + midi_intf = intf_nb; + return true; + } + + // vendor specific device + if ((midi_intf == -1) && + (intf_class == 0xff) && + (intf_subclass == 0x03)) { + midi_intf = intf_nb; + return true; + } + + return false; +} + +/*virtual*/ bool USBHostMIDI::useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir) //Must return true if the endpoint will be used +{ + if (intf_nb == midi_intf) { + if (type == BULK_ENDPOINT) { + midi_device_found = true; + return true; + } + } + return false; +} + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostMIDI/USBHostMIDI.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,353 @@ +/* Copyright (c) 2014 mbed.org, MIT License + * + * Permission is hereby granted, free of charge, to any person obtaining a copy of this software + * and associated documentation files (the "Software"), to deal in the Software without + * restriction, including without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all copies or + * substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING + * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, + * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef USBHOSTMIDI_H +#define USBHOSTMIDI_H + +#include "USBHostConf.h" + +#if USBHOST_MIDI + +#include "USBHost.h" + +/** + * A class to communicate a USB MIDI device + */ +class USBHostMIDI : public IUSBEnumerator { +public: + /** + * Constructor + */ + USBHostMIDI(); + + /** + * Check if a USB MIDI device is connected + * + * @returns true if a midi device is connected + */ + bool connected(); + + /** + * Try to connect a midi device + * + * @return true if connection was successful + */ + bool connect(); + + /** + * Attach a callback called when miscellaneous function code is received + * + * @param ptr function pointer + * prototype: void onMiscellaneousFunctionCode(uint8_t data1, uint8_t data2, uint8_t data3); + */ + inline void attachMiscellaneousFunctionCode(void (*fn)(uint8_t, uint8_t, uint8_t)) { + miscellaneousFunctionCode = fn; + } + + /** + * Attach a callback called when cable event is received + * + * @param ptr function pointer + * prototype: void onCableEvent(uint8_t data1, uint8_t data2, uint8_t data3); + */ + inline void attachCableEvent(void (*fn)(uint8_t, uint8_t, uint8_t)) { + cableEvent = fn; + } + + /** + * Attach a callback called when system exclusive is received + * + * @param ptr function pointer + * prototype: void onSystemCommonTwoBytes(uint8_t data1, uint8_t data2); + */ + inline void attachSystemCommonTwoBytes(void (*fn)(uint8_t, uint8_t)) { + systemCommonTwoBytes = fn; + } + + /** + * Attach a callback called when system exclusive is received + * + * @param ptr function pointer + * prototype: void onSystemCommonThreeBytes(uint8_t data1, uint8_t data2, uint8_t data3); + */ + inline void attachSystemCommonThreeBytes(void (*fn)(uint8_t, uint8_t, uint8_t)) { + systemCommonThreeBytes = fn; + } + + /** + * Attach a callback called when system exclusive is received + * + * @param ptr function pointer + * prototype: void onSystemExclusive(uint8_t *data, uint16_t length, bool hasNextData); + */ + inline void attachSystemExclusive(void (*fn)(uint8_t *, uint16_t, bool)) { + systemExclusive = fn; + } + + /** + * Attach a callback called when note on is received + * + * @param ptr function pointer + * prototype: void onNoteOn(uint8_t channel, uint8_t note, uint8_t velocity); + */ + inline void attachNoteOn(void (*fn)(uint8_t, uint8_t, uint8_t)) { + noteOn = fn; + } + + /** + * Attach a callback called when note off is received + * + * @param ptr function pointer + * prototype: void onNoteOff(uint8_t channel, uint8_t note, uint8_t velocity); + */ + inline void attachNoteOff(void (*fn)(uint8_t, uint8_t, uint8_t)) { + noteOff = fn; + } + + /** + * Attach a callback called when poly keypress is received + * + * @param ptr function pointer + * prototype: void onPolyKeyPress(uint8_t channel, uint8_t note, uint8_t pressure); + */ + inline void attachPolyKeyPress(void (*fn)(uint8_t, uint8_t, uint8_t)) { + polyKeyPress = fn; + } + + /** + * Attach a callback called when control change is received + * + * @param ptr function pointer + * prototype: void onControlChange(uint8_t channel, uint8_t key, uint8_t value); + */ + inline void attachControlChange(void (*fn)(uint8_t, uint8_t, uint8_t)) { + controlChange = fn; + } + + /** + * Attach a callback called when program change is received + * + * @param ptr function pointer + * prototype: void onProgramChange(uint8_t channel, uint8_t program); + */ + inline void attachProgramChange(void (*fn)(uint8_t, uint8_t)) { + programChange = fn; + } + + /** + * Attach a callback called when channel pressure is received + * + * @param ptr function pointer + * prototype: void onChannelPressure(uint8_t channel, uint8_t pressure); + */ + inline void attachChannelPressure(void (*fn)(uint8_t, uint8_t)) { + channelPressure = fn; + } + + /** + * Attach a callback called when pitch bend is received + * + * @param ptr function pointer + * prototype: void onPitchBend(uint8_t channel, uint16_t value); + */ + inline void attachPitchBend(void (*fn)(uint8_t, uint16_t)) { + pitchBend = fn; + } + + /** + * Attach a callback called when single byte is received + * + * @param ptr function pointer + * prototype: void onSingleByte(uint8_t value); + */ + inline void attachSingleByte(void (*fn)(uint8_t)) { + singleByte = fn; + } + + /** + * Send a cable event with 3 bytes event + * + * @param data1 0-255 + * @param data2 0-255 + * @param data3 0-255 + * @return true if message sent successfully + */ + bool sendMiscellaneousFunctionCode(uint8_t data1, uint8_t data2, uint8_t data3); + + /** + * Send a cable event with 3 bytes event + * + * @param data1 0-255 + * @param data2 0-255 + * @param data3 0-255 + * @return true if message sent successfully + */ + bool sendCableEvent(uint8_t data1, uint8_t data2, uint8_t data3); + + /** + * Send a system common message with 2 bytes event + * + * @param data1 0-255 + * @param data2 0-255 + * @return true if message sent successfully + */ + bool sendSystemCommmonTwoBytes(uint8_t data1, uint8_t data2); + + /** + * Send a system common message with 3 bytes event + * + * @param data1 0-255 + * @param data2 0-255 + * @param data3 0-255 + * @return true if message sent successfully + */ + bool sendSystemCommmonThreeBytes(uint8_t data1, uint8_t data2, uint8_t data3); + + /** + * Send a system exclusive event + * + * @param buffer, starts with 0xF0, and end with 0xf7 + * @param length + * @return true if message sent successfully + */ + bool sendSystemExclusive(uint8_t *buffer, int length); + + /** + * Send a note off event + * + * @param channel 0-15 + * @param note 0-127 + * @param velocity 0-127 + * @return true if message sent successfully + */ + bool sendNoteOff(uint8_t channel, uint8_t note, uint8_t velocity); + + /** + * Send a note on event + * + * @param channel 0-15 + * @param note 0-127 + * @param velocity 0-127 (0 means note off) + * @return true if message sent successfully + */ + bool sendNoteOn(uint8_t channel, uint8_t note, uint8_t velocity); + + /** + * Send a poly keypress event + * + * @param channel 0-15 + * @param note 0-127 + * @param pressure 0-127 + * @return true if message sent successfully + */ + bool sendPolyKeyPress(uint8_t channel, uint8_t note, uint8_t pressure); + + /** + * Send a control change event + * + * @param channel 0-15 + * @param key 0-127 + * @param value 0-127 + * @return true if message sent successfully + */ + bool sendControlChange(uint8_t channel, uint8_t key, uint8_t value); + + /** + * Send a program change event + * + * @param channel 0-15 + * @param program 0-127 + * @return true if message sent successfully + */ + bool sendProgramChange(uint8_t channel, uint8_t program); + + /** + * Send a channel pressure event + * + * @param channel 0-15 + * @param pressure 0-127 + * @return true if message sent successfully + */ + bool sendChannelPressure(uint8_t channel, uint8_t pressure); + + /** + * Send a control change event + * + * @param channel 0-15 + * @param key 0(lower)-8191(center)-16383(higher) + * @return true if message sent successfully + */ + bool sendPitchBend(uint8_t channel, uint16_t value); + + /** + * Send a single byte event + * + * @param data 0-255 + * @return true if message sent successfully + */ + bool sendSingleByte(uint8_t data); + +protected: + //From IUSBEnumerator + virtual void setVidPid(uint16_t vid, uint16_t pid); + virtual bool parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol); //Must return true if the interface should be parsed + virtual bool useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir); //Must return true if the endpoint will be used + +private: + USBHost * host; + USBDeviceConnected * dev; + USBEndpoint * bulk_in; + USBEndpoint * bulk_out; + uint32_t size_bulk_in; + uint32_t size_bulk_out; + + bool dev_connected; + + void init(); + + uint8_t buf[64]; + + void rxHandler(); + + uint16_t sysExBufferPos; + uint8_t sysExBuffer[64]; + + void (*miscellaneousFunctionCode)(uint8_t, uint8_t, uint8_t); + void (*cableEvent)(uint8_t, uint8_t, uint8_t); + void (*systemCommonTwoBytes)(uint8_t, uint8_t); + void (*systemCommonThreeBytes)(uint8_t, uint8_t, uint8_t); + void (*systemExclusive)(uint8_t *, uint16_t, bool); + void (*noteOff)(uint8_t, uint8_t, uint8_t); + void (*noteOn)(uint8_t, uint8_t, uint8_t); + void (*polyKeyPress)(uint8_t, uint8_t, uint8_t); + void (*controlChange)(uint8_t, uint8_t, uint8_t); + void (*programChange)(uint8_t, uint8_t); + void (*channelPressure)(uint8_t, uint8_t); + void (*pitchBend)(uint8_t, uint16_t); + void (*singleByte)(uint8_t); + + bool sendMidiBuffer(uint8_t data0, uint8_t data1, uint8_t data2, uint8_t data3); + + int midi_intf; + bool midi_device_found; + +}; + +#endif /* USBHOST_MIDI */ + +#endif /* USBHOSTMIDI_H */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostMSD/USBHostMSD.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,379 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 "USBHostMSD.h" + +#if USBHOST_MSD + +#include "dbg.h" + +#define CBW_SIGNATURE 0x43425355 +#define CSW_SIGNATURE 0x53425355 + +#define DEVICE_TO_HOST 0x80 +#define HOST_TO_DEVICE 0x00 + +#define GET_MAX_LUN (0xFE) +#define BO_MASS_STORAGE_RESET (0xFF) + +USBHostMSD::USBHostMSD(const char * rootdir) : FATFileSystem(rootdir) +{ + host = USBHost::getHostInst(); + init(); +} + +void USBHostMSD::init() { + dev_connected = false; + dev = NULL; + bulk_in = NULL; + bulk_out = NULL; + dev_connected = false; + blockSize = 0; + blockCount = 0; + msd_intf = -1; + msd_device_found = false; + disk_init = false; + dev_connected = false; + nb_ep = 0; +} + + +bool USBHostMSD::connected() +{ + return dev_connected; +} + +bool USBHostMSD::connect() +{ + + if (dev_connected) { + return true; + } + + for (uint8_t i = 0; i < MAX_DEVICE_CONNECTED; i++) { + if ((dev = host->getDevice(i)) != NULL) { + + USB_DBG("Trying to connect MSD device\r\n"); + + if(host->enumerate(dev, this)) + break; + + if (msd_device_found) { + /* As this is done in a specific thread + * this lock is taken to avoid to process a disconnection in + * usb process during the device registering */ + USBHost::Lock Lock(host); + + bulk_in = dev->getEndpoint(msd_intf, BULK_ENDPOINT, IN); + bulk_out = dev->getEndpoint(msd_intf, BULK_ENDPOINT, OUT); + + if (!bulk_in || !bulk_out) + continue; + + USB_INFO("New MSD device: VID:%04x PID:%04x [dev: %p - intf: %d]", dev->getVid(), dev->getPid(), dev, msd_intf); + dev->setName("MSD", msd_intf); + host->registerDriver(dev, msd_intf, this, &USBHostMSD::init); + + dev_connected = true; + return true; + } + } //if() + } //for() + init(); + return false; +} + +/*virtual*/ void USBHostMSD::setVidPid(uint16_t vid, uint16_t pid) +{ + // we don't check VID/PID for MSD driver +} + +/*virtual*/ bool USBHostMSD::parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) //Must return true if the interface should be parsed +{ + if ((msd_intf == -1) && + (intf_class == MSD_CLASS) && + (intf_subclass == 0x06) && + (intf_protocol == 0x50)) { + msd_intf = intf_nb; + return true; + } + return false; +} + +/*virtual*/ bool USBHostMSD::useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir) //Must return true if the endpoint will be used +{ + if (intf_nb == msd_intf) { + if (type == BULK_ENDPOINT) { + nb_ep++; + if (nb_ep == 2) + msd_device_found = true; + return true; + } + } + return false; +} + + +int USBHostMSD::testUnitReady() +{ + USB_DBG("Test unit ready"); + return SCSITransfer(NULL, 6, DEVICE_TO_HOST, 0, 0); +} + + +int USBHostMSD::readCapacity() +{ + USB_DBG("Read capacity"); + uint8_t cmd[10] = {0x25,0,0,0,0,0,0,0,0,0}; + uint8_t result[8]; + int status = SCSITransfer(cmd, 10, DEVICE_TO_HOST, result, 8); + if (status == 0) { + blockCount = (result[0] << 24) | (result[1] << 16) | (result[2] << 8) | result[3]; + blockSize = (result[4] << 24) | (result[5] << 16) | (result[6] << 8) | result[7]; + USB_INFO("MSD [dev: %p] - blockCount: %lld, blockSize: %d, Capacity: %lld\r\n", dev, blockCount, blockSize, blockCount*blockSize); + } + return status; +} + + +int USBHostMSD::SCSIRequestSense() +{ + USB_DBG("Request sense"); + uint8_t cmd[6] = {0x03,0,0,0,18,0}; + uint8_t result[18]; + int status = SCSITransfer(cmd, 6, DEVICE_TO_HOST, result, 18); + return status; +} + + +int USBHostMSD::inquiry(uint8_t lun, uint8_t page_code) +{ + USB_DBG("Inquiry"); + uint8_t evpd = (page_code == 0) ? 0 : 1; + uint8_t cmd[6] = {0x12, uint8_t((lun << 5) | evpd), page_code, 0, 36, 0}; + uint8_t result[36]; + int status = SCSITransfer(cmd, 6, DEVICE_TO_HOST, result, 36); + if (status == 0) { + char vid_pid[17]; + memcpy(vid_pid, &result[8], 8); + vid_pid[8] = 0; + USB_INFO("MSD [dev: %p] - Vendor ID: %s", dev, vid_pid); + + memcpy(vid_pid, &result[16], 16); + vid_pid[16] = 0; + USB_INFO("MSD [dev: %p] - Product ID: %s", dev, vid_pid); + + memcpy(vid_pid, &result[32], 4); + vid_pid[4] = 0; + USB_INFO("MSD [dev: %p] - Product rev: %s", dev, vid_pid); + } + return status; +} + +int USBHostMSD::checkResult(uint8_t res, USBEndpoint * ep) +{ + // if ep stalled: send clear feature + if (res == USB_TYPE_STALL_ERROR) { + res = host->controlWrite( dev, + USB_RECIPIENT_ENDPOINT | USB_HOST_TO_DEVICE | USB_REQUEST_TYPE_STANDARD, + CLEAR_FEATURE, + 0, ep->getAddress(), NULL, 0); + // set state to IDLE if clear feature successful + if (res == USB_TYPE_OK) { + ep->setState(USB_TYPE_IDLE); + } + } + + if (res != USB_TYPE_OK) + return -1; + + return 0; +} + + +int USBHostMSD::SCSITransfer(uint8_t * cmd, uint8_t cmd_len, int flags, uint8_t * data, uint32_t transfer_len) +{ + + int res = 0; + + cbw.Signature = CBW_SIGNATURE; + cbw.Tag = 0; + cbw.DataLength = transfer_len; + cbw.Flags = flags; + cbw.LUN = 0; + cbw.CBLength = cmd_len; + memset(cbw.CB,0,sizeof(cbw.CB)); + if (cmd) { + memcpy(cbw.CB,cmd,cmd_len); + } + + // send the cbw + USB_DBG("Send CBW"); + res = host->bulkWrite(dev, bulk_out,(uint8_t *)&cbw, 31); + if (checkResult(res, bulk_out)) + return -1; + + // data stage if needed + if (data) { + USB_DBG("data stage"); + if (flags == HOST_TO_DEVICE) { + + res = host->bulkWrite(dev, bulk_out, data, transfer_len); + if (checkResult(res, bulk_out)) + return -1; + + } else if (flags == DEVICE_TO_HOST) { + + res = host->bulkRead(dev, bulk_in, data, transfer_len); + if (checkResult(res, bulk_in)) + return -1; + } + } + + // status stage + csw.Signature = 0; + USB_DBG("Read CSW"); + res = host->bulkRead(dev, bulk_in,(uint8_t *)&csw, 13); + if (checkResult(res, bulk_in)) + return -1; + + if (csw.Signature != CSW_SIGNATURE) { + return -1; + } + + USB_DBG("recv csw: status: %d", csw.Status); + + // ModeSense? + if ((csw.Status == 1) && (cmd[0] != 0x03)) { + USB_DBG("request mode sense"); + return SCSIRequestSense(); + } + + // perform reset recovery + if ((csw.Status == 2) && (cmd[0] != 0x03)) { + + // send Bulk-Only Mass Storage Reset request + res = host->controlWrite( dev, + USB_RECIPIENT_INTERFACE | USB_HOST_TO_DEVICE | USB_REQUEST_TYPE_CLASS, + BO_MASS_STORAGE_RESET, + 0, msd_intf, NULL, 0); + + // unstall both endpoints + res = host->controlWrite( dev, + USB_RECIPIENT_ENDPOINT | USB_HOST_TO_DEVICE | USB_REQUEST_TYPE_STANDARD, + CLEAR_FEATURE, + 0, bulk_in->getAddress(), NULL, 0); + + res = host->controlWrite( dev, + USB_RECIPIENT_ENDPOINT | USB_HOST_TO_DEVICE | USB_REQUEST_TYPE_STANDARD, + CLEAR_FEATURE, + 0, bulk_out->getAddress(), NULL, 0); + + } + + return csw.Status; +} + + +int USBHostMSD::dataTransfer(uint8_t * buf, uint32_t block, uint8_t nbBlock, int direction) +{ + uint8_t cmd[10]; + memset(cmd,0,10); + cmd[0] = (direction == DEVICE_TO_HOST) ? 0x28 : 0x2A; + + cmd[2] = (block >> 24) & 0xff; + cmd[3] = (block >> 16) & 0xff; + cmd[4] = (block >> 8) & 0xff; + cmd[5] = block & 0xff; + + cmd[7] = (nbBlock >> 8) & 0xff; + cmd[8] = nbBlock & 0xff; + + return SCSITransfer(cmd, 10, direction, buf, blockSize*nbBlock); +} + +int USBHostMSD::getMaxLun() +{ + uint8_t buf[1], res; + res = host->controlRead( dev, USB_RECIPIENT_INTERFACE | USB_DEVICE_TO_HOST | USB_REQUEST_TYPE_CLASS, + 0xfe, 0, msd_intf, buf, 1); + USB_DBG("max lun: %d", buf[0]); + return res; +} + +int USBHostMSD::disk_initialize() { + USB_DBG("FILESYSTEM: init"); + uint16_t i, timeout = 10; + + getMaxLun(); + + for (i = 0; i < timeout; i++) { + Thread::wait(100); + if (!testUnitReady()) + break; + } + + if (i == timeout) { + disk_init = false; + return -1; + } + + inquiry(0, 0); + disk_init = 1; + return readCapacity(); +} + +int USBHostMSD::disk_write(const uint8_t* buffer, uint32_t block_number, uint32_t count) { + USB_DBG("FILESYSTEM: write block: %lld, count: %d", block_number, count); + if (!disk_init) { + disk_initialize(); + } + if (!disk_init) + return -1; + for (uint32_t b = block_number; b < block_number + count; b++) { + if (dataTransfer((uint8_t*)buffer, b, 1, HOST_TO_DEVICE)) + return -1; + buffer += 512; + } + return 0; +} + +int USBHostMSD::disk_read(uint8_t* buffer, uint32_t block_number, uint32_t count) { + USB_DBG("FILESYSTEM: read block: %lld, count: %d", block_number, count); + if (!disk_init) { + disk_initialize(); + } + if (!disk_init) + return -1; + for (uint32_t b = block_number; b < block_number + count; b++) { + if (dataTransfer((uint8_t*)buffer, b, 1, DEVICE_TO_HOST)) + return -1; + buffer += 512; + } + return 0; +} + +uint32_t USBHostMSD::disk_sectors() { + USB_DBG("FILESYSTEM: sectors"); + if (!disk_init) { + disk_initialize(); + } + if (!disk_init) + return 0; + return blockCount; +} + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostMSD/USBHostMSD.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,119 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBHOSTMSD_H +#define USBHOSTMSD_H + +#include "USBHostConf.h" + +#if USBHOST_MSD + +#include "USBHost.h" +#include "FATFileSystem.h" + +/** + * A class to communicate a USB flash disk + */ +class USBHostMSD : public IUSBEnumerator, public FATFileSystem { +public: + /** + * Constructor + * + * @param rootdir mount name + */ + USBHostMSD(const char * rootdir); + + /** + * Check if a MSD device is connected + * + * @return true if a MSD device is connected + */ + bool connected(); + + /** + * Try to connect to a MSD device + * + * @return true if connection was successful + */ + bool connect(); + +protected: + //From IUSBEnumerator + virtual void setVidPid(uint16_t vid, uint16_t pid); + virtual bool parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol); //Must return true if the interface should be parsed + virtual bool useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir); //Must return true if the endpoint will be used + + // From FATFileSystem + virtual int disk_initialize(); + virtual int disk_status() {return 0;}; + virtual int disk_read(uint8_t* buffer, uint32_t sector, uint32_t count); + virtual int disk_write(const uint8_t* buffer, uint32_t sector, uint32_t count); + virtual int disk_sync() {return 0;}; + virtual uint32_t disk_sectors(); + +private: + USBHost * host; + USBDeviceConnected * dev; + bool dev_connected; + USBEndpoint * bulk_in; + USBEndpoint * bulk_out; + uint8_t nb_ep; + + // Bulk-only CBW + typedef struct { + uint32_t Signature; + uint32_t Tag; + uint32_t DataLength; + uint8_t Flags; + uint8_t LUN; + uint8_t CBLength; + uint8_t CB[16]; + } PACKED CBW; + + // Bulk-only CSW + typedef struct { + uint32_t Signature; + uint32_t Tag; + uint32_t DataResidue; + uint8_t Status; + } PACKED CSW; + + CBW cbw; + CSW csw; + + int SCSITransfer(uint8_t * cmd, uint8_t cmd_len, int flags, uint8_t * data, uint32_t transfer_len); + int testUnitReady(); + int readCapacity(); + int inquiry(uint8_t lun, uint8_t page_code); + int SCSIRequestSense(); + int dataTransfer(uint8_t * buf, uint32_t block, uint8_t nbBlock, int direction); + int checkResult(uint8_t res, USBEndpoint * ep); + int getMaxLun(); + + int blockSize; + uint32_t blockCount; + + int msd_intf; + bool msd_device_found; + bool disk_init; + + void init(); + +}; + +#endif + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostSerial/MtxCircBuffer.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,89 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 MTXCIRCBUFFER_H +#define MTXCIRCBUFFER_H + +#include "stdint.h" +#include "rtos.h" + +//Mutex protected circular buffer +template<typename T, int size> +class MtxCircBuffer { +public: + + MtxCircBuffer() { + write = 0; + read = 0; + } + + bool isFull() { + mtx.lock(); + bool r = (((write + 1) % size) == read); + mtx.unlock(); + return r; + } + + bool isEmpty() { + mtx.lock(); + bool r = (read == write); + mtx.unlock(); + return r; + } + + void flush() { + write = 0; + read = 0; + } + + void queue(T k) { + mtx.lock(); + while (((write + 1) % size) == read) { + mtx.unlock(); + Thread::wait(10); + mtx.lock(); + } + buf[write++] = k; + write %= size; + mtx.unlock(); + } + + uint16_t available() { + mtx.lock(); + uint16_t a = (write >= read) ? (write - read) : (size - read + write); + mtx.unlock(); + return a; + } + + bool dequeue(T * c) { + mtx.lock(); + bool empty = (read == write); + if (!empty) { + *c = buf[read++]; + read %= size; + } + mtx.unlock(); + return (!empty); + } + +private: + volatile uint16_t write; + volatile uint16_t read; + volatile T buf[size]; + Mutex mtx; +}; + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostSerial/USBHostSerial.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,345 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 "USBHostSerial.h" + +#if USBHOST_SERIAL + +#include "dbg.h" + +#define CHECK_INTERFACE(cls,subcls,proto) \ + (((cls == 0xFF) && (subcls == 0xFF) && (proto == 0xFF)) /* QUALCOM CDC */ || \ + ((cls == SERIAL_CLASS) && (subcls == 0x00) && (proto == 0x00)) /* STANDARD CDC */ ) + +#if (USBHOST_SERIAL <= 1) + +USBHostSerial::USBHostSerial() +{ + host = USBHost::getHostInst(); + ports_found = 0; + dev_connected = false; +} + +bool USBHostSerial::connected() +{ + return dev_connected; +} + +void USBHostSerial::disconnect(void) +{ + ports_found = 0; + dev = NULL; +} + +bool USBHostSerial::connect() { + + if (dev) + { + for (uint8_t i = 0; i < MAX_DEVICE_CONNECTED; i++) + { + USBDeviceConnected* d = host->getDevice(i); + if (dev == d) + return true; + } + disconnect(); + } + for (uint8_t i = 0; i < MAX_DEVICE_CONNECTED; i++) + { + USBDeviceConnected* d = host->getDevice(i); + if (d != NULL) { + + USB_DBG("Trying to connect serial device \r\n"); + if(host->enumerate(d, this)) + break; + + USBEndpoint* bulk_in = d->getEndpoint(port_intf, BULK_ENDPOINT, IN); + USBEndpoint* bulk_out = d->getEndpoint(port_intf, BULK_ENDPOINT, OUT); + if (bulk_in && bulk_out) + { + USBHostSerialPort::connect(host,d,port_intf,bulk_in, bulk_out); + dev = d; + dev_connected = true; + } + } + } + return dev != NULL; +} + +/*virtual*/ void USBHostSerial::setVidPid(uint16_t vid, uint16_t pid) +{ + // we don't check VID/PID for MSD driver +} + +/*virtual*/ bool USBHostSerial::parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) //Must return true if the interface should be parsed +{ + if (!ports_found && + CHECK_INTERFACE(intf_class, intf_subclass, intf_protocol)) { + port_intf = intf_nb; + ports_found = true; + return true; + } + return false; +} + +/*virtual*/ bool USBHostSerial::useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir) //Must return true if the endpoint will be used +{ + if (ports_found && (intf_nb == port_intf)) { + if (type == BULK_ENDPOINT) + return true; + } + return false; +} + +#else // (USBHOST_SERIAL > 1) + +//------------------------------------------------------------------------------ + +USBHostMultiSerial::USBHostMultiSerial() +{ + host = USBHost::getHostInst(); + dev = NULL; + memset(ports, NULL, sizeof(ports)); + ports_found = 0; + dev_connected = false; +} + +USBHostMultiSerial::~USBHostMultiSerial() +{ + disconnect(); +} + +bool USBHostMultiSerial::connected() +{ + return dev_connected; +} + +void USBHostMultiSerial::disconnect(void) +{ + for (int port = 0; port < USBHOST_SERIAL; port ++) + { + if (ports[port]) + { + delete ports[port]; + ports[port] = NULL; + } + } + ports_found = 0; + dev = NULL; +} + +bool USBHostMultiSerial::connect() { + + if (dev) + { + for (uint8_t i = 0; i < MAX_DEVICE_CONNECTED; i++) + { + USBDeviceConnected* d = host->getDevice(i); + if (dev == d) + return true; + } + disconnect(); + } + for (uint8_t i = 0; i < MAX_DEVICE_CONNECTED; i++) + { + USBDeviceConnected* d = host->getDevice(i); + if (d != NULL) { + + USB_DBG("Trying to connect serial device \r\n"); + if(host->enumerate(d, this)) + break; + + for (int port = 0; port < ports_found; port ++) + { + USBEndpoint* bulk_in = d->getEndpoint(port_intf[port], BULK_ENDPOINT, IN); + USBEndpoint* bulk_out = d->getEndpoint(port_intf[port], BULK_ENDPOINT, OUT); + if (bulk_in && bulk_out) + { + ports[port] = new USBHostSerialPort(); + if (ports[port]) + { + ports[port]->connect(host,d,port_intf[port],bulk_in, bulk_out); + dev = d; + dev_connected = true; + } + } + } + } + } + return dev != NULL; +} + +/*virtual*/ void USBHostMultiSerial::setVidPid(uint16_t vid, uint16_t pid) +{ + // we don't check VID/PID for MSD driver +} + +/*virtual*/ bool USBHostMultiSerial::parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) //Must return true if the interface should be parsed +{ + if ((ports_found < USBHOST_SERIAL) && + CHECK_INTERFACE(intf_class, intf_subclass, intf_protocol)) { + port_intf[ports_found++] = intf_nb; + return true; + } + return false; +} + +/*virtual*/ bool USBHostMultiSerial::useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir) //Must return true if the endpoint will be used +{ + if ((ports_found > 0) && (intf_nb == port_intf[ports_found-1])) { + if (type == BULK_ENDPOINT) + return true; + } + return false; +} + +#endif + +//------------------------------------------------------------------------------ + +#define SET_LINE_CODING 0x20 + +USBHostSerialPort::USBHostSerialPort(): circ_buf() +{ + init(); +} + +void USBHostSerialPort::init(void) +{ + host = NULL; + dev = NULL; + serial_intf = NULL; + size_bulk_in = 0; + size_bulk_out = 0; + bulk_in = NULL; + bulk_out = NULL; + line_coding.baudrate = 9600; + line_coding.data_bits = 8; + line_coding.parity = None; + line_coding.stop_bits = 1; + circ_buf.flush(); +} + +void USBHostSerialPort::connect(USBHost* _host, USBDeviceConnected * _dev, + uint8_t _serial_intf, USBEndpoint* _bulk_in, USBEndpoint* _bulk_out) +{ + host = _host; + dev = _dev; + serial_intf = _serial_intf; + bulk_in = _bulk_in; + bulk_out = _bulk_out; + + USB_INFO("New Serial device: VID:%04x PID:%04x [dev: %p - intf: %d]", dev->getVid(), dev->getPid(), dev, serial_intf); + dev->setName("Serial", serial_intf); + host->registerDriver(dev, serial_intf, this, &USBHostSerialPort::init); + baud(9600); + size_bulk_in = bulk_in->getSize(); + size_bulk_out = bulk_out->getSize(); + bulk_in->attach(this, &USBHostSerialPort::rxHandler); + bulk_out->attach(this, &USBHostSerialPort::txHandler); + host->bulkRead(dev, bulk_in, buf, size_bulk_in, false); +} + +void USBHostSerialPort::rxHandler() { + if (bulk_in) { + int len = bulk_in->getLengthTransferred(); + if (bulk_in->getState() == USB_TYPE_IDLE) { + for (int i = 0; i < len; i++) { + circ_buf.queue(buf[i]); + } + rx.call(); + host->bulkRead(dev, bulk_in, buf, size_bulk_in, false); + } + } +} + +void USBHostSerialPort::txHandler() { + if (bulk_out) { + if (bulk_out->getState() == USB_TYPE_IDLE) { + tx.call(); + } + } +} + +int USBHostSerialPort::_putc(int c) { + if (bulk_out) { + if (host->bulkWrite(dev, bulk_out, (uint8_t *)&c, 1) == USB_TYPE_OK) { + return 1; + } + } + return -1; +} + +void USBHostSerialPort::baud(int baudrate) { + line_coding.baudrate = baudrate; + format(line_coding.data_bits, (Parity)line_coding.parity, line_coding.stop_bits); +} + +void USBHostSerialPort::format(int bits, Parity parity, int stop_bits) { + line_coding.data_bits = bits; + line_coding.parity = parity; + line_coding.stop_bits = (stop_bits == 1) ? 0 : 2; + + // set line coding + host->controlWrite( dev, + USB_RECIPIENT_INTERFACE | USB_HOST_TO_DEVICE | USB_REQUEST_TYPE_CLASS, + SET_LINE_CODING, + 0, serial_intf, (uint8_t *)&line_coding, 7); +} + +int USBHostSerialPort::_getc() { + uint8_t c = 0; + if (bulk_in == NULL) { + init(); + return -1; + } + while (circ_buf.isEmpty()); + circ_buf.dequeue(&c); + return c; +} + +int USBHostSerialPort::writeBuf(const char* b, int s) +{ + int c = 0; + if (bulk_out) + { + while (c < s) + { + int i = (s < size_bulk_out) ? s : size_bulk_out; + if (host->bulkWrite(dev, bulk_out, (uint8_t *)(b+c), i) == USB_TYPE_OK) + c += i; + } + } + return s; +} + +int USBHostSerialPort::readBuf(char* b, int s) +{ + int i = 0; + if (bulk_in) + { + for (i = 0; i < s; ) + b[i++] = getc(); + } + return i; +} + +uint8_t USBHostSerialPort::available() { + return circ_buf.available(); +} + + + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/USBHostSerial/USBHostSerial.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,232 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBHOSTSERIAL_H +#define USBHOSTSERIAL_H + +#include "USBHostConf.h" + +#if USBHOST_SERIAL + +#include "USBHost.h" +#include "Stream.h" +#include "MtxCircBuffer.h" +#include "Callback.h" + +/** + * A class to communicate a USB virtual serial port + */ +class USBHostSerialPort : public Stream { +public: + /** + * Constructor + */ + USBHostSerialPort(); + + enum IrqType { + RxIrq, + TxIrq + }; + + enum Parity { + None = 0, + Odd, + Even, + Mark, + Space + }; + + void connect(USBHost* _host, USBDeviceConnected * _dev, + uint8_t _serial_intf, USBEndpoint* _bulk_in, USBEndpoint* _bulk_out); + + /** + * Check the number of bytes available. + * + * @returns the number of bytes available + */ + uint8_t available(); + + /** + * Attach a member function to call when a packet is received. + * + * @param tptr pointer to the object to call the member function on + * @param mptr pointer to the member function to be called + * @param irq irq type + */ + template<typename T> + inline void attach(T* tptr, void (T::*mptr)(void), IrqType irq = RxIrq) { + if ((mptr != NULL) && (tptr != NULL)) { + if (irq == RxIrq) { + rx.attach(tptr, mptr); + } else { + tx.attach(tptr, mptr); + } + } + } + + /** + * Attach a callback called when a packet is received + * + * @param ptr function pointer + */ + inline void attach(void (*fn)(void), IrqType irq = RxIrq) { + if (fn != NULL) { + if (irq == RxIrq) { + rx.attach(fn); + } else { + tx.attach(fn); + } + } + } + + /** Set the baud rate of the serial port + * + * @param baudrate The baudrate of the serial port (default = 9600). + */ + void baud(int baudrate = 9600); + + /** Set the transmission format used by the Serial port + * + * @param bits The number of bits in a word (default = 8) + * @param parity The parity used (USBHostSerialPort::None, USBHostSerialPort::Odd, USBHostSerialPort::Even, USBHostSerialPort::Mark, USBHostSerialPort::Space; default = USBHostSerialPort::None) + * @param stop The number of stop bits (1 or 2; default = 1) + */ + void format(int bits = 8, Parity parity = USBHostSerialPort::None, int stop_bits = 1); + virtual int writeBuf(const char* b, int s); + virtual int readBuf(char* b, int s); + +protected: + virtual int _getc(); + virtual int _putc(int c); + +private: + USBHost * host; + USBDeviceConnected * dev; + + USBEndpoint * bulk_in; + USBEndpoint * bulk_out; + uint32_t size_bulk_in; + uint32_t size_bulk_out; + + void init(); + + MtxCircBuffer<uint8_t, 128> circ_buf; + + uint8_t buf[64]; + + typedef struct { + uint32_t baudrate; + uint8_t stop_bits; + uint8_t parity; + uint8_t data_bits; + } PACKED LINE_CODING; + + LINE_CODING line_coding; + + void rxHandler(); + void txHandler(); + Callback<void()> rx; + Callback<void()> tx; + + uint8_t serial_intf; +}; + +#if (USBHOST_SERIAL <= 1) + +class USBHostSerial : public IUSBEnumerator, public USBHostSerialPort +{ +public: + USBHostSerial(); + + /** + * Try to connect a serial device + * + * @return true if connection was successful + */ + bool connect(); + + void disconnect(); + + /** + * Check if a any serial port is connected + * + * @returns true if a serial device is connected + */ + bool connected(); + +protected: + USBHost* host; + USBDeviceConnected* dev; + uint8_t port_intf; + int ports_found; + + //From IUSBEnumerator + virtual void setVidPid(uint16_t vid, uint16_t pid); + virtual bool parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol); //Must return true if the interface should be parsed + virtual bool useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir); //Must return true if the endpoint will be used + +private: + bool dev_connected; +}; + +#else // (USBHOST_SERIAL > 1) + +class USBHostMultiSerial : public IUSBEnumerator { +public: + USBHostMultiSerial(); + virtual ~USBHostMultiSerial(); + + USBHostSerialPort* getPort(int port) + { + return port < USBHOST_SERIAL ? ports[port] : NULL; + } + + /** + * Try to connect a serial device + * + * @return true if connection was successful + */ + bool connect(); + + void disconnect(); + + /** + * Check if a any serial port is connected + * + * @returns true if a serial device is connected + */ + bool connected(); + +protected: + USBHost* host; + USBDeviceConnected* dev; + USBHostSerialPort* ports[USBHOST_SERIAL]; + uint8_t port_intf[USBHOST_SERIAL]; + int ports_found; + + //From IUSBEnumerator + virtual void setVidPid(uint16_t vid, uint16_t pid); + virtual bool parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol); //Must return true if the interface should be parsed + virtual bool useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir); //Must return true if the endpoint will be used + +private: + bool dev_connected; +}; +#endif // (USBHOST_SERIAL <= 1) + +#endif + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/mbed-rtos.lib Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/mbed_official/code/mbed-rtos/#5713cbbdb706
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_NUVOTON/TARGET_M451/USBHALHost_M451.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,347 @@ +/* mbed Microcontroller Library + * Copyright (c) 2015-2016 Nuvoton + * + * 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(TARGET_M451) + +#include "mbed.h" +#include "USBHALHost.h" +#include "dbg.h" +#include "pinmap.h" + +#define HCCA_SIZE sizeof(HCCA) +#define ED_SIZE sizeof(HCED) +#define TD_SIZE sizeof(HCTD) + +#define TOTAL_SIZE (HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE) + (MAX_TD*TD_SIZE)) + +#ifndef USBH_HcRhDescriptorA_POTPGT_Pos +#define USBH_HcRhDescriptorA_POTPGT_Pos (24) +#endif +#ifndef USBH_HcRhDescriptorA_POTPGT_Msk +#define USBH_HcRhDescriptorA_POTPGT_Msk (0xfful << USBH_HcRhDescriptorA_POTPGT_Pos) +#endif + +static volatile MBED_ALIGN(256) uint8_t usb_buf[TOTAL_SIZE]; // 256 bytes aligned! + +USBHALHost * USBHALHost::instHost; + +USBHALHost::USBHALHost() +{ + instHost = this; + memInit(); + memset((void*)usb_hcca, 0, HCCA_SIZE); + for (int i = 0; i < MAX_ENDPOINT; i++) { + edBufAlloc[i] = false; + } + for (int i = 0; i < MAX_TD; i++) { + tdBufAlloc[i] = false; + } +} + +void USBHALHost::init() +{ + // Unlock protected registers + SYS_UnlockReg(); + + // Enable USBH clock + CLK_EnableModuleClock(USBH_MODULE); + // Set USBH clock source/divider + CLK_SetModuleClock(USBH_MODULE, 0, CLK_CLKDIV0_USB(3)); + + // Configure OTG function as Host-Only + SYS->USBPHY = SYS_USBPHY_LDO33EN_Msk | SYS_USBPHY_USBROLE_STD_USBH; + + /* Below settings is use power switch IC to enable/disable USB Host power. + Set PA.2 is VBUS_EN function pin and PA.3 VBUS_ST function pin */ + pin_function(PA_3, SYS_GPA_MFPL_PA3MFP_USB_VBUS_ST); + pin_function(PA_2, SYS_GPA_MFPL_PA2MFP_USB_VBUS_EN); + + // Enable OTG clock + CLK_EnableModuleClock(OTG_MODULE); + + // Lock protected registers + SYS_LockReg(); + + // Overcurrent flag is low active + USBH->HcMiscControl |= USBH_HcMiscControl_OCAL_Msk; + + // Disable HC interrupts + USBH->HcInterruptDisable = OR_INTR_ENABLE_MIE; + + // Needed by some controllers + USBH->HcControl = 0; + + // Software reset + USBH->HcCommandStatus = OR_CMD_STATUS_HCR; + while (USBH->HcCommandStatus & OR_CMD_STATUS_HCR); + + // Put HC in reset state + USBH->HcControl = (USBH->HcControl & ~OR_CONTROL_HCFS) | OR_CONTROL_HC_RSET; + // HCD must wait 10ms for HC reset complete + wait_ms(100); + + USBH->HcControlHeadED = 0; // Initialize Control ED list head to 0 + USBH->HcBulkHeadED = 0; // Initialize Bulk ED list head to 0 + USBH->HcHCCA = (uint32_t) usb_hcca; + + USBH->HcFmInterval = DEFAULT_FMINTERVAL; // Frame interval = 12000 - 1 + // MPS = 10,104 + USBH->HcPeriodicStart = FI * 90 / 100; // 90% of frame interval + USBH->HcLSThreshold = 0x628; // Low speed threshold + + // Put HC in operational state + USBH->HcControl = (USBH->HcControl & (~OR_CONTROL_HCFS)) | OR_CONTROL_HC_OPER; + + // FIXME + USBH->HcRhDescriptorA = USBH->HcRhDescriptorA & ~(USBH_HcRhDescriptorA_NOCP_Msk | USBH_HcRhDescriptorA_OCPM_Msk | USBH_HcRhDescriptorA_PSM_Msk); + // Issue SetGlobalPower command + USBH->HcRhStatus = USBH_HcRhStatus_LPSC_Msk; + // Power On To Power Good Time, in 2 ms units + wait_ms(((USBH->HcRhDescriptorA & USBH_HcRhDescriptorA_POTPGT_Msk) >> USBH_HcRhDescriptorA_POTPGT_Pos) * 2); + + // Clear Interrrupt Status + USBH->HcInterruptStatus |= USBH->HcInterruptStatus; + // Enable interrupts we care about + USBH->HcInterruptEnable = OR_INTR_ENABLE_MIE | OR_INTR_ENABLE_WDH | OR_INTR_ENABLE_RHSC; + + NVIC_SetVector(USBH_IRQn, (uint32_t)(_usbisr)); + NVIC_EnableIRQ(USBH_IRQn); + + // Check for any connected devices + if (USBH->HcRhPortStatus[0] & OR_RH_PORT_CCS) { + // Device connected + wait_ms(150); + deviceConnected(0, 1, USBH->HcRhPortStatus[0] & OR_RH_PORT_LSDA); + } +} + +uint32_t USBHALHost::controlHeadED() +{ + return USBH->HcControlHeadED; +} + +uint32_t USBHALHost::bulkHeadED() +{ + return USBH->HcBulkHeadED; +} + +uint32_t USBHALHost::interruptHeadED() +{ + // FIXME: Only support one INT ED? + return usb_hcca->IntTable[0]; +} + +void USBHALHost::updateBulkHeadED(uint32_t addr) +{ + USBH->HcBulkHeadED = addr; +} + + +void USBHALHost::updateControlHeadED(uint32_t addr) +{ + USBH->HcControlHeadED = addr; +} + +void USBHALHost::updateInterruptHeadED(uint32_t addr) +{ + // FIXME: Only support one INT ED? + usb_hcca->IntTable[0] = addr; +} + + +void USBHALHost::enableList(ENDPOINT_TYPE type) +{ + switch(type) { + case CONTROL_ENDPOINT: + USBH->HcCommandStatus = OR_CMD_STATUS_CLF; + USBH->HcControl |= OR_CONTROL_CLE; + break; + case ISOCHRONOUS_ENDPOINT: + // FIXME + break; + case BULK_ENDPOINT: + USBH->HcCommandStatus = OR_CMD_STATUS_BLF; + USBH->HcControl |= OR_CONTROL_BLE; + break; + case INTERRUPT_ENDPOINT: + USBH->HcControl |= OR_CONTROL_PLE; + break; + } +} + + +bool USBHALHost::disableList(ENDPOINT_TYPE type) +{ + switch(type) { + case CONTROL_ENDPOINT: + if(USBH->HcControl & OR_CONTROL_CLE) { + USBH->HcControl &= ~OR_CONTROL_CLE; + return true; + } + return false; + case ISOCHRONOUS_ENDPOINT: + // FIXME + return false; + case BULK_ENDPOINT: + if(USBH->HcControl & OR_CONTROL_BLE){ + USBH->HcControl &= ~OR_CONTROL_BLE; + return true; + } + return false; + case INTERRUPT_ENDPOINT: + if(USBH->HcControl & OR_CONTROL_PLE) { + USBH->HcControl &= ~OR_CONTROL_PLE; + return true; + } + return false; + } + return false; +} + + +void USBHALHost::memInit() +{ + usb_hcca = (volatile HCCA *)usb_buf; + usb_edBuf = usb_buf + HCCA_SIZE; + usb_tdBuf = usb_buf + HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE); +} + +volatile uint8_t * USBHALHost::getED() +{ + for (int i = 0; i < MAX_ENDPOINT; i++) { + if ( !edBufAlloc[i] ) { + edBufAlloc[i] = true; + return (volatile uint8_t *)(usb_edBuf + i*ED_SIZE); + } + } + perror("Could not allocate ED\r\n"); + return NULL; //Could not alloc ED +} + +volatile uint8_t * USBHALHost::getTD() +{ + int i; + for (i = 0; i < MAX_TD; i++) { + if ( !tdBufAlloc[i] ) { + tdBufAlloc[i] = true; + return (volatile uint8_t *)(usb_tdBuf + i*TD_SIZE); + } + } + perror("Could not allocate TD\r\n"); + return NULL; //Could not alloc TD +} + + +void USBHALHost::freeED(volatile uint8_t * ed) +{ + int i; + i = (ed - usb_edBuf) / ED_SIZE; + edBufAlloc[i] = false; +} + +void USBHALHost::freeTD(volatile uint8_t * td) +{ + int i; + i = (td - usb_tdBuf) / TD_SIZE; + tdBufAlloc[i] = false; +} + + +void USBHALHost::resetRootHub() +{ + // Reset port1 + USBH->HcRhPortStatus[0] = OR_RH_PORT_PRS; + while (USBH->HcRhPortStatus[0] & OR_RH_PORT_PRS); + USBH->HcRhPortStatus[0] = OR_RH_PORT_PRSC; +} + + +void USBHALHost::_usbisr(void) +{ + if (instHost) { + instHost->UsbIrqhandler(); + } +} + +void USBHALHost::UsbIrqhandler() +{ + uint32_t ints = USBH->HcInterruptStatus; + + // Root hub status change interrupt + if (ints & OR_INTR_STATUS_RHSC) { + uint32_t ints_roothub = USBH->HcRhStatus; + uint32_t ints_port1 = USBH->HcRhPortStatus[0]; + uint32_t ints_port2 = USBH->HcRhPortStatus[1]; + + // Port1: ConnectStatusChange + if (ints_port1 & OR_RH_PORT_CSC) { + if (ints_roothub & OR_RH_STATUS_DRWE) { + // When DRWE is on, Connect Status Change means a remote wakeup event. + } else { + if (ints_port1 & OR_RH_PORT_CCS) { + // Root device connected + + // wait 150ms to avoid bounce + wait_ms(150); + + //Hub 0 (root hub), Port 1 (count starts at 1), Low or High speed + deviceConnected(0, 1, ints_port1 & OR_RH_PORT_LSDA); + } else { + // Root device disconnected + + if (!(ints & OR_INTR_STATUS_WDH)) { + usb_hcca->DoneHead = 0; + } + + // wait 200ms to avoid bounce + wait_ms(200); + + deviceDisconnected(0, 1, NULL, usb_hcca->DoneHead & 0xFFFFFFFE); + + if (ints & OR_INTR_STATUS_WDH) { + usb_hcca->DoneHead = 0; + USBH->HcInterruptStatus = OR_INTR_STATUS_WDH; + } + } + } + USBH->HcRhPortStatus[0] = OR_RH_PORT_CSC; + } + // Port1: Reset completed + if (ints_port1 & OR_RH_PORT_PRSC) { + USBH->HcRhPortStatus[0] = OR_RH_PORT_PRSC; + } + // Port1: PortEnableStatusChange + if (ints_port1 & OR_RH_PORT_PESC) { + USBH->HcRhPortStatus[0] = OR_RH_PORT_PESC; + } + + // Port2: PortOverCurrentIndicatorChange + if (ints_port2 & OR_RH_PORT_OCIC) { + USBH->HcRhPortStatus[1] = OR_RH_PORT_OCIC; + } + + USBH->HcInterruptStatus = OR_INTR_STATUS_RHSC; + } + + // Writeback Done Head interrupt + if (ints & OR_INTR_STATUS_WDH) { + transferCompleted(usb_hcca->DoneHead & 0xFFFFFFFE); + USBH->HcInterruptStatus = OR_INTR_STATUS_WDH; + } + + +} +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_NUVOTON/TARGET_NUC472/USBHALHost_NUC472.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,365 @@ +/* mbed Microcontroller Library + * Copyright (c) 2015-2016 Nuvoton + * + * 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(TARGET_NUC472) + +#include "mbed.h" +#include "USBHALHost.h" +#include "dbg.h" +#include "pinmap.h" + +#define HCCA_SIZE sizeof(HCCA) +#define ED_SIZE sizeof(HCED) +#define TD_SIZE sizeof(HCTD) + +#define TOTAL_SIZE (HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE) + (MAX_TD*TD_SIZE)) + +static volatile MBED_ALIGN(256) uint8_t usb_buf[TOTAL_SIZE]; // 256 bytes aligned! + +USBHALHost * USBHALHost::instHost; + +USBHALHost::USBHALHost() +{ + instHost = this; + memInit(); + memset((void*)usb_hcca, 0, HCCA_SIZE); + for (int i = 0; i < MAX_ENDPOINT; i++) { + edBufAlloc[i] = false; + } + for (int i = 0; i < MAX_TD; i++) { + tdBufAlloc[i] = false; + } +} + +void USBHALHost::init() +{ + // Unlock protected registers + SYS_UnlockReg(); + + // NOTE: Configure as OTG device first; otherwise, program will trap in wait loop CLK_STATUS_PLL2STB_Msk below. + SYS->USBPHY = SYS_USBPHY_LDO33EN_Msk | SYS_USBPHY_USBROLE_ON_THE_GO; + + // NOTE: Enable OTG here; otherwise, program will trap in wait loop CLK_STATUS_PLL2STB_Msk below. + CLK_EnableModuleClock(OTG_MODULE); + OTG->PHYCTL = (OTG->PHYCTL | OTG_PHYCTL_OTGPHYEN_Msk) & ~OTG_PHYCTL_IDDETEN_Msk; + //OTG->CTL |= OTG_CTL_OTGEN_Msk | OTG_CTL_BUSREQ_Msk; + + // PB.0: USB0 external VBUS regulator status + // USB_OC + // PB.1: USB0 external VBUS regulator enable + // NCT3520U low active (USB_PWR_EN) + pin_function(PB_0, SYS_GPB_MFPL_PB0MFP_USB0_OTG5V_ST); + pin_function(PB_1, SYS_GPB_MFPL_PB1MFP_USB0_OTG5V_EN); + + // PB.2: USB1 differential signal D- + // PB.3: USB1 differential signal D+ + //pin_function(PB_2, SYS_GPB_MFPL_PB2MFP_USB1_D_N); + //pin_function(PB_3, SYS_GPB_MFPL_PB3MFP_USB1_D_P); + + // Set PB.4 output high to enable USB power + //gpio_t gpio; + //gpio_init_out_ex(&gpio, PB_4, 1); + + // NOTE: + // 1. Set USBH clock source to PLL2; otherwise, program will trap in wait loop CLK_STATUS_PLL2STB_Msk below. + // 2. Don't set CLK_PLL2CTL_PLL2CKEN_Msk. USBH will work abnormally with it enabled. + CLK->CLKSEL0 &= ~CLK_CLKSEL0_USBHSEL_Msk; + // Enable PLL2, 480 MHz / 2 / (1+4) => 48 MHz output + CLK->PLL2CTL = /*CLK_PLL2CTL_PLL2CKEN_Msk | */ (4 << CLK_PLL2CTL_PLL2DIV_Pos); + // Wait PLL2 stable ... + while (!(CLK->STATUS & CLK_STATUS_PLL2STB_Msk)); + + // Select USB Host clock source from PLL2, clock divied by 1 + CLK_SetModuleClock(USBH_MODULE, CLK_CLKSEL0_USBHSEL_PLL2, CLK_CLKDIV0_USB(1)); + + // Enable USB Host clock + CLK_EnableModuleClock(USBH_MODULE); + + // Lock protected registers + SYS_LockReg(); + + // Overcurrent flag is high active + USBH->HcMiscControl &= ~USBH_HcMiscControl_OCAL_Msk; + + // Disable HC interrupts + USBH->HcInterruptDisable = OR_INTR_ENABLE_MIE; + + // Needed by some controllers + USBH->HcControl = 0; + + // Software reset + USBH->HcCommandStatus = OR_CMD_STATUS_HCR; + while (USBH->HcCommandStatus & OR_CMD_STATUS_HCR); + + // Put HC in reset state + USBH->HcControl = (USBH->HcControl & ~OR_CONTROL_HCFS) | OR_CONTROL_HC_RSET; + // HCD must wait 10ms for HC reset complete + wait_ms(100); + + USBH->HcControlHeadED = 0; // Initialize Control ED list head to 0 + USBH->HcBulkHeadED = 0; // Initialize Bulk ED list head to 0 + USBH->HcHCCA = (uint32_t) usb_hcca; + + USBH->HcFmInterval = DEFAULT_FMINTERVAL; // Frame interval = 12000 - 1 + // MPS = 10,104 + USBH->HcPeriodicStart = FI * 90 / 100; // 90% of frame interval + USBH->HcLSThreshold = 0x628; // Low speed threshold + + // Put HC in operational state + USBH->HcControl = (USBH->HcControl & (~OR_CONTROL_HCFS)) | OR_CONTROL_HC_OPER; + + // FIXME: Ports are power switched. All ports are powered at the same time. Doesn't match BSP sample. + USBH->HcRhDescriptorA = USBH->HcRhDescriptorA & ~USBH_HcRhDescriptorA_NPS_Msk & ~USBH_HcRhDescriptorA_PSM_Msk; + // Issue SetGlobalPower command + USBH->HcRhStatus = USBH_HcRhStatus_LPSC_Msk; + // Power On To Power Good Time, in 2 ms units + wait_ms(((USBH->HcRhDescriptorA & USBH_HcRhDescriptorA_POTPGT_Msk) >> USBH_HcRhDescriptorA_POTPGT_Pos) * 2); + + // Clear Interrrupt Status + USBH->HcInterruptStatus |= USBH->HcInterruptStatus; + // Enable interrupts we care about + USBH->HcInterruptEnable = OR_INTR_ENABLE_MIE | OR_INTR_ENABLE_WDH | OR_INTR_ENABLE_RHSC; + + + // Unlock protected registers + SYS_UnlockReg(); + + // NOTE: Configure as USB host after USBH init above; otherwise system will crash. + SYS->USBPHY = (SYS->USBPHY & ~SYS_USBPHY_USBROLE_Msk) | SYS_USBPHY_USBROLE_STD_USBH; + + // Lock protected registers + SYS_LockReg(); + + NVIC_SetVector(USBH_IRQn, (uint32_t)(_usbisr)); + NVIC_EnableIRQ(USBH_IRQn); + + // Check for any connected devices + if (USBH->HcRhPortStatus[0] & OR_RH_PORT_CCS) { + // Device connected + wait_ms(150); + deviceConnected(0, 1, USBH->HcRhPortStatus[0] & OR_RH_PORT_LSDA); + } +} + +uint32_t USBHALHost::controlHeadED() +{ + return USBH->HcControlHeadED; +} + +uint32_t USBHALHost::bulkHeadED() +{ + return USBH->HcBulkHeadED; +} + +uint32_t USBHALHost::interruptHeadED() +{ + // FIXME: Only support one INT ED? + return usb_hcca->IntTable[0]; +} + +void USBHALHost::updateBulkHeadED(uint32_t addr) +{ + USBH->HcBulkHeadED = addr; +} + + +void USBHALHost::updateControlHeadED(uint32_t addr) +{ + USBH->HcControlHeadED = addr; +} + +void USBHALHost::updateInterruptHeadED(uint32_t addr) +{ + // FIXME: Only support one INT ED? + usb_hcca->IntTable[0] = addr; +} + + +void USBHALHost::enableList(ENDPOINT_TYPE type) +{ + switch(type) { + case CONTROL_ENDPOINT: + USBH->HcCommandStatus = OR_CMD_STATUS_CLF; + USBH->HcControl |= OR_CONTROL_CLE; + break; + case ISOCHRONOUS_ENDPOINT: + // FIXME + break; + case BULK_ENDPOINT: + USBH->HcCommandStatus = OR_CMD_STATUS_BLF; + USBH->HcControl |= OR_CONTROL_BLE; + break; + case INTERRUPT_ENDPOINT: + USBH->HcControl |= OR_CONTROL_PLE; + break; + } +} + + +bool USBHALHost::disableList(ENDPOINT_TYPE type) +{ + switch(type) { + case CONTROL_ENDPOINT: + if(USBH->HcControl & OR_CONTROL_CLE) { + USBH->HcControl &= ~OR_CONTROL_CLE; + return true; + } + return false; + case ISOCHRONOUS_ENDPOINT: + // FIXME + return false; + case BULK_ENDPOINT: + if(USBH->HcControl & OR_CONTROL_BLE){ + USBH->HcControl &= ~OR_CONTROL_BLE; + return true; + } + return false; + case INTERRUPT_ENDPOINT: + if(USBH->HcControl & OR_CONTROL_PLE) { + USBH->HcControl &= ~OR_CONTROL_PLE; + return true; + } + return false; + } + return false; +} + + +void USBHALHost::memInit() +{ + usb_hcca = (volatile HCCA *)usb_buf; + usb_edBuf = usb_buf + HCCA_SIZE; + usb_tdBuf = usb_buf + HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE); +} + +volatile uint8_t * USBHALHost::getED() +{ + for (int i = 0; i < MAX_ENDPOINT; i++) { + if ( !edBufAlloc[i] ) { + edBufAlloc[i] = true; + return (volatile uint8_t *)(usb_edBuf + i*ED_SIZE); + } + } + perror("Could not allocate ED\r\n"); + return NULL; //Could not alloc ED +} + +volatile uint8_t * USBHALHost::getTD() +{ + int i; + for (i = 0; i < MAX_TD; i++) { + if ( !tdBufAlloc[i] ) { + tdBufAlloc[i] = true; + return (volatile uint8_t *)(usb_tdBuf + i*TD_SIZE); + } + } + perror("Could not allocate TD\r\n"); + return NULL; //Could not alloc TD +} + + +void USBHALHost::freeED(volatile uint8_t * ed) +{ + int i; + i = (ed - usb_edBuf) / ED_SIZE; + edBufAlloc[i] = false; +} + +void USBHALHost::freeTD(volatile uint8_t * td) +{ + int i; + i = (td - usb_tdBuf) / TD_SIZE; + tdBufAlloc[i] = false; +} + + +void USBHALHost::resetRootHub() +{ + // Reset port1 + USBH->HcRhPortStatus[0] = OR_RH_PORT_PRS; + while (USBH->HcRhPortStatus[0] & OR_RH_PORT_PRS); + USBH->HcRhPortStatus[0] = OR_RH_PORT_PRSC; +} + + +void USBHALHost::_usbisr(void) +{ + if (instHost) { + instHost->UsbIrqhandler(); + } +} + +void USBHALHost::UsbIrqhandler() +{ + uint32_t ints = USBH->HcInterruptStatus; + + // Root hub status change interrupt + if (ints & OR_INTR_STATUS_RHSC) { + uint32_t ints_roothub = USBH->HcRhStatus; + uint32_t ints_port1 = USBH->HcRhPortStatus[0]; + + // Port1: ConnectStatusChange + if (ints_port1 & OR_RH_PORT_CSC) { + if (ints_roothub & OR_RH_STATUS_DRWE) { + // When DRWE is on, Connect Status Change means a remote wakeup event. + } else { + if (ints_port1 & OR_RH_PORT_CCS) { + // Root device connected + + // wait 150ms to avoid bounce + wait_ms(150); + + //Hub 0 (root hub), Port 1 (count starts at 1), Low or High speed + deviceConnected(0, 1, ints_port1 & OR_RH_PORT_LSDA); + } else { + // Root device disconnected + + if (!(ints & OR_INTR_STATUS_WDH)) { + usb_hcca->DoneHead = 0; + } + + // wait 200ms to avoid bounce + wait_ms(200); + + deviceDisconnected(0, 1, NULL, usb_hcca->DoneHead & 0xFFFFFFFE); + + if (ints & OR_INTR_STATUS_WDH) { + usb_hcca->DoneHead = 0; + USBH->HcInterruptStatus = OR_INTR_STATUS_WDH; + } + } + } + USBH->HcRhPortStatus[0] = OR_RH_PORT_CSC; + } + // Port1: Reset completed + if (ints_port1 & OR_RH_PORT_PRSC) { + USBH->HcRhPortStatus[0] = OR_RH_PORT_PRSC; + } + // Port1: PortEnableStatusChange + if (ints_port1 & OR_RH_PORT_PESC) { + USBH->HcRhPortStatus[0] = OR_RH_PORT_PESC; + } + + USBH->HcInterruptStatus = OR_INTR_STATUS_RHSC; + } + + // Writeback Done Head interrupt + if (ints & OR_INTR_STATUS_WDH) { + transferCompleted(usb_hcca->DoneHead & 0xFFFFFFFE); + USBH->HcInterruptStatus = OR_INTR_STATUS_WDH; + } +} +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_NXP/USBHALHost_LPC17.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,325 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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(TARGET_LPC1768) || defined(TARGET_LPC2460) + +#include "mbed.h" +#include "USBHALHost.h" +#include "dbg.h" + +// bits of the USB/OTG clock control register +#define HOST_CLK_EN (1<<0) +#define DEV_CLK_EN (1<<1) +#define PORTSEL_CLK_EN (1<<3) +#define AHB_CLK_EN (1<<4) + +// bits of the USB/OTG clock status register +#define HOST_CLK_ON (1<<0) +#define DEV_CLK_ON (1<<1) +#define PORTSEL_CLK_ON (1<<3) +#define AHB_CLK_ON (1<<4) + +// we need host clock, OTG/portsel clock and AHB clock +#define CLOCK_MASK (HOST_CLK_EN | PORTSEL_CLK_EN | AHB_CLK_EN) + +#define HCCA_SIZE sizeof(HCCA) +#define ED_SIZE sizeof(HCED) +#define TD_SIZE sizeof(HCTD) + +#define TOTAL_SIZE (HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE) + (MAX_TD*TD_SIZE)) + +static volatile uint8_t usb_buf[TOTAL_SIZE] __attribute((section("AHBSRAM1"),aligned(256))); //256 bytes aligned! + +USBHALHost * USBHALHost::instHost; + +USBHALHost::USBHALHost() { + instHost = this; + memInit(); + memset((void*)usb_hcca, 0, HCCA_SIZE); + for (int i = 0; i < MAX_ENDPOINT; i++) { + edBufAlloc[i] = false; + } + for (int i = 0; i < MAX_TD; i++) { + tdBufAlloc[i] = false; + } +} + +void USBHALHost::init() { + NVIC_DisableIRQ(USB_IRQn); + + //Cut power + LPC_SC->PCONP &= ~(1UL<<31); + wait_ms(100); + + // turn on power for USB + LPC_SC->PCONP |= (1UL<<31); + + // Enable USB host clock, port selection and AHB clock + LPC_USB->USBClkCtrl |= CLOCK_MASK; + + // Wait for clocks to become available + while ((LPC_USB->USBClkSt & CLOCK_MASK) != CLOCK_MASK); + + // it seems the bits[0:1] mean the following + // 0: U1=device, U2=host + // 1: U1=host, U2=host + // 2: reserved + // 3: U1=host, U2=device + // NB: this register is only available if OTG clock (aka "port select") is enabled!! + // since we don't care about port 2, set just bit 0 to 1 (U1=host) + LPC_USB->OTGStCtrl |= 1; + + // now that we've configured the ports, we can turn off the portsel clock + LPC_USB->USBClkCtrl &= ~PORTSEL_CLK_EN; + + // configure USB D+/D- pins + // P0[29] = USB_D+, 01 + // P0[30] = USB_D-, 01 + LPC_PINCON->PINSEL1 &= ~((3<<26) | (3<<28)); + LPC_PINCON->PINSEL1 |= ((1<<26) | (1<<28)); + + LPC_USB->HcControl = 0; // HARDWARE RESET + LPC_USB->HcControlHeadED = 0; // Initialize Control list head to Zero + LPC_USB->HcBulkHeadED = 0; // Initialize Bulk list head to Zero + + // Wait 100 ms before apply reset + wait_ms(100); + + // software reset + LPC_USB->HcCommandStatus = OR_CMD_STATUS_HCR; + + // Write Fm Interval and Largest Data Packet Counter + LPC_USB->HcFmInterval = DEFAULT_FMINTERVAL; + LPC_USB->HcPeriodicStart = FI * 90 / 100; + + // Put HC in operational state + LPC_USB->HcControl = (LPC_USB->HcControl & (~OR_CONTROL_HCFS)) | OR_CONTROL_HC_OPER; + // Set Global Power + LPC_USB->HcRhStatus = OR_RH_STATUS_LPSC; + + LPC_USB->HcHCCA = (uint32_t)(usb_hcca); + + // Clear Interrrupt Status + LPC_USB->HcInterruptStatus |= LPC_USB->HcInterruptStatus; + + LPC_USB->HcInterruptEnable = OR_INTR_ENABLE_MIE | OR_INTR_ENABLE_WDH | OR_INTR_ENABLE_RHSC; + + // Enable the USB Interrupt + NVIC_SetVector(USB_IRQn, (uint32_t)(_usbisr)); + LPC_USB->HcRhPortStatus1 = OR_RH_PORT_CSC; + LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRSC; + + NVIC_EnableIRQ(USB_IRQn); + + // Check for any connected devices + if (LPC_USB->HcRhPortStatus1 & OR_RH_PORT_CCS) { + //Device connected + wait_ms(150); + USB_DBG("Device connected (%08x)\n\r", LPC_USB->HcRhPortStatus1); + deviceConnected(0, 1, LPC_USB->HcRhPortStatus1 & OR_RH_PORT_LSDA); + } +} + +uint32_t USBHALHost::controlHeadED() { + return LPC_USB->HcControlHeadED; +} + +uint32_t USBHALHost::bulkHeadED() { + return LPC_USB->HcBulkHeadED; +} + +uint32_t USBHALHost::interruptHeadED() { + return usb_hcca->IntTable[0]; +} + +void USBHALHost::updateBulkHeadED(uint32_t addr) { + LPC_USB->HcBulkHeadED = addr; +} + + +void USBHALHost::updateControlHeadED(uint32_t addr) { + LPC_USB->HcControlHeadED = addr; +} + +void USBHALHost::updateInterruptHeadED(uint32_t addr) { + usb_hcca->IntTable[0] = addr; +} + + +void USBHALHost::enableList(ENDPOINT_TYPE type) { + switch(type) { + case CONTROL_ENDPOINT: + LPC_USB->HcCommandStatus = OR_CMD_STATUS_CLF; + LPC_USB->HcControl |= OR_CONTROL_CLE; + break; + case ISOCHRONOUS_ENDPOINT: + break; + case BULK_ENDPOINT: + LPC_USB->HcCommandStatus = OR_CMD_STATUS_BLF; + LPC_USB->HcControl |= OR_CONTROL_BLE; + break; + case INTERRUPT_ENDPOINT: + LPC_USB->HcControl |= OR_CONTROL_PLE; + break; + } +} + + +bool USBHALHost::disableList(ENDPOINT_TYPE type) { + switch(type) { + case CONTROL_ENDPOINT: + if(LPC_USB->HcControl & OR_CONTROL_CLE) { + LPC_USB->HcControl &= ~OR_CONTROL_CLE; + return true; + } + return false; + case ISOCHRONOUS_ENDPOINT: + return false; + case BULK_ENDPOINT: + if(LPC_USB->HcControl & OR_CONTROL_BLE){ + LPC_USB->HcControl &= ~OR_CONTROL_BLE; + return true; + } + return false; + case INTERRUPT_ENDPOINT: + if(LPC_USB->HcControl & OR_CONTROL_PLE) { + LPC_USB->HcControl &= ~OR_CONTROL_PLE; + return true; + } + return false; + } + return false; +} + + +void USBHALHost::memInit() { + usb_hcca = (volatile HCCA *)usb_buf; + usb_edBuf = usb_buf + HCCA_SIZE; + usb_tdBuf = usb_buf + HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE); +} + +volatile uint8_t * USBHALHost::getED() { + for (int i = 0; i < MAX_ENDPOINT; i++) { + if ( !edBufAlloc[i] ) { + edBufAlloc[i] = true; + return (volatile uint8_t *)(usb_edBuf + i*ED_SIZE); + } + } + perror("Could not allocate ED\r\n"); + return NULL; //Could not alloc ED +} + +volatile uint8_t * USBHALHost::getTD() { + int i; + for (i = 0; i < MAX_TD; i++) { + if ( !tdBufAlloc[i] ) { + tdBufAlloc[i] = true; + return (volatile uint8_t *)(usb_tdBuf + i*TD_SIZE); + } + } + perror("Could not allocate TD\r\n"); + return NULL; //Could not alloc TD +} + + +void USBHALHost::freeED(volatile uint8_t * ed) { + int i; + i = (ed - usb_edBuf) / ED_SIZE; + edBufAlloc[i] = false; +} + +void USBHALHost::freeTD(volatile uint8_t * td) { + int i; + i = (td - usb_tdBuf) / TD_SIZE; + tdBufAlloc[i] = false; +} + + +void USBHALHost::resetRootHub() { + // Initiate port reset + LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRS; + + while (LPC_USB->HcRhPortStatus1 & OR_RH_PORT_PRS); + + // ...and clear port reset signal + LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRSC; +} + + +void USBHALHost::_usbisr(void) { + if (instHost) { + instHost->UsbIrqhandler(); + } +} + +void USBHALHost::UsbIrqhandler() { + if( LPC_USB->HcInterruptStatus & LPC_USB->HcInterruptEnable ) //Is there something to actually process? + { + + uint32_t int_status = LPC_USB->HcInterruptStatus & LPC_USB->HcInterruptEnable; + + // Root hub status change interrupt + if (int_status & OR_INTR_STATUS_RHSC) { + if (LPC_USB->HcRhPortStatus1 & OR_RH_PORT_CSC) { + if (LPC_USB->HcRhStatus & OR_RH_STATUS_DRWE) { + // When DRWE is on, Connect Status Change + // means a remote wakeup event. + } else { + + //Root device connected + if (LPC_USB->HcRhPortStatus1 & OR_RH_PORT_CCS) { + + // wait 150ms to avoid bounce + wait_ms(150); + + //Hub 0 (root hub), Port 1 (count starts at 1), Low or High speed + deviceConnected(0, 1, LPC_USB->HcRhPortStatus1 & OR_RH_PORT_LSDA); + } + + //Root device disconnected + else { + + if (!(int_status & OR_INTR_STATUS_WDH)) { + usb_hcca->DoneHead = 0; + } + + // wait 200ms to avoid bounce + wait_ms(200); + + deviceDisconnected(0, 1, NULL, usb_hcca->DoneHead & 0xFFFFFFFE); + + if (int_status & OR_INTR_STATUS_WDH) { + usb_hcca->DoneHead = 0; + LPC_USB->HcInterruptStatus = OR_INTR_STATUS_WDH; + } + } + } + LPC_USB->HcRhPortStatus1 = OR_RH_PORT_CSC; + } + if (LPC_USB->HcRhPortStatus1 & OR_RH_PORT_PRSC) { + LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRSC; + } + LPC_USB->HcInterruptStatus = OR_INTR_STATUS_RHSC; + } + + // Writeback Done Head interrupt + if (int_status & OR_INTR_STATUS_WDH) { + transferCompleted(usb_hcca->DoneHead & 0xFFFFFFFE); + LPC_USB->HcInterruptStatus = OR_INTR_STATUS_WDH; + } + } +} +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/inc/devdrv_usb_host_api.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,329 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : devdrv_usb_host_api.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB_HOST_API_H +#define USB_HOST_API_H + +#include "r_typedefs.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define USB_HOST_PORTNUM (2) + +#define USB_HOST_ELT_INTERRUPT_LEVEL (9) + +#define USBHCLOCK_X1_48MHZ (0x0000u) /* USB_X1_48MHz */ +#define USBHCLOCK_EXTAL_12MHZ (0x0004u) /* EXTAL_12MHz */ + +#define USB_HOST_MAX_DEVICE (10) + +#define USB_HOST_ON (1) +#define USB_HOST_OFF (0) +#define USB_HOST_YES (1) +#define USB_HOST_NO (0) + +#define USB_HOST_NON_SPEED (0) +#define USB_HOST_LOW_SPEED (1) +#define USB_HOST_FULL_SPEED (2) +#define USB_HOST_HIGH_SPEED (3) + +/* DEVDRV_SUCCESS(0) & DEVDRV_ERROR(-1) is dev_drv.h */ +#define DEVDRV_USBH_STALL (-2) +#define DEVDRV_USBH_TIMEOUT (-3) +#define DEVDRV_USBH_NAK_TIMEOUT (-4) +#define DEVDRV_USBH_DETACH_ERR (-5) +#define DEVDRV_USBH_SETUP_ERR (-6) +#define DEVDRV_USBH_CTRL_COM_ERR (-7) +#define DEVDRV_USBH_COM_ERR (-8) +#define DEVDRV_USBH_DEV_ADDR_ERR (-9) + +#define USB_HOST_ATTACH (1) +#define USB_HOST_DETACH (0) + +#define USB_HOST_MAX_PIPE_NO (9u) +#define USB_HOST_PIPE0 (0) +#define USB_HOST_PIPE1 (1) +#define USB_HOST_PIPE2 (2) +#define USB_HOST_PIPE3 (3) +#define USB_HOST_PIPE4 (4) +#define USB_HOST_PIPE5 (5) +#define USB_HOST_PIPE6 (6) +#define USB_HOST_PIPE7 (7) +#define USB_HOST_PIPE8 (8) +#define USB_HOST_PIPE9 (9) + +#define USB_HOST_ISO (0xc000u) +#define USB_HOST_INTERRUPT (0x8000u) +#define USB_HOST_BULK (0x4000u) + +#define USB_HOST_PIPE_IDLE (0x00) +#define USB_HOST_PIPE_WAIT (0x01) +#define USB_HOST_PIPE_DONE (0x02) +#define USB_HOST_PIPE_NORES (0x03) +#define USB_HOST_PIPE_STALL (0x04) +#define USB_HOST_PIPE_ERROR (0x05) + +#define USB_HOST_NONE (0x0000u) +#define USB_HOST_BFREFIELD (0x0400u) +#define USB_HOST_BFREON (0x0400u) +#define USB_HOST_BFREOFF (0x0000u) +#define USB_HOST_DBLBFIELD (0x0200u) +#define USB_HOST_DBLBON (0x0200u) +#define USB_HOST_DBLBOFF (0x0000u) +#define USB_HOST_CNTMDFIELD (0x0100u) +#define USB_HOST_CNTMDON (0x0100u) +#define USB_HOST_CNTMDOFF (0x0000u) +#define USB_HOST_SHTNAKON (0x0080u) +#define USB_HOST_SHTNAKOFF (0x0000u) +#define USB_HOST_DIRFIELD (0x0010u) +#define USB_HOST_DIR_H_OUT (0x0010u) +#define USB_HOST_DIR_H_IN (0x0000u) +#define USB_HOST_EPNUMFIELD (0x000fu) + +#define USB_HOST_CUSE (0) +#define USB_HOST_D0USE (1) +#define USB_HOST_D0DMA (2) +#define USB_HOST_D1USE (3) +#define USB_HOST_D1DMA (4) + +#define USB_HOST_CFIFO_USE (0x0000) +#define USB_HOST_D0FIFO_USE (0x1000) +#define USB_HOST_D1FIFO_USE (0x2000) +#define USB_HOST_D0FIFO_DMA (0x5000) +#define USB_HOST_D1FIFO_DMA (0x6000) + +#define USB_HOST_BUF2FIFO (0) +#define USB_HOST_FIFO2BUF (1) + +#define USB_HOST_DRV_DETACHED (0x0000) +#define USB_HOST_DRV_ATTACHED (0x0001) +#define USB_HOST_DRV_GET_DEVICE_DESC_64 (0x0002) +#define USB_HOST_DRV_POWERED (0x0003) +#define USB_HOST_DRV_DEFAULT (0x0004) +#define USB_HOST_DRV_SET_ADDRESS (0x0005) +#define USB_HOST_DRV_ADDRESSED (0x0006) +#define USB_HOST_DRV_GET_DEVICE_DESC_18 (0x0007) +#define USB_HOST_DRV_GET_CONGIG_DESC_9 (0x0008) +#define USB_HOST_DRV_GET_CONGIG_DESC (0x0009) +#define USB_HOST_DRV_SET_CONFIG (0x000a) +#define USB_HOST_DRV_CONFIGURED (0x000b) +#define USB_HOST_DRV_SUSPEND (0x1000) +#define USB_HOST_DRV_NORES (0x0100) +#define USB_HOST_DRV_STALL (0x0200) + +#define USB_HOST_TESTMODE_FORCE (0x000du) +#define USB_HOST_TESTMODE_TESTPACKET (0x000cu) +#define USB_HOST_TESTMODE_SE0_NAK (0x000bu) +#define USB_HOST_TESTMODE_K (0x000au) +#define USB_HOST_TESTMODE_J (0x0009u) +#define USB_HOST_TESTMODE_NORMAL (0x0000u) + +#define USB_HOST_DT_DEVICE (0x01) +#define USB_HOST_DT_CONFIGURATION (0x02) +#define USB_HOST_DT_STRING (0x03) +#define USB_HOST_DT_INTERFACE (0x04) +#define USB_HOST_DT_ENDPOINT (0x05) +#define USB_HOST_DT_DEVICE_QUALIFIER (0x06) +#define USB_HOST_DT_OTHER_SPEED_CONFIGURATION (0x07) +#define USB_HOST_DT_INTERFACE_POWER (0x08) + +#define USB_HOST_IF_CLS_NOT (0x00) +#define USB_HOST_IF_CLS_AUDIO (0x01) +#define USB_HOST_IF_CLS_CDC_CTRL (0x02) +#define USB_HOST_IF_CLS_HID (0x03) +#define USB_HOST_IF_CLS_PHYSICAL (0x05) +#define USB_HOST_IF_CLS_IMAGE (0x06) +#define USB_HOST_IF_CLS_PRINTER (0x07) +#define USB_HOST_IF_CLS_MASS (0x08) +#define USB_HOST_IF_CLS_HUB (0x09) +#define USB_HOST_IF_CLS_CDC_DATA (0x0a) +#define USB_HOST_IF_CLS_CRAD (0x0b) +#define USB_HOST_IF_CLS_CONTENT (0x0d) +#define USB_HOST_IF_CLS_VIDEO (0x0e) +#define USB_HOST_IF_CLS_DIAG (0xdc) +#define USB_HOST_IF_CLS_WIRELESS (0xe0) +#define USB_HOST_IF_CLS_APL (0xfe) +#define USB_HOST_IF_CLS_VENDOR (0xff) +#define USB_HOST_IF_CLS_HELE (0xaa) + +#define USB_HOST_EP_DIR_MASK (0x80) +#define USB_HOST_EP_OUT (0x00) +#define USB_HOST_EP_IN (0x80) +#define USB_HOST_EP_TYPE (0x03) +#define USB_HOST_EP_CNTRL (0x00) +#define USB_HOST_EP_ISO (0x01) +#define USB_HOST_EP_BULK (0x02) +#define USB_HOST_EP_INT (0x03) +#define USB_HOST_EP_NUM_MASK (0x0f) + +#define USB_HOST_PIPE_IN (0) +#define USB_HOST_PIPE_OUT (1) + +#define USB_END_POINT_ERROR (0xffff) + +#define USB_HOST_REQ_GET_STATUS (0x0000) +#define USB_HOST_REQ_CLEAR_FEATURE (0x0100) +#define USB_HOST_REQ_RESERVED2 (0x0200) +#define USB_HOST_REQ_SET_FEATURE (0x0300) +#define USB_HOST_REQ_RESERVED4 (0x0400) +#define USB_HOST_REQ_SET_ADDRESS (0x0500) +#define USB_HOST_REQ_GET_DESCRIPTOR (0x0600) +#define USB_HOST_REQ_SET_DESCRIPTOR (0x0700) +#define USB_HOST_REQ_GET_CONFIGURATION (0x0800) +#define USB_HOST_REQ_SET_CONFIGURATION (0x0900) +#define USB_HOST_REQ_GET_INTERFACE (0x0a00) +#define USB_HOST_REQ_SET_INTERFACE (0x0b00) +#define USB_HOST_REQ_SYNCH_FRAME (0x0c00) + +#define USB_HOST_REQTYPE_HOST_TO_DEVICE (0x0000) +#define USB_HOST_REQTYPE_DEVICE_TO_HOST (0x0080) +#define USB_HOST_REQTYPE_STANDARD (0x0020) +#define USB_HOST_REQTYPE_CLASS (0x0040) +#define USB_HOST_REQTYPE_VENDOR (0x0060) +#define USB_HOST_REQTYPE_DEVICE (0x0000) +#define USB_HOST_REQTYPE_INTERFACE (0x0001) +#define USB_HOST_REQTYPE_ENDPOINT (0x0002) +#define USB_HOST_REQTYPE_OTHER (0x0003) + +#define USB_HOST_DESCTYPE_DEVICE (0x0100) +#define USB_HOST_DESCTYPE_CONFIGURATION (0x0200) +#define USB_HOST_DESCTYPE_STRING (0x0300) +#define USB_HOST_DESCTYPE_INTERFACE (0x0400) +#define USB_HOST_DESCTYPE_ENDPOINT (0x0500) +#define USB_HOST_DESCTYPE_DEVICE_QUALIFIER (0x0600) +#define USB_HOST_DESCTYPE_OTHER_SPEED_CONFIGURATION (0x0700) +#define USB_HOST_DESCTYPE_INTERFACE_POWER (0x0800) + + +/******************************************************************************* +Variable Externs +*******************************************************************************/ +typedef struct +{ + uint16_t pipe_number; + uint16_t pipe_cfg; + uint16_t pipe_buf; + uint16_t pipe_max_pktsize; + uint16_t pipe_cycle; + uint16_t fifo_port; +} USB_HOST_CFG_PIPETBL_t; + +typedef struct +{ + uint32_t fifo; + uint32_t buffer; + uint32_t bytes; + uint32_t dir; + uint32_t size; +} USB_HOST_DMA_t; + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +uint16_t R_USB_api_host_init(uint16_t root, uint8_t int_level, uint16_t mode, uint16_t clockmode); +int32_t R_USB_api_host_enumeration(uint16_t root, uint16_t devadr); +int32_t R_USB_api_host_detach(uint16_t root); +int32_t R_USB_api_host_data_in(uint16_t root, uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t R_USB_api_host_data_in2(uint16_t root, uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf, uint32_t *bytes); +int32_t R_USB_api_host_data_out(uint16_t root, uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t R_USB_api_host_control_transfer(uint16_t root, uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len, uint8_t *Buf); +int32_t R_USB_api_host_set_endpoint(uint16_t root, uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t *configdescriptor); +int32_t R_USB_api_host_clear_endpoint(uint16_t root, USB_HOST_CFG_PIPETBL_t *user_table); +int32_t R_USB_api_host_clear_endpoint_pipe(uint16_t root, uint16_t pipe_sel, USB_HOST_CFG_PIPETBL_t *user_table); +uint16_t R_USB_api_host_SetEndpointTable(uint16_t root, uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t* Table); + +int32_t R_USB_api_host_GetDeviceDescriptor(uint16_t root, uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t R_USB_api_host_GetConfigDescriptor(uint16_t root, uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t R_USB_api_host_SetConfig(uint16_t root, uint16_t devadr, uint16_t confignum); +int32_t R_USB_api_host_SetInterface(uint16_t root, uint16_t devadr, uint16_t interface_alt, uint16_t interface_index); +int32_t R_USB_api_host_ClearStall(uint16_t root, uint16_t devadr, uint16_t ep_dir); +uint16_t R_USB_api_host_GetUsbDeviceState(uint16_t root); + +void R_USB_api_host_elt_clocksel(uint16_t clockmode); +void R_USB_api_host_elt_4_4(uint16_t root); +void R_USB_api_host_elt_4_5(uint16_t root); +void R_USB_api_host_elt_4_6(uint16_t root); +void R_USB_api_host_elt_4_7(uint16_t root); +void R_USB_api_host_elt_4_8(uint16_t root); +void R_USB_api_host_elt_4_9(uint16_t root); +void R_USB_api_host_elt_get_desc(uint16_t root); + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host_api.h" +#include "usb1_host_api.h" + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +#ifdef USB0_HOST_API_H +uint16_t Userdef_USB_usb0_host_d0fifo_dmaintid(void); +uint16_t Userdef_USB_usb0_host_d1fifo_dmaintid(void); +void Userdef_USB_usb0_host_attach(void); +void Userdef_USB_usb0_host_detach(void); +void Userdef_USB_usb0_host_delay_1ms(void); +void Userdef_USB_usb0_host_delay_xms(uint32_t msec); +void Userdef_USB_usb0_host_delay_10us(uint32_t usec); +void Userdef_USB_usb0_host_delay_500ns(void); +void Userdef_USB_usb0_host_start_dma(USB_HOST_DMA_t * dma, uint16_t dfacc); +uint32_t Userdef_USB_usb0_host_stop_dma0(void); +uint32_t Userdef_USB_usb0_host_stop_dma1(void); +void Userdef_USB_usb0_host_notice(const char * format); +void Userdef_USB_usb0_host_user_rdy(const char * format, uint16_t data); +#endif + +#ifdef USB1_HOST_API_H +uint16_t Userdef_USB_usb1_host_d0fifo_dmaintid(void); +uint16_t Userdef_USB_usb1_host_d1fifo_dmaintid(void); +void Userdef_USB_usb1_host_attach(void); +void Userdef_USB_usb1_host_detach(void); +void Userdef_USB_usb1_host_delay_1ms(void); +void Userdef_USB_usb1_host_delay_xms(uint32_t msec); +void Userdef_USB_usb1_host_delay_10us(uint32_t usec); +void Userdef_USB_usb1_host_delay_500ns(void); +void Userdef_USB_usb1_host_start_dma(USB_HOST_DMA_t * dma, uint16_t dfacc); +uint32_t Userdef_USB_usb1_host_stop_dma0(void); +uint32_t Userdef_USB_usb1_host_stop_dma1(void); +void Userdef_USB_usb1_host_notice(const char * format); +void Userdef_USB_usb1_host_user_rdy(const char * format, uint16_t data); +#endif + +#endif /* USB_HOST_API_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/inc/usb_host.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,201 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb_host.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB_HOST_H +#define USB_HOST_H + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "r_typedefs.h" +#include "iodefine.h" +#include "rza_io_regrw.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define USB_HOST_DEVICE_0 (0u) +#define USB_HOST_DEVICE_1 (1u) +#define USB_HOST_DEVICE_2 (2u) +#define USB_HOST_DEVICE_3 (3u) +#define USB_HOST_DEVICE_4 (4u) +#define USB_HOST_DEVICE_5 (5u) +#define USB_HOST_DEVICE_6 (6u) +#define USB_HOST_DEVICE_7 (7u) +#define USB_HOST_DEVICE_8 (8u) +#define USB_HOST_DEVICE_9 (9u) +#define USB_HOST_DEVICE_10 (10u) + +#define USB_HOST_ENDPOINT_DESC (0x05) + +#define USB_HOST_BITUPLLE (0x0002u) +#define USB_HOST_BITUCKSEL (0x0004u) +#define USB_HOST_BITBWAIT (0x003fu) + +#define USB_HOST_BUSWAIT_02 (0x0000u) +#define USB_HOST_BUSWAIT_03 (0x0001u) +#define USB_HOST_BUSWAIT_04 (0x0002u) +#define USB_HOST_BUSWAIT_05 (0x0003u) +#define USB_HOST_BUSWAIT_06 (0x0004u) +#define USB_HOST_BUSWAIT_07 (0x0005u) +#define USB_HOST_BUSWAIT_08 (0x0006u) +#define USB_HOST_BUSWAIT_09 (0x0007u) +#define USB_HOST_BUSWAIT_10 (0x0008u) +#define USB_HOST_BUSWAIT_11 (0x0009u) +#define USB_HOST_BUSWAIT_12 (0x000au) +#define USB_HOST_BUSWAIT_13 (0x000bu) +#define USB_HOST_BUSWAIT_14 (0x000cu) +#define USB_HOST_BUSWAIT_15 (0x000du) +#define USB_HOST_BUSWAIT_16 (0x000eu) +#define USB_HOST_BUSWAIT_17 (0x000fu) + +#define USB_HOST_FS_JSTS (0x0001u) +#define USB_HOST_LS_JSTS (0x0002u) + +#define USB_HOST_BITRST (0x0040u) +#define USB_HOST_BITRESUME (0x0020u) +#define USB_HOST_BITUACT (0x0010u) +#define USB_HOST_HSPROC (0x0004u) +#define USB_HOST_HSMODE (0x0003u) +#define USB_HOST_FSMODE (0x0002u) +#define USB_HOST_LSMODE (0x0001u) +#define USB_HOST_UNDECID (0x0000u) + +#define USB_HOST_BITRCNT (0x8000u) +#define USB_HOST_BITDREQE (0x1000u) +#define USB_HOST_BITMBW (0x0c00u) +#define USB_HOST_BITMBW_8 (0x0000u) +#define USB_HOST_BITMBW_16 (0x0400u) +#define USB_HOST_BITMBW_32 (0x0800u) +#define USB_HOST_BITBYTE_LITTLE (0x0000u) +#define USB_HOST_BITBYTE_BIG (0x0100u) +#define USB_HOST_BITISEL (0x0020u) +#define USB_HOST_BITCURPIPE (0x000fu) + +#define USB_HOST_CFIFO_READ (0x0000u) +#define USB_HOST_CFIFO_WRITE (0x0020u) + +#define USB_HOST_BITBVAL (0x8000u) +#define USB_HOST_BITBCLR (0x4000u) +#define USB_HOST_BITFRDY (0x2000u) +#define USB_HOST_BITDTLN (0x0fffu) + +#define USB_HOST_BITBEMPE (0x0400u) +#define USB_HOST_BITNRDYE (0x0200u) +#define USB_HOST_BITBRDYE (0x0100u) +#define USB_HOST_BITBEMP (0x0400u) +#define USB_HOST_BITNRDY (0x0200u) +#define USB_HOST_BITBRDY (0x0100u) + +#define USB_HOST_BITBCHGE (0x4000u) +#define USB_HOST_BITDTCHE (0x1000u) +#define USB_HOST_BITATTCHE (0x0800u) +#define USB_HOST_BITEOFERRE (0x0040u) +#define USB_HOST_BITBCHG (0x4000u) +#define USB_HOST_BITDTCH (0x1000u) +#define USB_HOST_BITATTCH (0x0800u) +#define USB_HOST_BITEOFERR (0x0040u) + +#define USB_HOST_BITSIGNE (0x0020u) +#define USB_HOST_BITSACKE (0x0010u) +#define USB_HOST_BITSIGN (0x0020u) +#define USB_HOST_BITSACK (0x0010u) + +#define USB_HOST_BITSUREQ (0x4000u) +#define USB_HOST_BITSQSET (0x0080u) +#define USB_HOST_PID_STALL2 (0x0003u) +#define USB_HOST_PID_STALL (0x0002u) +#define USB_HOST_PID_BUF (0x0001u) +#define USB_HOST_PID_NAK (0x0000u) + +#define USB_HOST_PIPExBUF (64u) + +#define USB_HOST_D0FIFO (0) +#define USB_HOST_D1FIFO (1) +#define USB_HOST_DMA_READY (0) +#define USB_HOST_DMA_BUSY (1) +#define USB_HOST_DMA_BUSYEND (2) + +#define USB_HOST_FIFO_USE (0x7000) + +#define USB_HOST_FIFOERROR (0xffff) +#define USB_HOST_WRITEEND (0) +#define USB_HOST_WRITESHRT (1) +#define USB_HOST_WRITING (2) +#define USB_HOST_WRITEDMA (3) +#define USB_HOST_READEND (0) +#define USB_HOST_READSHRT (1) +#define USB_HOST_READING (2) +#define USB_HOST_READOVER (3) +#define USB_HOST_READZERO (4) + +#define USB_HOST_CMD_IDLE (0x0000) +#define USB_HOST_CMD_DOING (0x0001) +#define USB_HOST_CMD_DONE (0x0002) +#define USB_HOST_CMD_NORES (0x0003) +#define USB_HOST_CMD_STALL (0x0004) +#define USB_HOST_CMD_FIELD (0x000f) + +#if 0 +#define USB_HOST_CHG_CMDFIELD( r, v ) do { r &= ( ~USB_HOST_CMD_FIELD ); \ + r |= v; } while(0) +#endif + +#define USB_HOST_MODE_WRITE (0x0100) +#define USB_HOST_MODE_READ (0x0200) +#define USB_HOST_MODE_NO_DATA (0x0300) +#define USB_HOST_MODE_FIELD (0x0f00) + +#define USB_HOST_STAGE_SETUP (0x0010) +#define USB_HOST_STAGE_DATA (0x0020) +#define USB_HOST_STAGE_STATUS (0x0030) +#define USB_HOST_STAGE_FIELD (0x00f0) + +#if 0 +#define USB_HOST_CHG_STAGEFIELD( r, v ) do { r &= ( ~USB_HOST_STAGE_FIELD ); \ + r |= v; } while(0) +#endif + +#define USB_HOST_DEVADD_MASK (0x7fc0) + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +extern uint16_t g_usb_host_elt_clockmode; + +#endif /* USB_HOST_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/inc/usb_host_version.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,32 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb_host_version.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ + +#define USB_HOST_LOCAL_Rev "VER080_140709" + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/ohci_wrapp_RZ_A1.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,1492 @@ +/* Copyright (c) 2010-2011 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#include <string.h> +#include "cmsis.h" +#include "cmsis_os.h" +#include "ohci_wrapp_RZ_A1.h" +#include "ohci_wrapp_RZ_A1_local.h" +#include "rza_io_regrw.h" +#include "usb_host_setting.h" + +/* ------------------ HcControl Register --------------------- */ +#define OR_CONTROL_PLE (0x00000004) +#define OR_CONTROL_IE (0x00000008) +#define OR_CONTROL_CLE (0x00000010) +#define OR_CONTROL_BLE (0x00000020) +/* ----------------- HcCommandStatus Register ----------------- */ +#define OR_CMD_STATUS_HCR (0x00000001) +#define OR_CMD_STATUS_CLF (0x00000002) +#define OR_CMD_STATUS_BLF (0x00000004) +#define OR_CMD_STATUS_OCR (0x00000008) +/* --------------- HcInterruptStatus Register ----------------- */ +#define OR_INTR_STATUS_WDH (0x00000002) +#define OR_INTR_STATUS_RHSC (0x00000040) +/* --------------- HcInterruptEnable Register ----------------- */ +#define OR_INTR_ENABLE_WDH (0x00000002) +#define OR_INTR_ENABLE_RHSC (0x00000040) +/* -------------- HcRhPortStatus[1:NDP] Register -------------- */ +#define OR_RH_PORT_CSC (0x00010000) +#define OR_RH_PORT_LSDA (0x00000200) +#define OR_RH_PORT_PRS (0x00000010) +#define OR_RH_PORT_POCI (0x00000008) +#define OR_RH_PORT_CCS (0x00000001) + +#define ED_FORMAT (0x00008000) /* Format */ +#define ED_SKIP (0x00004000) /* Skip this ep in queue */ +#define ED_TOGLE_CARRY (0x00000002) +#define ED_HALTED (0x00000001) + +#define TD_SETUP (0x00000000) /* Direction of Setup Packet */ +#define TD_OUT (0x00080000) /* Direction Out */ +#define TD_TOGGLE_0 (0x02000000) /* Toggle 0 */ +#define TD_TOGGLE_1 (0x03000000) /* Toggle 1 */ + +/* -------------- USB Standard Requests -------------- */ +#define GET_STATUS (0x00) +#define SET_FEATURE (0x03) +#define SET_ADDRESS (0x05) + +#define TD_CTL_MSK_DP (0x00180000) +#define TD_CTL_MSK_T (0x03000000) +#define TD_CTL_MSK_CC (0xF0000000) +#define TD_CTL_MSK_EC (0x0C000000) +#define TD_CTL_SHFT_CC (28) +#define TD_CTL_SHFT_EC (26) +#define TD_CTL_SHFT_T (24) +#define ED_SHFT_TOGLE_CARRY (1) +#define SIG_GEN_LIST_REQ (1) +#if (ISO_TRANS_MAX_NUM > 0) +#define TD_PSW_MSK_CC (0xF000) +#define TD_PSW_SHFT_CC (12) +#define TD_CTL_MSK_FC (0x07000000) +#define TD_CTL_SHFT_FC (24) +#endif + +#define CTL_TRANS_TIMEOUT (1000) +#define BLK_TRANS_TIMEOUT (5) +#define TOTAL_SEM_NUM (5 + (2 * INT_TRANS_MAX_NUM) + (2 * ISO_TRANS_MAX_NUM)) + +#define PORT_LOW_SPEED (0x00000200) +#define PORT_HIGH_SPEED (0x00000400) +#define PORT_NUM (16 + 1) /* num + root(1) */ + +typedef struct tag_hctd { + uint32_t control; /* Transfer descriptor control */ + uint8_t *currBufPtr; /* Physical address of current buffer pointer */ + struct tag_hctd *nextTD; /* Physical pointer to next Transfer Descriptor */ + uint8_t *bufEnd; /* Physical address of end of buffer */ +} hctd_t; + +#if (ISO_TRANS_MAX_NUM > 0) +#define PSW_NUM (8) +typedef struct tag_hcisotd { + uint32_t control; /* Transfer descriptor control */ + uint8_t *bufferPage0; /* Buffer Page 0 */ + struct tag_hcisotd *nextTD; /* Physical pointer to next Transfer Descriptor */ + uint8_t *bufEnd; /* Physical address of end of buffer */ + uint16_t offsetPSW[PSW_NUM]; /* Offset/PSW */ +} hcisotd_t; +#endif + +typedef struct tag_hced { + uint32_t control; /* Endpoint descriptor control */ + uint32_t tailTD; /* Physical address of tail in Transfer descriptor list */ + uint32_t headTD; /* Physcial address of head in Transfer descriptor list */ + struct tag_hced *nextED; /* Physical address of next Endpoint descriptor */ +} hced_t; + +typedef struct tag_hcca { + uint32_t IntTable[32]; /* Interrupt Table */ + uint32_t FrameNumber; /* Frame Number */ + uint32_t DoneHead; /* Done Head */ + volatile uint8_t Reserved[116]; /* Reserved for future use */ + volatile uint8_t Unknown[4]; /* Unused */ +} hcca_t; + +typedef struct tag_usb_ohci_reg { + volatile uint32_t HcRevision; + volatile uint32_t HcControl; + volatile uint32_t HcCommandStatus; + volatile uint32_t HcInterruptStatus; + volatile uint32_t HcInterruptEnable; + volatile uint32_t HcInterruptDisable; + volatile uint32_t HcHCCA; + volatile uint32_t HcPeriodCurrentED; + volatile uint32_t HcControlHeadED; + volatile uint32_t HcControlCurrentED; + volatile uint32_t HcBulkHeadED; + volatile uint32_t HcBulkCurrentED; + volatile uint32_t HcDoneHead; + volatile uint32_t HcFmInterval; + volatile uint32_t HcFmRemaining; + volatile uint32_t HcFmNumber; + volatile uint32_t HcPeriodicStart; + volatile uint32_t HcLSThreshold; + volatile uint32_t HcRhDescriptorA; + volatile uint32_t HcRhDescriptorB; + volatile uint32_t HcRhStatus; + volatile uint32_t HcRhPortStatus1; +} usb_ohci_reg_t; + +typedef struct tag_genelal_ed { + osThreadId tskid; + osSemaphoreId semid_wait; + osSemaphoreId semid_list; + void *p_curr_td; /* pointer of hctd_t or hcisotd_t */ + hced_t *p_curr_ed; + uint32_t pipe_no; + uint32_t trans_wait; + uint32_t cycle_time; + uint8_t *p_start_buf; +#if (ISO_TRANS_MAX_NUM > 0) + uint32_t psw_idx; +#endif +} genelal_ed_t; + +typedef struct tag_tdinfo { + uint32_t count; + uint32_t direction; + uint32_t msp; + uint16_t devadr; + uint16_t speed; /* 1:Speed = Low */ + uint8_t endpoint_no; +} tdinfo_t; + +typedef struct tag_split_trans { + uint16_t root_devadr; + uint16_t get_port; + uint16_t port_speed; + uint16_t reset_port; + uint32_t seq_cnt; + uint32_t port_sts_bits[PORT_NUM]; +} split_trans_t; + +static void callback_task(void const * argument); +static void control_ed_task(void const * argument); +static void bulk_ed_task(void const * argument); +static void int_ed_task(void const * argument); +static int32_t int_trans_doing(hced_t *p_ed, uint32_t index); +static int32_t chk_genelal_ed(genelal_ed_t *p_g_ed); +static void chk_genelal_td_done(genelal_ed_t *p_g_ed); +static void chk_split_trans_setting(genelal_ed_t *p_g_ed); +static void set_split_trans_setting(void); +static void control_trans(genelal_ed_t *p_g_ed); +static void bulk_trans(genelal_ed_t *p_g_ed); +static void int_trans_setting(genelal_ed_t *p_g_ed, uint32_t index); +static uint32_t chk_cycle(hced_t *p_ed); +static void int_trans(genelal_ed_t *p_g_ed); +static void get_td_info(genelal_ed_t *p_g_ed, tdinfo_t *p_td_info); +static void set_togle(uint32_t pipe, hctd_t *p_td, hced_t *p_ed); +#if (ISO_TRANS_MAX_NUM > 0) +static void iso_ed_task(void const * argument); +static int32_t iso_trans_doing(hced_t *p_ed, uint32_t index); +static void chk_iso_td_done(genelal_ed_t *p_g_ed); +static int32_t chk_iso_ed(genelal_ed_t *p_g_ed); +static void iso_trans_setting(genelal_ed_t *p_g_ed, uint32_t index); +static void iso_trans(genelal_ed_t *p_g_ed); +#endif +static void connect_check(void); + +extern USB_HOST_CFG_PIPETBL_t usb_host_blk_ep_tbl1[]; +extern USB_HOST_CFG_PIPETBL_t usb_host_int_ep_tbl1[]; +#if (ISO_TRANS_MAX_NUM > 0) +extern USB_HOST_CFG_PIPETBL_t usb_host_iso_ep_tbl1[]; +#endif + +static usb_ohci_reg_t usb_reg; +static usb_ohci_reg_t *p_usb_reg = &usb_reg; +static usbisr_fnc_t *p_usbisr_cb = NULL; +static osSemaphoreId semid_cb = NULL; +static uint32_t connect_change = 0xFFFFFFFF; +static uint32_t connect_status = 0; +static uint32_t init_end = 0; +static genelal_ed_t ctl_ed; +static genelal_ed_t blk_ed; +static genelal_ed_t int_ed[INT_TRANS_MAX_NUM]; +static split_trans_t split_ctl; + +#if (ISO_TRANS_MAX_NUM > 0) +static genelal_ed_t iso_ed[ISO_TRANS_MAX_NUM]; +#endif + +osSemaphoreDef(ohciwrapp_sem_01); +osSemaphoreDef(ohciwrapp_sem_02); +osSemaphoreDef(ohciwrapp_sem_03); +osSemaphoreDef(ohciwrapp_sem_04); +osSemaphoreDef(ohciwrapp_sem_05); +osSemaphoreDef(ohciwrapp_sem_06); +osSemaphoreDef(ohciwrapp_sem_07); +#if (INT_TRANS_MAX_NUM >= 2) +osSemaphoreDef(ohciwrapp_sem_08); +osSemaphoreDef(ohciwrapp_sem_09); +#endif +#if (INT_TRANS_MAX_NUM >= 3) +osSemaphoreDef(ohciwrapp_sem_10); +osSemaphoreDef(ohciwrapp_sem_11); +#endif +#if (INT_TRANS_MAX_NUM >= 4) +osSemaphoreDef(ohciwrapp_sem_12); +osSemaphoreDef(ohciwrapp_sem_13); +#endif +#if (ISO_TRANS_MAX_NUM >= 1) +osSemaphoreDef(ohciwrapp_sem_14); +osSemaphoreDef(ohciwrapp_sem_15); +#endif +#if (ISO_TRANS_MAX_NUM >= 2) +osSemaphoreDef(ohciwrapp_sem_16); +osSemaphoreDef(ohciwrapp_sem_17); +#endif + +osThreadDef(callback_task, osPriorityHigh, 512); +osThreadDef(control_ed_task, osPriorityNormal, 512); +osThreadDef(bulk_ed_task, osPriorityNormal, 512); +static void int_ed_task_1(void const * argument) { + int_ed_task(argument); +} +osThreadDef(int_ed_task_1, osPriorityNormal, 512); +#if (INT_TRANS_MAX_NUM >= 2) +static void int_ed_task_2(void const * argument) { + int_ed_task(argument); +} +osThreadDef(int_ed_task_2, osPriorityNormal, 512); +#endif +#if (INT_TRANS_MAX_NUM >= 3) +static void int_ed_task_3(void const * argument) { + int_ed_task(argument); +} +osThreadDef(int_ed_task_3, osPriorityNormal, 512); +#endif +#if (INT_TRANS_MAX_NUM >= 4) +static void int_ed_task_4(void const * argument) { + int_ed_task(argument); +} +osThreadDef(int_ed_task_4, osPriorityNormal, 512); +#endif + +#if (ISO_TRANS_MAX_NUM >= 1) +static void iso_ed_task_1(void const * argument) { + iso_ed_task(argument); +} +osThreadDef(iso_ed_task_1, osPriorityAboveNormal, 512); +#endif +#if (ISO_TRANS_MAX_NUM >= 2) +static void iso_ed_task_2(void const * argument) { + iso_ed_task(argument); +} +osThreadDef(iso_ed_task_2, osPriorityAboveNormal, 512); +#endif + +void ohciwrapp_init(usbisr_fnc_t *p_usbisr_fnc) { + static const osSemaphoreDef_t * const sem_def_tbl[TOTAL_SEM_NUM] = { + osSemaphore(ohciwrapp_sem_01), osSemaphore(ohciwrapp_sem_02), osSemaphore(ohciwrapp_sem_03) + , osSemaphore(ohciwrapp_sem_04), osSemaphore(ohciwrapp_sem_05), osSemaphore(ohciwrapp_sem_06) + , osSemaphore(ohciwrapp_sem_07) +#if (INT_TRANS_MAX_NUM >= 2) + , osSemaphore(ohciwrapp_sem_08), osSemaphore(ohciwrapp_sem_09) +#endif +#if (INT_TRANS_MAX_NUM >= 3) + , osSemaphore(ohciwrapp_sem_10), osSemaphore(ohciwrapp_sem_11) +#endif +#if (INT_TRANS_MAX_NUM >= 4) + , osSemaphore(ohciwrapp_sem_12), osSemaphore(ohciwrapp_sem_13) +#endif +#if (ISO_TRANS_MAX_NUM >= 1) + , osSemaphore(ohciwrapp_sem_14), osSemaphore(ohciwrapp_sem_15) +#endif +#if (ISO_TRANS_MAX_NUM >= 2) + , osSemaphore(ohciwrapp_sem_16), osSemaphore(ohciwrapp_sem_17) +#endif + }; + static const osThreadDef_t * const int_tsk_def_tbl[INT_TRANS_MAX_NUM] = { + osThread(int_ed_task_1) +#if (INT_TRANS_MAX_NUM >= 2) + , osThread(int_ed_task_2) +#endif +#if (INT_TRANS_MAX_NUM >= 3) + , osThread(int_ed_task_3) +#endif +#if (INT_TRANS_MAX_NUM >= 4) + , osThread(int_ed_task_4) +#endif + }; +#if (ISO_TRANS_MAX_NUM > 0) + static const osThreadDef_t * const iso_tsk_def_tbl[ISO_TRANS_MAX_NUM] = { + osThread(iso_ed_task_1) +#if (ISO_TRANS_MAX_NUM >= 2) + , osThread(iso_ed_task_2) +#endif + }; +#endif + + uint32_t cnt; + uint32_t index = 0; + + /* Disables interrupt for usb */ + GIC_DisableIRQ(USBIXUSBIX); + +#if (USB_HOST_CH == 0) + /* P4_1(USB0_EN) */ + GPIOP4 &= ~0x0002; /* Outputs low level */ + GPIOPMC4 &= ~0x0002; /* Port mode */ + GPIOPM4 &= ~0x0002; /* Output mode */ +#endif + + p_usbisr_cb = p_usbisr_fnc; +#if (USB_HOST_HISPEED == 0) + g_usbx_host_SupportUsbDeviceSpeed = USB_HOST_FULL_SPEED; +#else + g_usbx_host_SupportUsbDeviceSpeed = USB_HOST_HIGH_SPEED; +#endif + p_usb_reg->HcRevision = 0x00000010; + p_usb_reg->HcControl = 0x00000000; + p_usb_reg->HcCommandStatus = 0x00000000; + p_usb_reg->HcInterruptStatus = 0x00000000; + p_usb_reg->HcInterruptEnable = 0x00000000; + p_usb_reg->HcInterruptDisable = 0x00000000; + p_usb_reg->HcHCCA = 0x00000000; + p_usb_reg->HcPeriodCurrentED = 0x00000000; + p_usb_reg->HcControlHeadED = 0x00000000; + p_usb_reg->HcControlCurrentED = 0x00000000; + p_usb_reg->HcBulkHeadED = 0x00000000; + p_usb_reg->HcBulkCurrentED = 0x00000000; + p_usb_reg->HcDoneHead = 0x00000000; + p_usb_reg->HcFmInterval = 0x00002EDF; + p_usb_reg->HcFmRemaining = 0x00002EDF; + p_usb_reg->HcFmNumber = 0x00000000; + p_usb_reg->HcPeriodicStart = 0x00000000; + p_usb_reg->HcLSThreshold = 0x00000628; + p_usb_reg->HcRhDescriptorA = 0xFF000901; + p_usb_reg->HcRhDescriptorB = 0x00020000; + p_usb_reg->HcRhStatus = 0x00000000; + p_usb_reg->HcRhPortStatus1 = 0x00000000; + +#if (USB_HOST_CH == 0) + GPIOP4 |= 0x0002; /* P4_1 Outputs high level */ + osDelay(5); + GPIOP4 &= ~0x0002; /* P4_1 Outputs low level */ + osDelay(10); +#else + osDelay(15); +#endif + + if (init_end == 0) { + (void)memset(&ctl_ed, 0, sizeof(ctl_ed)); + (void)memset(&blk_ed, 0, sizeof(blk_ed)); + (void)memset(&int_ed[0], 0, sizeof(int_ed)); +#if (ISO_TRANS_MAX_NUM > 0) + (void)memset(&iso_ed[0], 0, sizeof(iso_ed)); +#endif + + /* callback */ + semid_cb = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + (void)osThreadCreate(osThread(callback_task), 0); + + /* control transfer */ + ctl_ed.semid_wait = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + ctl_ed.semid_list = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + ctl_ed.tskid = osThreadCreate(osThread(control_ed_task), 0); + + /* bulk transfer */ + blk_ed.semid_wait = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + blk_ed.semid_list = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + blk_ed.tskid = osThreadCreate(osThread(bulk_ed_task), 0); + + /* interrupt transfer */ + for (cnt = 0; cnt < INT_TRANS_MAX_NUM; cnt++) { + int_ed[cnt].semid_wait = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + int_ed[cnt].semid_list = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + int_ed[cnt].tskid = osThreadCreate(int_tsk_def_tbl[cnt], (void *)cnt); + } + +#if (ISO_TRANS_MAX_NUM > 0) + /* isochronous transfer */ + for (cnt = 0; cnt < ISO_TRANS_MAX_NUM; cnt++) { + iso_ed[cnt].semid_wait = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + iso_ed[cnt].semid_list = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + iso_ed[cnt].tskid = osThreadCreate(iso_tsk_def_tbl[cnt], (void *)cnt); + } +#endif + init_end = 1; + } +} + +uint32_t ohciwrapp_reg_r(uint32_t reg_ofs) { + if (init_end == 0) { + return 0; + } + + return *(uint32_t *)((uint8_t *)p_usb_reg + reg_ofs); +} + +void ohciwrapp_reg_w(uint32_t reg_ofs, uint32_t set_data) { + uint32_t cnt; + uint32_t last_data; + hcca_t *p_hcca; + + if (init_end == 0) { + return; + } + + switch (reg_ofs) { + case OHCI_REG_CONTROL: + last_data = p_usb_reg->HcControl; + p_usb_reg->HcControl = (set_data & 0x000007FF); + if ((last_data & OR_CONTROL_CLE) != (set_data & OR_CONTROL_CLE)) { + /* change CLE */ + if ((set_data & OR_CONTROL_CLE) != 0) { + (void)osSemaphoreRelease(ctl_ed.semid_list); + } else { + if (ctl_ed.trans_wait == 1) { + ctl_ed.trans_wait = 0; + (void)osSemaphoreRelease(ctl_ed.semid_wait); + } + (void)osSemaphoreWait(ctl_ed.semid_list, osWaitForever); + } + } + if ((last_data & OR_CONTROL_BLE) != (set_data & OR_CONTROL_BLE)) { + /* change BLE */ + if ((set_data & OR_CONTROL_BLE) != 0) { + (void)osSemaphoreRelease(blk_ed.semid_list); + } else { + if (blk_ed.trans_wait == 1) { + blk_ed.trans_wait = 0; + (void)osSemaphoreRelease(blk_ed.semid_wait); + } + (void)osSemaphoreWait(blk_ed.semid_list, osWaitForever); + } + } +#if (ISO_TRANS_MAX_NUM > 0) + if ((last_data & OR_CONTROL_IE) != (set_data & OR_CONTROL_IE)) { + /* change IE */ + for (cnt = 0; cnt < ISO_TRANS_MAX_NUM; cnt++) { + if ((set_data & OR_CONTROL_IE) != 0) { + (void)osSemaphoreRelease(iso_ed[cnt].semid_list); + } else { + if (iso_ed[cnt].trans_wait == 1) { + iso_ed[cnt].trans_wait = 0; + (void)osSemaphoreRelease(iso_ed[cnt].semid_wait); + } + (void)osSemaphoreWait(iso_ed[cnt].semid_list, osWaitForever); + } + } + } +#endif + if ((last_data & OR_CONTROL_PLE) != (set_data & OR_CONTROL_PLE)) { + /* change PLE */ + for (cnt = 0; cnt < INT_TRANS_MAX_NUM; cnt++) { + if ((set_data & OR_CONTROL_PLE) != 0) { + (void)osSemaphoreRelease(int_ed[cnt].semid_list); + } else { + if (int_ed[cnt].trans_wait == 1) { + int_ed[cnt].trans_wait = 0; + (void)osSemaphoreRelease(int_ed[cnt].semid_wait); + } + (void)osSemaphoreWait(int_ed[cnt].semid_list, osWaitForever); + } + } + } + break; + case OHCI_REG_COMMANDSTATUS: + if ((set_data & OR_CMD_STATUS_HCR) != 0) { /* HostController Reset */ + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_HCR; + if (usbx_api_host_init(16, g_usbx_host_SupportUsbDeviceSpeed, USBHCLOCK_X1_48MHZ) == USB_HOST_ATTACH) { + ohciwrapp_loc_Connect(1); + } + p_usb_reg->HcCommandStatus &= ~OR_CMD_STATUS_HCR; + } + if ((set_data & OR_CMD_STATUS_CLF) != 0) { + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_CLF; + osSignalSet(ctl_ed.tskid, SIG_GEN_LIST_REQ); + } + if ((set_data & OR_CMD_STATUS_BLF) != 0) { + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_BLF; + osSignalSet(blk_ed.tskid, SIG_GEN_LIST_REQ); + } + if ((set_data & OR_CMD_STATUS_OCR) != 0) { + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_OCR; + } else { + p_usb_reg->HcCommandStatus &= ~OR_CMD_STATUS_OCR; + } + break; + case OHCI_REG_INTERRUPTSTATUS: + if (((p_usb_reg->HcInterruptStatus & OR_INTR_STATUS_WDH) != 0) + && ((set_data & OR_INTR_STATUS_WDH) != 0)) { + if (p_usb_reg->HcDoneHead != 0x00000000) { + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + p_hcca->DoneHead = p_usb_reg->HcDoneHead; + p_usb_reg->HcDoneHead = 0x00000000; + p_usb_reg->HcInterruptStatus |= OR_INTR_STATUS_WDH; + (void)osSemaphoreRelease(semid_cb); + } else { + p_usb_reg->HcInterruptStatus &= ~OR_INTR_STATUS_WDH; + } + } + if ((set_data & OR_INTR_STATUS_RHSC) != 0) { + p_usb_reg->HcInterruptStatus &= ~OR_INTR_STATUS_RHSC; + } + break; + case OHCI_REG_INTERRUPTENABLE: + case OHCI_REG_INTERRUPTDISABLE: + case OHCI_REG_HCCA: + case OHCI_REG_CONTROLHEADED: + case OHCI_REG_CONTROLCURRENTED: + case OHCI_REG_BULKHEADED: + case OHCI_REG_BULKCURRENTED: + case OHCI_REG_FMINTERVAL: + case OHCI_REG_FMREMAINING: + case OHCI_REG_PERIODICSTART: + case OHCI_REG_LSTHRESHOLD: + case OHCI_REG_RHDESCRIPTORA: + case OHCI_REG_RHDESCRIPTORB: + case OHCI_REG_RHSTATUS: + *(uint32_t *)((uint8_t *)p_usb_reg + reg_ofs) = set_data; + break; + case OHCI_REG_RHPORTSTATUS1: + p_usb_reg->HcRhPortStatus1 &= ~(set_data & 0xFFFF0000); + if ((set_data & OR_RH_PORT_PRS) != 0) { /* Set Port Reset */ + p_usb_reg->HcRhPortStatus1 |= OR_RH_PORT_PRS; + usbx_host_UsbBusReset(); + p_usb_reg->HcRhPortStatus1 &= ~OR_RH_PORT_PRS; + } + break; + case OHCI_REG_REVISION: + case OHCI_REG_PERIODCURRENTED: + case OHCI_REG_DONEHEADED: + case OHCI_REG_FMNUMBER: + default: + /* Do Nothing */ + break; + } +} + +static void callback_task(void const * argument) { + usbisr_fnc_t *p_wk_cb = p_usbisr_cb; + + if (p_wk_cb == NULL) { + return; + } + + while (1) { + osSemaphoreWait(semid_cb, osWaitForever); + if (connect_change != 0xFFFFFFFF) { + connect_change = 0xFFFFFFFF; + connect_check(); + } + p_wk_cb(); + } +} + +static void control_ed_task(void const * argument) { + while (1) { + osSignalWait(SIG_GEN_LIST_REQ, osWaitForever); + (void)osSemaphoreWait(ctl_ed.semid_list, osWaitForever); + while ((p_usb_reg->HcControl & OR_CONTROL_CLE) != 0) { + if ((p_usb_reg->HcControlCurrentED == 0) + && ((p_usb_reg->HcCommandStatus & OR_CMD_STATUS_CLF) != 0)) { + p_usb_reg->HcControlCurrentED = p_usb_reg->HcControlHeadED; + p_usb_reg->HcCommandStatus &= ~OR_CMD_STATUS_CLF; + } + if (p_usb_reg->HcControlCurrentED != 0) { + ctl_ed.p_curr_ed = (hced_t *)p_usb_reg->HcControlCurrentED; + if (chk_genelal_ed(&ctl_ed) != 0) { + control_trans(&ctl_ed); + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_CLF; + } + p_usb_reg->HcControlCurrentED = (uint32_t)ctl_ed.p_curr_ed->nextED; + } else { + break; + } + } + if ((p_usb_reg->HcCommandStatus & OR_CMD_STATUS_CLF) != 0) { + osSignalSet(ctl_ed.tskid, SIG_GEN_LIST_REQ); + } + (void)osSemaphoreRelease(ctl_ed.semid_list); + } +} + +static void bulk_ed_task(void const * argument) { + while (1) { + osSignalWait(SIG_GEN_LIST_REQ, osWaitForever); + (void)osSemaphoreWait(blk_ed.semid_list, osWaitForever); + while ((p_usb_reg->HcControl & OR_CONTROL_BLE) != 0) { + if ((p_usb_reg->HcBulkCurrentED == 0) + && ((p_usb_reg->HcCommandStatus & OR_CMD_STATUS_BLF) != 0)) { + p_usb_reg->HcBulkCurrentED = p_usb_reg->HcBulkHeadED; + p_usb_reg->HcCommandStatus &= ~OR_CMD_STATUS_BLF; + } + if (p_usb_reg->HcBulkCurrentED != 0) { + blk_ed.p_curr_ed = (hced_t *)p_usb_reg->HcBulkCurrentED; + if (chk_genelal_ed(&blk_ed) != 0) { + bulk_trans(&blk_ed); + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_BLF; + } + p_usb_reg->HcBulkCurrentED = (uint32_t)blk_ed.p_curr_ed->nextED; + } else { + break; + } + } + if ((p_usb_reg->HcCommandStatus & OR_CMD_STATUS_BLF) != 0) { + osSignalSet(blk_ed.tskid, SIG_GEN_LIST_REQ); + } + (void)osSemaphoreRelease(blk_ed.semid_list); + } +} + +static void int_ed_task(void const * argument) { + genelal_ed_t *p_int_ed = &int_ed[(uint32_t)argument]; + uint32_t cnt; + uint32_t wait_cnt = 0; + hcca_t *p_hcca; + hced_t *p_ed; + + while (1) { + (void)osSemaphoreWait(p_int_ed->semid_list, osWaitForever); + if (p_int_ed->p_curr_ed == NULL) { + for (cnt = 0; (cnt < 32) && ((p_usb_reg->HcControl & OR_CONTROL_PLE) != 0) + && (p_int_ed->p_curr_ed == NULL); cnt++) { + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + p_ed = (hced_t *)p_hcca->IntTable[cnt]; + while ((p_ed != NULL) && ((p_usb_reg->HcControl & OR_CONTROL_PLE) != 0) + && (p_int_ed->p_curr_ed == NULL)) { + if (int_trans_doing(p_ed, (uint32_t)argument) == 0) { + p_int_ed->p_curr_ed = p_ed; + if (chk_genelal_ed(p_int_ed) != 0) { + int_trans_setting(p_int_ed, (uint32_t)argument); + } else { + p_int_ed->p_curr_ed = NULL; + } + } + p_ed = p_ed->nextED; + } + } + } + if (p_int_ed->p_curr_ed != NULL) { + while ((p_usb_reg->HcControl & OR_CONTROL_PLE) != 0) { + if (chk_genelal_ed(p_int_ed) != 0) { + int_trans(p_int_ed); + (void)osSemaphoreWait(p_int_ed->semid_wait, osWaitForever); + usbx_host_stop_transfer(p_int_ed->pipe_no); + wait_cnt = p_int_ed->cycle_time; + } else { + if (wait_cnt > 0) { + wait_cnt--; + } else { + p_int_ed->p_curr_ed = NULL; + } + break; + } + } + } + (void)osSemaphoreRelease(p_int_ed->semid_list); + if (p_int_ed->p_curr_ed == NULL) { + osDelay(10); + } else { + osDelay(1); + } + } +} + +static int32_t int_trans_doing(hced_t *p_ed, uint32_t index) { + uint32_t cnt; + int32_t ret = 0; + + for (cnt = 0; cnt < INT_TRANS_MAX_NUM; cnt++) { + if ((index != cnt) && (int_ed[cnt].p_curr_ed == p_ed)) { + ret = 1; + } + } + + return ret; +} + +static int32_t chk_genelal_ed(genelal_ed_t *p_g_ed){ + int32_t ret = 0; + hced_t *p_ed = p_g_ed->p_curr_ed; + + if (((p_ed->control & ED_SKIP) != 0) + || ((p_ed->control & ED_FORMAT) != 0) + || ((p_ed->headTD & ED_HALTED) != 0) + || ((p_ed->tailTD & 0xFFFFFFF0) == (p_ed->headTD & 0xFFFFFFF0))) { + /* Do Nothing */ + } else if ((p_ed->control & 0x0000007F) > 10) { + p_ed->headTD |= ED_HALTED; + } else { + p_g_ed->p_curr_td = (void *)(p_ed->headTD & 0xFFFFFFF0); + if (p_g_ed->p_curr_td == NULL) { + p_ed->headTD |= ED_HALTED; + } else { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + + p_g_ed->p_start_buf = p_td->currBufPtr; + ret = 1; + } + } + + return ret; +} + +static void chk_genelal_td_done(genelal_ed_t *p_g_ed) { + hcca_t *p_hcca; + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + uint32_t ConditionCode = RZA_IO_RegRead_32(&p_td->control, TD_CTL_SHFT_CC, TD_CTL_MSK_CC); + + if ((ConditionCode != TD_CC_NOT_ACCESSED_1) && (ConditionCode != TD_CC_NOT_ACCESSED_2)) { + p_g_ed->p_curr_ed->headTD = ((uint32_t)p_td->nextTD & 0xFFFFFFF0) + | (p_g_ed->p_curr_ed->headTD & 0x0000000F); + p_td->nextTD = (hctd_t *)p_usb_reg->HcDoneHead; + p_usb_reg->HcDoneHead = (uint32_t)p_g_ed->p_curr_td; + if ((p_usb_reg->HcInterruptStatus & OR_INTR_STATUS_WDH) == 0) { + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + p_hcca->DoneHead = p_usb_reg->HcDoneHead; + p_usb_reg->HcDoneHead = 0x00000000; + p_usb_reg->HcInterruptStatus |= OR_INTR_STATUS_WDH; + (void)osSemaphoreRelease(semid_cb); + } + } +} + +static void chk_split_trans_setting(genelal_ed_t *p_g_ed) { + uint8_t *p_buf; + tdinfo_t td_info; + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + + /* Hi-Speed mode only */ + if (g_usbx_host_UsbDeviceSpeed != USB_HOST_HIGH_SPEED) { + return; + } + + if (RZA_IO_RegRead_32(&p_td->control, TD_CTL_SHFT_CC, TD_CTL_MSK_CC) != TD_CC_NOERROR) { + return; + } + + get_td_info(p_g_ed, &td_info); + p_buf = p_g_ed->p_start_buf; + + if (td_info.direction == 0) { + uint8_t bRequest = p_buf[1]; + uint16_t wValue = (p_buf[3] << 8) + p_buf[2]; + uint16_t wIndx = (p_buf[5] << 8) + p_buf[4]; + uint16_t devadd; + + if ((td_info.devadr == 0) && (bRequest == SET_ADDRESS)) { + /* SET_ADDRESS */ + usbx_host_get_devadd(USB_HOST_DEVICE_0, &devadd); + usbx_host_set_devadd(wValue, &devadd); + if (split_ctl.root_devadr == 0) { + split_ctl.root_devadr = wValue; /* New Address */ + } + } else if ((td_info.devadr == split_ctl.root_devadr) && (bRequest == SET_FEATURE) + && (wValue == 0x0004) && (split_ctl.root_devadr != 0)) { + /* SET_FEATURE PORT_RESET */ + split_ctl.reset_port = (wIndx & 0x00FF); + } else if ((td_info.devadr == split_ctl.root_devadr) && (bRequest == GET_STATUS)) { + /* GET_STATUS */ + split_ctl.get_port = wIndx; + split_ctl.seq_cnt = 1; + } else { + /* Do Nothing */ + } + } else if (td_info.direction == 2) { + if ((td_info.devadr == split_ctl.root_devadr) && (split_ctl.seq_cnt == 1)) { + if (split_ctl.get_port < PORT_NUM) { + split_ctl.port_sts_bits[split_ctl.get_port] = (p_buf[1] << 8) + p_buf[0]; + } + split_ctl.seq_cnt = 0; + } + } else { + /* Do Nothing */ + } +} + +static void set_split_trans_setting(void) { + uint16_t port_speed; + uint16_t devadd; + + if ((split_ctl.root_devadr != 0) && (split_ctl.reset_port != 0) && (split_ctl.reset_port < PORT_NUM)) { + usbx_host_get_devadd(USB_HOST_DEVICE_0, &devadd); + RZA_IO_RegWrite_16(&devadd, split_ctl.root_devadr, USB_DEVADDn_UPPHUB_SHIFT, USB_DEVADDn_UPPHUB); + RZA_IO_RegWrite_16(&devadd, split_ctl.reset_port, USB_DEVADDn_HUBPORT_SHIFT, USB_DEVADDn_HUBPORT); + if ((split_ctl.port_sts_bits[split_ctl.reset_port] & PORT_HIGH_SPEED) != 0) { + port_speed = USB_HOST_HIGH_SPEED; + } else if ((split_ctl.port_sts_bits[split_ctl.reset_port] & PORT_LOW_SPEED) != 0) { + port_speed = USB_HOST_LOW_SPEED; + } else { + port_speed = USB_HOST_FULL_SPEED; + } + RZA_IO_RegWrite_16(&devadd, port_speed, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD); + usbx_host_set_devadd(USB_HOST_DEVICE_0, &devadd); + split_ctl.reset_port = 0; + } +} + +static void control_trans(genelal_ed_t *p_g_ed) { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + tdinfo_t td_info; + uint16_t devadd; + + get_td_info(p_g_ed, &td_info); + + if (g_usbx_host_UsbDeviceSpeed == USB_HOST_HIGH_SPEED) { + if (td_info.devadr == 0) { + set_split_trans_setting(); + } + } else { + /* When a non-Hi-Speed, the communication speed is determined from the TD. */ + usbx_host_get_devadd(USB_HOST_DEVICE_0, &devadd); + if (td_info.speed == 1) { + RZA_IO_RegWrite_16(&devadd, USB_HOST_LOW_SPEED, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD); + } else { + RZA_IO_RegWrite_16(&devadd, USB_HOST_FULL_SPEED, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD); + } + usbx_host_set_devadd(td_info.devadr, &devadd); + } + + USB20X.DCPMAXP = (td_info.devadr << 12) + td_info.msp; + if (td_info.direction == 0) { + g_usbx_host_CmdStage = (USB_HOST_STAGE_SETUP | USB_HOST_CMD_IDLE); + } else if (td_info.count != 0) { + g_usbx_host_CmdStage = (USB_HOST_STAGE_DATA | USB_HOST_CMD_IDLE); + } else { + g_usbx_host_CmdStage = (USB_HOST_STAGE_STATUS | USB_HOST_CMD_IDLE); + } + g_usbx_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_WAIT; + p_g_ed->pipe_no = USB_HOST_PIPE0; + + p_g_ed->trans_wait = 1; + if (connect_status == 0) { + ohciwrapp_loc_TransEnd(p_g_ed->pipe_no, TD_CC_DEVICENOTRESPONDING); + } else { + if (td_info.direction == 0) { + uint16_t Req = (p_td->currBufPtr[1] << 8) + p_td->currBufPtr[0]; + uint16_t Val = (p_td->currBufPtr[3] << 8) + p_td->currBufPtr[2]; + uint16_t Indx = (p_td->currBufPtr[5] << 8) + p_td->currBufPtr[4]; + uint16_t Len = (p_td->currBufPtr[7] << 8) + p_td->currBufPtr[6]; + + g_usbx_host_data_pointer[USB_HOST_PIPE0] = p_td->bufEnd; + usbx_host_SetupStage(Req, Val, Indx, Len); + } else if (td_info.direction == 1) { + usbx_host_CtrlWriteStart(td_info.count, p_td->currBufPtr); + } else { + usbx_host_CtrlReadStart(td_info.count, p_td->currBufPtr); + } + + (void)osSemaphoreWait(p_g_ed->semid_wait, CTL_TRANS_TIMEOUT); + if (p_g_ed->trans_wait == 1) { + p_g_ed->trans_wait = 0; + RZA_IO_RegWrite_32(&p_td->control, TD_CC_DEVICENOTRESPONDING, TD_CTL_SHFT_CC, TD_CTL_MSK_CC); + } + } + + g_usbx_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usbx_host_CmdStage |= USB_HOST_CMD_IDLE; + g_usbx_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_IDLE; +} + +static void bulk_trans(genelal_ed_t *p_g_ed) { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + hced_t *p_ed = p_g_ed->p_curr_ed; + tdinfo_t td_info; + USB_HOST_CFG_PIPETBL_t *user_table = &usb_host_blk_ep_tbl1[0]; + uint8_t wk_table[6]; + + get_td_info(p_g_ed, &td_info); + + wk_table[0] = 0; + wk_table[1] = USB_HOST_ENDPOINT_DESC; + wk_table[2] = td_info.endpoint_no; + if (td_info.direction == 2) { + wk_table[2] |= USB_HOST_EP_IN; + } + wk_table[3] = USB_HOST_EP_BULK; + wk_table[4] = (uint8_t)td_info.msp; + wk_table[5] = (uint8_t)(td_info.msp >> 8); + p_g_ed->pipe_no = user_table->pipe_number; + usbx_api_host_SetEndpointTable(td_info.devadr, user_table, wk_table); + + set_togle(p_g_ed->pipe_no, p_td, p_ed); + + p_g_ed->trans_wait = 1; + if (connect_status == 0) { + ohciwrapp_loc_TransEnd(p_g_ed->pipe_no, TD_CC_DEVICENOTRESPONDING); + } else { + if (td_info.direction == 1) { + usbx_host_start_send_transfer(p_g_ed->pipe_no, td_info.count, p_td->currBufPtr); + } else { + usbx_host_start_receive_transfer(p_g_ed->pipe_no, td_info.count, p_td->currBufPtr); + } + + (void)osSemaphoreWait(p_g_ed->semid_wait, BLK_TRANS_TIMEOUT); + usbx_host_stop_transfer(p_g_ed->pipe_no); + } +} + +static void int_trans_setting(genelal_ed_t *p_g_ed, uint32_t index) { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + hced_t *p_ed = p_g_ed->p_curr_ed; + tdinfo_t td_info; + USB_HOST_CFG_PIPETBL_t *user_table = &usb_host_int_ep_tbl1[index]; + uint8_t wk_table[6]; + uint32_t cycle_time; + uint16_t devadd; + + get_td_info(p_g_ed, &td_info); + + wk_table[0] = 0; + wk_table[1] = USB_HOST_ENDPOINT_DESC; + wk_table[2] = td_info.endpoint_no; + if (td_info.direction == 2) { + wk_table[2] |= USB_HOST_EP_IN; + } + wk_table[3] = USB_HOST_EP_INT; + wk_table[4] = (uint8_t)td_info.msp; + wk_table[5] = (uint8_t)(td_info.msp >> 8); + cycle_time = chk_cycle(p_ed); + p_g_ed->cycle_time = cycle_time; + user_table->pipe_cycle = 0; + while (cycle_time > 1) { + cycle_time >>= 1; + user_table->pipe_cycle++; + } + if (g_usbx_host_UsbDeviceSpeed == USB_HOST_HIGH_SPEED) { + usbx_host_get_devadd(td_info.devadr, &devadd); + if (RZA_IO_RegRead_16(&devadd, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD) == USB_HOST_HIGH_SPEED) { + user_table->pipe_cycle += 3; + if (user_table->pipe_cycle > 7) { + user_table->pipe_cycle = 7; + } + } + } + + p_g_ed->pipe_no = user_table->pipe_number; + usbx_api_host_SetEndpointTable(td_info.devadr, user_table, wk_table); + + set_togle(p_g_ed->pipe_no, p_td, p_ed); +} + +static uint32_t chk_cycle(hced_t *p_ed) { + uint32_t cnt; + uint32_t hit_cnt = 0; + uint32_t cycle_time = 1; + hcca_t *p_hcca; + hced_t *p_wk_ed; + + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + + for (cnt = 0; cnt < 32; cnt++) { + p_wk_ed = (hced_t *)p_hcca->IntTable[cnt]; + while (p_wk_ed != NULL) { + if (p_wk_ed == p_ed) { + hit_cnt++; + break; + } + p_wk_ed = p_wk_ed->nextED; + } + } + if (hit_cnt < 2) { + cycle_time = 32; + } else if (hit_cnt < 4) { + cycle_time = 16; + } else if (hit_cnt < 8) { + cycle_time = 8; + } else if (hit_cnt < 16) { + cycle_time = 4; + } else if (hit_cnt < 32) { + cycle_time = 2; + } else{ + cycle_time = 1; + } + + return cycle_time; +} + +static void int_trans(genelal_ed_t *p_g_ed) { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + tdinfo_t td_info; + + get_td_info(p_g_ed, &td_info); + p_g_ed->trans_wait = 1; + if (connect_status == 0) { + ohciwrapp_loc_TransEnd(p_g_ed->pipe_no, TD_CC_DEVICENOTRESPONDING); + } else { + if (td_info.direction == 1) { + usbx_host_start_send_transfer(p_g_ed->pipe_no, td_info.count, p_td->currBufPtr); + } else { + usbx_host_start_receive_transfer(p_g_ed->pipe_no, td_info.count, p_td->currBufPtr); + } + } +} + +static void get_td_info(genelal_ed_t *p_g_ed, tdinfo_t *p_td_info) { + hced_t *p_ed = p_g_ed->p_curr_ed; + + p_td_info->endpoint_no = (uint8_t)((p_ed->control >> 7) & 0x0000000F); + p_td_info->msp = (p_ed->control >> 16) & 0x000007FF; + p_td_info->devadr = p_ed->control & 0x0000000F; + p_td_info->speed = (p_ed->control >> 13) & 0x00000001; + p_td_info->direction = (p_ed->control >> 11) & 0x00000003; + + if ((p_ed->control & ED_FORMAT) == 0) { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + + if ((p_td_info->direction == 0) || (p_td_info->direction == 3)) { + if ((p_td->control & TD_CTL_MSK_DP) == TD_SETUP) { + p_td_info->direction = 0; + } else if ((p_td->control & TD_CTL_MSK_DP) == TD_OUT) { + p_td_info->direction = 1; + } else { + p_td_info->direction = 2; + } + } + if (p_td->currBufPtr != NULL) { + p_td_info->count = (uint32_t)p_td->bufEnd - (uint32_t)p_td->currBufPtr + 1; + } else { + p_td_info->count = 0; + } + } else { +#if (ISO_TRANS_MAX_NUM > 0) + hcisotd_t *p_isotd = (hcisotd_t *)p_g_ed->p_curr_td; + + if ((p_td_info->direction == 0) || (p_td_info->direction == 3)) { + if ((p_isotd->control & TD_CTL_MSK_DP) == TD_SETUP) { + p_td_info->direction = 0; + } else if ((p_isotd->control & TD_CTL_MSK_DP) == TD_OUT) { + p_td_info->direction = 1; + } else { + p_td_info->direction = 2; + } + } +#endif + } +} + +static void set_togle(uint32_t pipe, hctd_t *p_td, hced_t *p_ed) { + if ((p_td->control & TD_CTL_MSK_T) == TD_TOGGLE_0) { + usbx_host_set_sqclr(pipe); + } else if ((p_td->control & TD_CTL_MSK_T) == TD_TOGGLE_1) { + usbx_host_set_sqset(pipe); + } else if ((p_ed->headTD & ED_TOGLE_CARRY) == 0) { + usbx_host_set_sqclr(pipe); + } else { + usbx_host_set_sqset(pipe); + } +} + +#if (ISO_TRANS_MAX_NUM > 0) +static void iso_ed_task(void const * argument) { + genelal_ed_t *p_iso_ed = &iso_ed[(uint32_t)argument]; + uint32_t wait_cnt = 0; + hcca_t *p_hcca; + hced_t *p_ed; + + while (1) { + (void)osSemaphoreWait(p_iso_ed->semid_list, osWaitForever); + if (p_iso_ed->p_curr_ed == NULL) { + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + p_ed = (hced_t *)p_hcca->IntTable[0]; + while ((p_ed != NULL) && ((p_usb_reg->HcControl & OR_CONTROL_IE) != 0) + && (p_iso_ed->p_curr_ed == NULL)) { + if (iso_trans_doing(p_ed, (uint32_t)argument) == 0) { + p_iso_ed->p_curr_ed = p_ed; + if (chk_iso_ed(p_iso_ed) != 0) { + iso_trans_setting(p_iso_ed, (uint32_t)argument); + } else { + p_iso_ed->p_curr_ed = NULL; + } + } + p_ed = p_ed->nextED; + } + p_iso_ed->psw_idx = 0; + } + if (p_iso_ed->p_curr_ed != NULL) { + while ((p_usb_reg->HcControl & OR_CONTROL_IE) != 0) { + if (chk_iso_ed(p_iso_ed) != 0) { + hcisotd_t *p_isotd = (hcisotd_t *)p_iso_ed->p_curr_td; + uint32_t starting_frame = p_isotd->control & 0x0000FFFF; + uint32_t wait_time = 0; + uint32_t wk_HcFmNumber = p_usb_reg->HcFmNumber; + + if (starting_frame > wk_HcFmNumber) { + wait_time = starting_frame - wk_HcFmNumber; + } else { + wait_time = (0xFFFF - wk_HcFmNumber) + starting_frame; + } + if ((wait_time >= 2) && (wait_time <= 1000)) { + for (int cnt = 0; cnt < (wait_time - 1); cnt++) { + osDelay(1); + p_usb_reg->HcFmNumber = (wk_HcFmNumber + cnt) & 0x0000FFFF; + } + } + p_iso_ed->psw_idx = 0; + iso_trans(p_iso_ed); + (void)osSemaphoreWait(p_iso_ed->semid_wait, osWaitForever); + wait_cnt = 8; + } else { + if (wait_cnt > 0) { + wait_cnt--; + } else { + p_iso_ed->p_curr_ed = NULL; + } + break; + } + } + } + (void)osSemaphoreRelease(p_iso_ed->semid_list); + if (p_iso_ed->p_curr_ed == NULL) { + osDelay(10); + } else { + osDelay(1); + } + } +} + +static int32_t iso_trans_doing(hced_t *p_ed, uint32_t index) { + uint32_t cnt; + int32_t ret = 0; + + for (cnt = 0; cnt < ISO_TRANS_MAX_NUM; cnt++) { + if ((index != cnt) && (iso_ed[cnt].p_curr_ed == p_ed)) { + ret = 1; + } + } + + return ret; +} + +static void chk_iso_td_done(genelal_ed_t *p_g_ed) { + hcca_t *p_hcca; + hcisotd_t *p_isotd = (hcisotd_t *)p_g_ed->p_curr_td; + uint32_t ConditionCode = RZA_IO_RegRead_32(&p_isotd->control, TD_CTL_SHFT_CC, TD_CTL_MSK_CC); + + if ((ConditionCode != TD_CC_NOT_ACCESSED_1) && (ConditionCode != TD_CC_NOT_ACCESSED_2)) { + p_g_ed->p_curr_ed->headTD = ((uint32_t)p_isotd->nextTD & 0xFFFFFFF0) + | (p_g_ed->p_curr_ed->headTD & 0x0000000F); + p_isotd->nextTD = (hcisotd_t *)p_usb_reg->HcDoneHead; + p_usb_reg->HcDoneHead = (uint32_t)p_g_ed->p_curr_td; + if ((p_usb_reg->HcInterruptStatus & OR_INTR_STATUS_WDH) == 0) { + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + p_hcca->DoneHead = p_usb_reg->HcDoneHead; + p_usb_reg->HcDoneHead = 0x00000000; + p_usb_reg->HcInterruptStatus |= OR_INTR_STATUS_WDH; + (void)osSemaphoreRelease(semid_cb); + } + } +} + +static int32_t chk_iso_ed(genelal_ed_t *p_g_ed){ + int32_t ret = 0; + hced_t *p_ed = p_g_ed->p_curr_ed; + + if (((p_ed->control & ED_SKIP) != 0) + || ((p_ed->control & ED_FORMAT) == 0) + || ((p_ed->headTD & ED_HALTED) != 0) + || ((p_ed->tailTD & 0xFFFFFFF0) == (p_ed->headTD & 0xFFFFFFF0))) { + /* Do Nothing */ + } else if ((p_ed->control & 0x0000007F) > 10) { + p_ed->headTD |= ED_HALTED; + } else { + p_g_ed->p_curr_td = (void *)(p_ed->headTD & 0xFFFFFFF0); + if (p_g_ed->p_curr_td == NULL) { + p_ed->headTD |= ED_HALTED; + } else { + hcisotd_t *p_isotd = (hcisotd_t *)p_g_ed->p_curr_td; + + p_g_ed->p_start_buf = p_isotd->bufferPage0; + ret = 1; + } + } + + return ret; +} + +static void iso_trans_setting(genelal_ed_t *p_g_ed, uint32_t index) { + tdinfo_t td_info; + USB_HOST_CFG_PIPETBL_t *user_table = &usb_host_iso_ep_tbl1[index]; + uint8_t wk_table[6]; + uint16_t devadd; + + get_td_info(p_g_ed, &td_info); + + wk_table[0] = 0; + wk_table[1] = USB_HOST_ENDPOINT_DESC; + wk_table[2] = td_info.endpoint_no; + if (td_info.direction == 2) { + wk_table[2] |= USB_HOST_EP_IN; + } + wk_table[3] = USB_HOST_EP_ISO; + wk_table[4] = (uint8_t)td_info.msp; + wk_table[5] = (uint8_t)(td_info.msp >> 8); + p_g_ed->cycle_time = 1; + user_table->pipe_cycle = 0; + if (g_usbx_host_UsbDeviceSpeed == USB_HOST_HIGH_SPEED) { + usbx_host_get_devadd(td_info.devadr, &devadd); + if (RZA_IO_RegRead_16(&devadd, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD) == USB_HOST_HIGH_SPEED) { + user_table->pipe_cycle += 3; + } + } + + p_g_ed->pipe_no = user_table->pipe_number; + usbx_api_host_SetEndpointTable(td_info.devadr, user_table, wk_table); +} + +static void iso_trans(genelal_ed_t *p_g_ed) { + hcisotd_t *p_isotd = (hcisotd_t *)p_g_ed->p_curr_td; + tdinfo_t td_info; + uint32_t buff_addr; + uint32_t data_size; + + if (((uint32_t)p_isotd->offsetPSW[p_g_ed->psw_idx] & 0x00001000) == 0) { + buff_addr = (uint32_t)p_isotd->bufferPage0 & 0xFFFFF000; + } else { + buff_addr = (uint32_t)p_isotd->bufEnd & 0xFFFFF000; + } + buff_addr |= (uint32_t)p_isotd->offsetPSW[p_g_ed->psw_idx] & 0x00000FFF; + + if (p_g_ed->psw_idx < RZA_IO_RegRead_32(&p_isotd->control, TD_CTL_SHFT_FC, TD_CTL_MSK_FC)) { + data_size = p_isotd->offsetPSW[p_g_ed->psw_idx + 1] - p_isotd->offsetPSW[p_g_ed->psw_idx]; + } else { + data_size = (uint32_t)p_isotd->bufEnd - buff_addr + 1; + } + p_isotd->offsetPSW[p_g_ed->psw_idx] = (uint16_t)data_size; + + get_td_info(p_g_ed, &td_info); + p_g_ed->trans_wait = 1; + if (connect_status == 0) { + ohciwrapp_loc_TransEnd(p_g_ed->pipe_no, TD_CC_DEVICENOTRESPONDING); + } else { + if (td_info.direction == 1) { + usbx_host_start_send_transfer(p_g_ed->pipe_no, data_size, (uint8_t *)buff_addr); + } else { + usbx_host_start_receive_transfer(p_g_ed->pipe_no, data_size, (uint8_t *)buff_addr); + } + } +} +#endif + +static void connect_check(void) { + uint32_t type = 0; + uint16_t stat; + uint16_t devadd = 0; + uint32_t wk_HcRhPortStatus1 = p_usb_reg->HcRhPortStatus1; + + if (usbx_host_CheckAttach() == USB_HOST_ATTACH) { + type = 1; + } + + if ((((wk_HcRhPortStatus1 & OR_RH_PORT_CCS) == 0) && (type == 0)) + || (((wk_HcRhPortStatus1 & OR_RH_PORT_CCS) != 0) && (type != 0))) { + return; + } + + if (type == 0) { + usbx_host_UsbDetach(); + wk_HcRhPortStatus1 &= ~OR_RH_PORT_CCS; + } else { + usbx_host_UsbAttach(); + stat = usbx_host_UsbBusReset(); + RZA_IO_RegWrite_16(&devadd, 0, USB_DEVADDn_UPPHUB_SHIFT, USB_DEVADDn_UPPHUB); + RZA_IO_RegWrite_16(&devadd, 0, USB_DEVADDn_HUBPORT_SHIFT, USB_DEVADDn_HUBPORT); + if (stat == USB_HOST_HSMODE) { + wk_HcRhPortStatus1 &= ~OR_RH_PORT_LSDA; + RZA_IO_RegWrite_16(&USB20X.SOFCFG, 0, USB_SOFCFG_TRNENSEL_SHIFT, USB_SOFCFG_TRNENSEL); + g_usbx_host_UsbDeviceSpeed = USB_HOST_HIGH_SPEED; + } else if (stat == USB_HOST_FSMODE) { + wk_HcRhPortStatus1 &= ~OR_RH_PORT_LSDA; + RZA_IO_RegWrite_16(&USB20X.SOFCFG, 0, USB_SOFCFG_TRNENSEL_SHIFT, USB_SOFCFG_TRNENSEL); + g_usbx_host_UsbDeviceSpeed = USB_HOST_FULL_SPEED; + } else { + wk_HcRhPortStatus1 |= OR_RH_PORT_LSDA; + RZA_IO_RegWrite_16(&USB20X.SOFCFG, 1, USB_SOFCFG_TRNENSEL_SHIFT, USB_SOFCFG_TRNENSEL); + g_usbx_host_UsbDeviceSpeed = USB_HOST_LOW_SPEED; + } + RZA_IO_RegWrite_16(&devadd, g_usbx_host_UsbDeviceSpeed, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD); + usbx_host_init_pipe_status(); + usbx_host_set_devadd(USB_HOST_DEVICE_0, &devadd); + wk_HcRhPortStatus1 |= OR_RH_PORT_CCS; + } + wk_HcRhPortStatus1 |= OR_RH_PORT_CSC; + p_usb_reg->HcRhPortStatus1 = wk_HcRhPortStatus1; + p_usb_reg->HcInterruptStatus |= OR_INTR_STATUS_RHSC; + (void)memset(&split_ctl, 0, sizeof(split_ctl)); +} + +void ohciwrapp_loc_Connect(uint32_t type) { + uint32_t cnt; + + connect_status = type; + connect_change = type; + if (type == 0) { + if (ctl_ed.trans_wait == 1) { + ohciwrapp_loc_TransEnd(ctl_ed.pipe_no, TD_CC_DEVICENOTRESPONDING); + } + if (blk_ed.trans_wait == 1) { + ohciwrapp_loc_TransEnd(blk_ed.pipe_no, TD_CC_DEVICENOTRESPONDING); + } + for (cnt = 0; cnt< INT_TRANS_MAX_NUM; cnt++) { + if (int_ed[cnt].trans_wait == 1) { + ohciwrapp_loc_TransEnd(int_ed[cnt].pipe_no, TD_CC_DEVICENOTRESPONDING); + } + } +#if (ISO_TRANS_MAX_NUM > 0) + for (cnt = 0; cnt< ISO_TRANS_MAX_NUM; cnt++) { + if (iso_ed[cnt].trans_wait == 1) { + hced_t *p_ed = iso_ed[cnt].p_curr_ed; + + p_ed->headTD |= ED_HALTED; + ohciwrapp_loc_TransEnd(iso_ed[cnt].pipe_no, TD_CC_DEVICENOTRESPONDING); + } + } +#endif + } + (void)osSemaphoreRelease(semid_cb); +} + +void ohciwrapp_loc_TransEnd(uint32_t pipe, uint32_t ConditionCode) { + uint32_t periodic = 0; + uint32_t cnt; + uint32_t sqmon; + hced_t *p_ed; + genelal_ed_t *p_wait_ed = NULL; + + if (ctl_ed.pipe_no == pipe) { + p_wait_ed = &ctl_ed; + } else if (blk_ed.pipe_no == pipe) { + p_wait_ed = &blk_ed; + } else { +#if (ISO_TRANS_MAX_NUM > 0) + if (p_wait_ed == NULL) { + for (cnt = 0; cnt< ISO_TRANS_MAX_NUM; cnt++) { + if (iso_ed[cnt].pipe_no == pipe) { + p_wait_ed = &iso_ed[cnt]; + break; + } + } + } +#endif + if (p_wait_ed == NULL) { + for (cnt = 0; cnt< INT_TRANS_MAX_NUM; cnt++) { + if (int_ed[cnt].pipe_no == pipe) { + p_wait_ed = &int_ed[cnt]; + periodic = 1; + break; + } + } + } + } + + if (p_wait_ed == NULL) { + return; + } + p_ed = p_wait_ed->p_curr_ed; + if (p_ed == NULL) { + return; + } + + if ((p_ed->control & ED_FORMAT) == 0) { + hctd_t *p_td = (hctd_t *)p_wait_ed->p_curr_td; + + if (p_td != NULL) { + if (ConditionCode == TD_CC_NOERROR) { + /* ErrorCount */ + RZA_IO_RegWrite_32(&p_td->control, 0, TD_CTL_SHFT_EC, TD_CTL_MSK_EC); + + /* CurrentBufferPointer */ + p_td->currBufPtr += ((uint32_t)p_td->bufEnd - (uint32_t)p_td->currBufPtr + 1) - g_usbx_host_data_count[pipe]; + } else { + /* ErrorCount */ + RZA_IO_RegWrite_32(&p_td->control, 3, TD_CTL_SHFT_EC, TD_CTL_MSK_EC); + } + + /* DataToggle */ + sqmon = usbx_host_get_sqmon(pipe); + RZA_IO_RegWrite_32(&p_td->control, sqmon, TD_CTL_SHFT_T, TD_CTL_MSK_T); + if (sqmon == 0) { + p_ed->headTD &= ~ED_TOGLE_CARRY; + } else { + p_ed->headTD |= ED_TOGLE_CARRY; + } + + /* ConditionCode */ + RZA_IO_RegWrite_32(&p_td->control, ConditionCode, TD_CTL_SHFT_CC, TD_CTL_MSK_CC); + + if (p_wait_ed == &ctl_ed) { + chk_split_trans_setting(&ctl_ed); + } + chk_genelal_td_done(p_wait_ed); + + if (periodic != 0) { + if (chk_genelal_ed(p_wait_ed) != 0) { + int_trans(p_wait_ed); + } else { + p_wait_ed->trans_wait = 0; + (void)osSemaphoreRelease(p_wait_ed->semid_wait); + } + } else { + p_wait_ed->trans_wait = 0; + (void)osSemaphoreRelease(p_wait_ed->semid_wait); + } + } + } else { +#if (ISO_TRANS_MAX_NUM > 0) + hcisotd_t *p_isotd = (hcisotd_t *)p_wait_ed->p_curr_td; + uint32_t next_trans = 0; + + if (p_isotd != NULL) { + usbx_host_stop_transfer(pipe); + p_usb_reg->HcFmNumber = ((p_isotd->control & 0x0000FFFF) + p_wait_ed->psw_idx) & 0x0000FFFF; + + /* Size of packet */ + p_isotd->offsetPSW[p_wait_ed->psw_idx] -= g_usbx_host_data_count[pipe]; + + /* ConditionCode */ + RZA_IO_RegWrite_32(&p_isotd->control, ConditionCode, TD_CTL_SHFT_CC, TD_CTL_MSK_CC); + RZA_IO_RegWrite_16(&p_isotd->offsetPSW[p_wait_ed->psw_idx], + (uint16_t)ConditionCode, TD_PSW_SHFT_CC, TD_PSW_MSK_CC); + + if (usbx_host_CheckAttach() != USB_HOST_ATTACH) { + p_ed->headTD |= ED_HALTED; + } + if (p_wait_ed->psw_idx >= RZA_IO_RegRead_32(&p_isotd->control, TD_CTL_SHFT_FC, TD_CTL_MSK_FC)) { + p_wait_ed->psw_idx = 0; + chk_iso_td_done(p_wait_ed); + } else { + p_wait_ed->psw_idx++; + } + if (chk_iso_ed(p_wait_ed) != 0) { + iso_trans(p_wait_ed); + next_trans = 1; + } + if (next_trans == 0) { + p_wait_ed->trans_wait = 0; + (void)osSemaphoreRelease(p_wait_ed->semid_wait); + } + } +#endif + } + +} +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/ohci_wrapp_RZ_A1.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,60 @@ +/* Copyright (c) 2010-2011 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#ifndef OHCI_WRAPP_RZ_A1_H +#define OHCI_WRAPP_RZ_A1_H + +#ifdef __cplusplus +extern "C" { +#endif + +#define OHCI_REG_REVISION (0x00) /* HcRevision */ +#define OHCI_REG_CONTROL (0x04) /* HcControl */ +#define OHCI_REG_COMMANDSTATUS (0x08) /* HcCommandStatus */ +#define OHCI_REG_INTERRUPTSTATUS (0x0C) /* HcInterruptStatus */ +#define OHCI_REG_INTERRUPTENABLE (0x10) /* HcInterruptEnable */ +#define OHCI_REG_INTERRUPTDISABLE (0x14) /* HcInterruptDisable */ +#define OHCI_REG_HCCA (0x18) /* HcHCCA */ +#define OHCI_REG_PERIODCURRENTED (0x1C) /* HcPeriodCurrentED */ +#define OHCI_REG_CONTROLHEADED (0x20) /* HcControlHeadED */ +#define OHCI_REG_CONTROLCURRENTED (0x24) /* HcControlCurrentED */ +#define OHCI_REG_BULKHEADED (0x28) /* HcBulkHeadED */ +#define OHCI_REG_BULKCURRENTED (0x2C) /* HcBulkCurrentED */ +#define OHCI_REG_DONEHEADED (0x30) /* HcDoneHead */ +#define OHCI_REG_FMINTERVAL (0x34) /* HcFmInterval */ +#define OHCI_REG_FMREMAINING (0x38) /* HcFmRemaining */ +#define OHCI_REG_FMNUMBER (0x3C) /* HcFmNumber */ +#define OHCI_REG_PERIODICSTART (0x40) /* HcPeriodicStart */ +#define OHCI_REG_LSTHRESHOLD (0x44) /* HcLSThreshold */ +#define OHCI_REG_RHDESCRIPTORA (0x48) /* HcRhDescriptorA */ +#define OHCI_REG_RHDESCRIPTORB (0x4C) /* HcRhDescriptorB */ +#define OHCI_REG_RHSTATUS (0x50) /* HcRhStatus */ +#define OHCI_REG_RHPORTSTATUS1 (0x54) /* HcRhPortStatus1 */ + +typedef void (usbisr_fnc_t)(void); + +extern void ohciwrapp_init(usbisr_fnc_t *p_usbisr_fnc); +extern uint32_t ohciwrapp_reg_r(uint32_t reg_ofs); +extern void ohciwrapp_reg_w(uint32_t reg_ofs, uint32_t set_data); +extern void ohciwrapp_interrupt(uint32_t int_sense); + +#ifdef __cplusplus +} +#endif + +#endif /* OHCI_WRAPP_RZ_A1_H */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/ohci_wrapp_RZ_A1_local.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,49 @@ +/* Copyright (c) 2010-2011 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#ifndef OHCI_WRAPP_RZ_A1_LOCAL_H +#define OHCI_WRAPP_RZ_A1_LOCAL_H + +#ifdef __cplusplus +extern "C" { +#endif + +/* ConditionCode */ +#define TD_CC_NOERROR (0) +#define TD_CC_CRC (1) +#define TD_CC_BITSTUFFING (2) +#define TD_CC_DATATOGGLEMISMATCH (3) +#define TD_CC_STALL (4) +#define TD_CC_DEVICENOTRESPONDING (5) +#define TD_CC_PIDCHECKFAILURE (6) +#define TD_CC_UNEXPECTEDPID (7) +#define TD_CC_DATAOVERRUN (8) +#define TD_CC_DATAUNDERRUN (9) +#define TD_CC_BUFFEROVERRUN (12) +#define TD_CC_BUFFERUNDERRUN (13) +#define TD_CC_NOT_ACCESSED_1 (14) +#define TD_CC_NOT_ACCESSED_2 (15) + +extern void ohciwrapp_loc_Connect(uint32_t type); +extern void ohciwrapp_loc_TransEnd(uint32_t pipe, uint32_t ConditionCode); + +#ifdef __cplusplus +} +#endif + +#endif /* OHCI_WRAPP_RZ_A1_LOCAL_H */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/ohci_wrapp_pipe.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,189 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "devdrv_usb_host_api.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/********************************************************************************************************/ +/* Endpoint Configuration Data Format */ +/********************************************************************************************************/ +/* LINE1: Pipe Window Select Register */ +/* CPU Access PIPE : USB_HOST_PIPE1 to USB_HOST_PIPE9 [ ### SET ### ] */ +/* LINE2: Pipe Configuration Register */ +/* Transfer Type : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* Buffer Ready interrupt : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* Double Buffer Mode : USB_HOST_DBLBON / USB_HOST_DBLBOFF [ ### SET ### ] */ +/* Continuous Transmit: : USB_HOST_CNTMDON / USB_HOST_CNTMDOFF [ ### SET ### ] */ +/* Short NAK : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* Transfer Direction : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* Endpoint Number : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* LINE3: Pipe Buffer Configuration Register */ +/* Buffer Size : (uint16_t)((uint16_t)(((x) / 64) - 1) << 10) */ +/* [ ### SET ### ] */ +/* Buffer Top Number : (uint16_t)(x) [ ### SET ### ] */ +/* LINE4: Pipe Maxpacket Size Register */ +/* Max Packet Size : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* LINE5: Pipe Cycle Configuration Register (0x6C) */ +/* ISO Buffer Flush Mode : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* ISO Interval Value : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* LINE6: use FIFO port */ +/* : USB_HOST_CUSE [ ### SET ### ] */ +/* : USB_HOST_D0USE / USB_HOST_D1USE */ +/* : USB_HOST_D0DMA / USB_HOST_D0DMA */ +/********************************************************************************************************/ + +/* Device Address 1 */ +USB_HOST_CFG_PIPETBL_t usb_host_blk_ep_tbl1[ ] = +{ + { + USB_HOST_PIPE3, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBON | USB_HOST_CNTMDON | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((1024) / 64) - 1) << 10) | (uint16_t)(8), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D0USE + }, + + { + /* Pipe end */ + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF + } +}; + +USB_HOST_CFG_PIPETBL_t usb_host_int_ep_tbl1[ ] = +{ + { + USB_HOST_PIPE6, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBOFF | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((64) / 64) - 1) << 10) | (uint16_t)(40), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + USB_HOST_PIPE7, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBOFF | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((64) / 64) - 1) << 10) | (uint16_t)(41), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + USB_HOST_PIPE8, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBOFF | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((64) / 64) - 1) << 10) | (uint16_t)(42), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + USB_HOST_PIPE9, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBOFF | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((64) / 64) - 1) << 10) | (uint16_t)(43), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + /* Pipe end */ + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF + } +}; + +USB_HOST_CFG_PIPETBL_t usb_host_iso_ep_tbl1[ ] = +{ + { + USB_HOST_PIPE1, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBON | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((1024) / 64) - 1) << 10) | (uint16_t)(44), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + USB_HOST_PIPE2, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBON | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((1024) / 64) - 1) << 10) | (uint16_t)(76), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + /* Pipe end */ + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF + } +}; + + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/inc/usb0_host.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,156 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB0_HOST_H +#define USB0_HOST_H + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "devdrv_usb_host_api.h" +#include "usb_host.h" + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +extern const uint16_t g_usb0_host_bit_set[]; +extern uint32_t g_usb0_host_data_count[USB_HOST_MAX_PIPE_NO + 1]; +extern uint8_t *g_usb0_host_data_pointer[USB_HOST_MAX_PIPE_NO + 1]; + +extern uint16_t g_usb0_host_PipeIgnore[]; +extern uint16_t g_usb0_host_PipeTbl[]; +extern uint16_t g_usb0_host_pipe_status[]; +extern uint32_t g_usb0_host_PipeDataSize[]; + +extern USB_HOST_DMA_t g_usb0_host_DmaInfo[]; +extern uint16_t g_usb0_host_DmaPipe[]; +extern uint16_t g_usb0_host_DmaBval[]; +extern uint16_t g_usb0_host_DmaStatus[]; + +extern uint16_t g_usb0_host_driver_state; +extern uint16_t g_usb0_host_ConfigNum; +extern uint16_t g_usb0_host_CmdStage; +extern uint16_t g_usb0_host_bchg_flag; +extern uint16_t g_usb0_host_detach_flag; +extern uint16_t g_usb0_host_attach_flag; + +extern uint16_t g_usb0_host_UsbAddress; +extern uint16_t g_usb0_host_setUsbAddress; +extern uint16_t g_usb0_host_default_max_packet[USB_HOST_MAX_DEVICE + 1]; +extern uint16_t g_usb0_host_UsbDeviceSpeed; +extern uint16_t g_usb0_host_SupportUsbDeviceSpeed; + +extern uint16_t g_usb0_host_SavReq; +extern uint16_t g_usb0_host_SavVal; +extern uint16_t g_usb0_host_SavIndx; +extern uint16_t g_usb0_host_SavLen; + +extern uint16_t g_usb0_host_pipecfg[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb0_host_pipebuf[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb0_host_pipemaxp[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb0_host_pipeperi[USB_HOST_MAX_PIPE_NO + 1]; + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +/* ==== common ==== */ +void usb0_host_dma_stop_d0(uint16_t pipe, uint32_t remain); +void usb0_host_dma_stop_d1(uint16_t pipe, uint32_t remain); +uint16_t usb0_host_is_hispeed(void); +uint16_t usb0_host_is_hispeed_enable(void); +uint16_t usb0_host_start_send_transfer(uint16_t pipe, uint32_t size, uint8_t *data); +uint16_t usb0_host_write_buffer(uint16_t pipe); +uint16_t usb0_host_write_buffer_c(uint16_t pipe); +uint16_t usb0_host_write_buffer_d0(uint16_t pipe); +uint16_t usb0_host_write_buffer_d1(uint16_t pipe); +void usb0_host_start_receive_transfer(uint16_t pipe, uint32_t size, uint8_t *data); +uint16_t usb0_host_read_buffer(uint16_t pipe); +uint16_t usb0_host_read_buffer_c(uint16_t pipe); +uint16_t usb0_host_read_buffer_d0(uint16_t pipe); +uint16_t usb0_host_read_buffer_d1(uint16_t pipe); +uint16_t usb0_host_change_fifo_port(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw); +void usb0_host_set_curpipe(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw); +void usb0_host_set_curpipe2(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw, uint16_t dfacc); +uint16_t usb0_host_get_mbw(uint32_t trncount, uint32_t dtptr); +uint16_t usb0_host_read_dma(uint16_t pipe); +void usb0_host_stop_transfer(uint16_t pipe); +void usb0_host_brdy_int(uint16_t status, uint16_t int_enb); +void usb0_host_nrdy_int(uint16_t status, uint16_t int_enb); +void usb0_host_bemp_int(uint16_t status, uint16_t int_enb); +void usb0_host_setting_interrupt(uint8_t level); +void usb0_host_reset_module(uint16_t clockmode); +uint16_t usb0_host_get_buf_size(uint16_t pipe); +uint16_t usb0_host_get_mxps(uint16_t pipe); +void usb0_host_enable_brdy_int(uint16_t pipe); +void usb0_host_disable_brdy_int(uint16_t pipe); +void usb0_host_clear_brdy_sts(uint16_t pipe); +void usb0_host_enable_bemp_int(uint16_t pipe); +void usb0_host_disable_bemp_int(uint16_t pipe); +void usb0_host_clear_bemp_sts(uint16_t pipe); +void usb0_host_enable_nrdy_int(uint16_t pipe); +void usb0_host_disable_nrdy_int(uint16_t pipe); +void usb0_host_clear_nrdy_sts(uint16_t pipe); +void usb0_host_set_pid_buf(uint16_t pipe); +void usb0_host_set_pid_nak(uint16_t pipe); +void usb0_host_set_pid_stall(uint16_t pipe); +void usb0_host_clear_pid_stall(uint16_t pipe); +uint16_t usb0_host_get_pid(uint16_t pipe); +void usb0_host_set_sqclr(uint16_t pipe); +void usb0_host_set_sqset(uint16_t pipe); +void usb0_host_set_csclr(uint16_t pipe); +void usb0_host_aclrm(uint16_t pipe); +void usb0_host_set_aclrm(uint16_t pipe); +void usb0_host_clr_aclrm(uint16_t pipe); +uint16_t usb0_host_get_sqmon(uint16_t pipe); +uint16_t usb0_host_get_inbuf(uint16_t pipe); + +/* ==== host ==== */ +void usb0_host_init_pipe_status(void); +int32_t usb0_host_CtrlTransStart(uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len, uint8_t *Buf); +void usb0_host_SetupStage(uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len); +void usb0_host_CtrlReadStart(uint32_t Bsize, uint8_t *Table); +uint16_t usb0_host_CtrlWriteStart(uint32_t Bsize, uint8_t *Table); +void usb0_host_StatusStage(void); +void usb0_host_get_devadd(uint16_t addr, uint16_t *devadd); +void usb0_host_set_devadd(uint16_t addr, uint16_t *devadd); +void usb0_host_InitModule(void); +uint16_t usb0_host_CheckAttach(void); +void usb0_host_UsbDetach(void); +void usb0_host_UsbDetach2(void); +void usb0_host_UsbAttach(void); +uint16_t usb0_host_UsbBusReset(void); +int32_t usb0_host_UsbResume(void); +int32_t usb0_host_UsbSuspend(void); +void usb0_host_Enable_DetachINT(void); +void usb0_host_Disable_DetachINT(void); +void usb0_host_UsbStateManager(void); + + +#endif /* USB0_HOST_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/inc/usb0_host_api.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,112 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_api.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB0_HOST_API_H +#define USB0_HOST_API_H + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Variable Externs +*******************************************************************************/ + + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +void usb0_host_interrupt(uint32_t int_sense); +void usb0_host_dma_interrupt_d0fifo(uint32_t int_sense); +void usb0_host_dma_interrupt_d1fifo(uint32_t int_sense); + +uint16_t usb0_api_host_init(uint8_t int_level, uint16_t mode, uint16_t clockmode); +int32_t usb0_api_host_enumeration(uint16_t devadr); +int32_t usb0_api_host_detach(void); +int32_t usb0_api_host_data_in(uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t usb0_api_host_data_out(uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t usb0_api_host_control_transfer(uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len, uint8_t *Buf); +int32_t usb0_api_host_set_endpoint(uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t *configdescriptor); +int32_t usb0_api_host_clear_endpoint(USB_HOST_CFG_PIPETBL_t *user_table); +int32_t usb0_api_host_clear_endpoint_pipe(uint16_t pipe_sel, USB_HOST_CFG_PIPETBL_t *user_table); +uint16_t usb0_api_host_SetEndpointTable(uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t* Table); +int32_t usb0_api_host_data_count(uint16_t pipe, uint32_t *data_count); + +int32_t usb0_api_host_GetDeviceDescriptor(uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t usb0_api_host_GetConfigDescriptor(uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t usb0_api_host_SetConfig(uint16_t devadr, uint16_t confignum); +int32_t usb0_api_host_SetInterface(uint16_t devadr, uint16_t interface_alt, uint16_t interface_index); +int32_t usb0_api_host_ClearStall(uint16_t devadr, uint16_t ep_dir); +uint16_t usb0_api_host_GetUsbDeviceState(void); + +void usb0_api_host_elt_4_4(void); +void usb0_api_host_elt_4_5(void); +void usb0_api_host_elt_4_6(void); +void usb0_api_host_elt_4_7(void); +void usb0_api_host_elt_4_8(void); +void usb0_api_host_elt_4_9(void); +void usb0_api_host_elt_get_desc(void); + +void usb0_host_EL_ModeInit(void); +void usb0_host_EL_SetUACT(void); +void usb0_host_EL_ClearUACT(void); +void usb0_host_EL_SetTESTMODE(uint16_t mode); +void usb0_host_EL_ClearNRDYSTS(uint16_t pipe); +uint16_t usb0_host_EL_GetINTSTS1(void); +void usb0_host_EL_UsbBusReset(void); +void usb0_host_EL_UsbAttach(void); +void usb0_host_EL_SetupStage(uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len); +void usb0_host_EL_StatusStage(void); +void usb0_host_EL_CtrlReadStart(uint32_t Bsize, uint8_t *Table); +int32_t usb0_host_EL_UsbSuspend(void); +int32_t usb0_host_EL_UsbResume(void); + +#if 0 /* prototype in devdrv_usb_host_api.h */ +uint16_t Userdef_USB_usb0_host_d0fifo_dmaintid(void); +uint16_t Userdef_USB_usb0_host_d1fifo_dmaintid(void); +void Userdef_USB_usb0_host_attach(void); +void Userdef_USB_usb0_host_detach(void); +void Userdef_USB_usb0_host_delay_1ms(void); +void Userdef_USB_usb0_host_delay_xms(uint32_t msec); +void Userdef_USB_usb0_host_delay_10us(uint32_t usec); +void Userdef_USB_usb0_host_delay_500ns(void); +void Userdef_USB_usb0_host_start_dma(USB_HOST_DMA_t *dma, uint16_t dfacc); +uint32_t Userdef_USB_usb0_host_stop_dma0(void); +uint32_t Userdef_USB_usb0_host_stop_dma1(void); +#endif + +#endif /* USB0_HOST_API_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/inc/usb0_host_dmacdrv.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,139 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_dmacdrv.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB0_HOST_DMACDRV_H +#define USB0_HOST_DMACDRV_H + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ +typedef struct dmac_transinfo +{ + uint32_t src_addr; /* Transfer source address */ + uint32_t dst_addr; /* Transfer destination address */ + uint32_t count; /* Transfer byte count */ + uint32_t src_size; /* Transfer source data size */ + uint32_t dst_size; /* Transfer destination data size */ + uint32_t saddr_dir; /* Transfer source address direction */ + uint32_t daddr_dir; /* Transfer destination address direction */ +} dmac_transinfo_t; + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +/* ==== Transfer specification of the sample program ==== */ +#define DMAC_SAMPLE_SINGLE (0) /* Single transfer */ +#define DMAC_SAMPLE_CONTINUATION (1) /* Continuous transfer (use REN bit) */ + +/* ==== DMA modes ==== */ +#define DMAC_MODE_REGISTER (0) /* Register mode */ +#define DMAC_MODE_LINK (1) /* Link mode */ + +/* ==== Transfer requests ==== */ +#define DMAC_REQ_MODE_EXT (0) /* External request */ +#define DMAC_REQ_MODE_PERI (1) /* On-chip peripheral module request */ +#define DMAC_REQ_MODE_SOFT (2) /* Auto-request (request by software) */ + +/* ==== DMAC transfer sizes ==== */ +#define DMAC_TRANS_SIZE_8 (0) /* 8 bits */ +#define DMAC_TRANS_SIZE_16 (1) /* 16 bits */ +#define DMAC_TRANS_SIZE_32 (2) /* 32 bits */ +#define DMAC_TRANS_SIZE_64 (3) /* 64 bits */ +#define DMAC_TRANS_SIZE_128 (4) /* 128 bits */ +#define DMAC_TRANS_SIZE_256 (5) /* 256 bits */ +#define DMAC_TRANS_SIZE_512 (6) /* 512 bits */ +#define DMAC_TRANS_SIZE_1024 (7) /* 1024 bits */ + +/* ==== Address increment for transferring ==== */ +#define DMAC_TRANS_ADR_NO_INC (1) /* Not increment */ +#define DMAC_TRANS_ADR_INC (0) /* Increment */ + +/* ==== Method for detecting DMA request ==== */ +#define DMAC_REQ_DET_FALL (0) /* Falling edge detection */ +#define DMAC_REQ_DET_RISE (1) /* Rising edge detection */ +#define DMAC_REQ_DET_LOW (2) /* Low level detection */ +#define DMAC_REQ_DET_HIGH (3) /* High level detection */ + +/* ==== Request Direction ==== */ +#define DMAC_REQ_DIR_SRC (0) /* DMAREQ is the source/ DMAACK is active when reading */ +#define DMAC_REQ_DIR_DST (1) /* DMAREQ is the destination/ DMAACK is active when writing */ + +/* ==== Descriptors ==== */ +#define DMAC_DESC_HEADER (0) /* Header */ +#define DMAC_DESC_SRC_ADDR (1) /* Source Address */ +#define DMAC_DESC_DST_ADDR (2) /* Destination Address */ +#define DMAC_DESC_COUNT (3) /* Transaction Byte */ +#define DMAC_DESC_CHCFG (4) /* Channel Confg */ +#define DMAC_DESC_CHITVL (5) /* Channel Interval */ +#define DMAC_DESC_CHEXT (6) /* Channel Extension */ +#define DMAC_DESC_LINK_ADDR (7) /* Link Address */ + +/* ==== On-chip peripheral module requests ===== */ +typedef enum dmac_request_factor +{ + DMAC_REQ_USB0_DMA0_TX, /* USB_0 channel 0 transmit FIFO empty */ + DMAC_REQ_USB0_DMA0_RX, /* USB_0 channel 0 receive FIFO full */ + DMAC_REQ_USB0_DMA1_TX, /* USB_0 channel 1 transmit FIFO empty */ + DMAC_REQ_USB0_DMA1_RX, /* USB_0 channel 1 receive FIFO full */ + DMAC_REQ_USB1_DMA0_TX, /* USB_1 channel 0 transmit FIFO empty */ + DMAC_REQ_USB1_DMA0_RX, /* USB_1 channel 0 receive FIFO full */ + DMAC_REQ_USB1_DMA1_TX, /* USB_1 channel 1 transmit FIFO empty */ + DMAC_REQ_USB1_DMA1_RX, /* USB_1 channel 1 receive FIFO full */ +} dmac_request_factor_t; + + +/******************************************************************************* +Variable Externs +*******************************************************************************/ + + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +void usb0_host_DMAC1_PeriReqInit(const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction); +int32_t usb0_host_DMAC1_Open(uint32_t req); +void usb0_host_DMAC1_Close(uint32_t * remain); +void usb0_host_DMAC1_Load_Set(uint32_t src_addr, uint32_t dst_addr, uint32_t count); + +void usb0_host_DMAC2_PeriReqInit(const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction); +int32_t usb0_host_DMAC2_Open(uint32_t req); +void usb0_host_DMAC2_Close(uint32_t * remain); +void usb0_host_DMAC2_Load_Set(uint32_t src_addr, uint32_t dst_addr, uint32_t count); + +#endif /* USB0_HOST_DMACDRV_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/src/common/usb0_host_dataio.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,2835 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_dataio.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +static uint16_t g_usb0_host_mbw[(USB_HOST_MAX_PIPE_NO + 1)]; + +static void usb0_host_start_receive_trns_c(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb0_host_start_receive_trns_d0(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb0_host_start_receive_trns_d1(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb0_host_start_receive_dma_d0(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb0_host_start_receive_dma_d1(uint16_t pipe, uint32_t size, uint8_t *data); +static uint16_t usb0_host_read_dma_d0(uint16_t pipe); +static uint16_t usb0_host_read_dma_d1(uint16_t pipe); +static uint16_t usb0_host_write_dma_d0(uint16_t pipe); +static uint16_t usb0_host_write_dma_d1(uint16_t pipe); + +static void usb0_host_read_c_fifo(uint16_t pipe, uint16_t count); +static void usb0_host_write_c_fifo(uint16_t Pipe, uint16_t count); +static void usb0_host_read_d0_fifo(uint16_t pipe, uint16_t count); +static void usb0_host_write_d0_fifo(uint16_t pipe, uint16_t count); +static void usb0_host_read_d1_fifo(uint16_t pipe, uint16_t count); +static void usb0_host_write_d1_fifo(uint16_t pipe, uint16_t count); + +static void usb0_host_clear_transaction_counter(uint16_t pipe); +static void usb0_host_set_transaction_counter(uint16_t pipe, uint32_t count); + +static uint32_t usb0_host_com_get_dmasize(uint32_t trncount, uint32_t dtptr); + +static uint16_t usb0_host_set_dfacc_d0(uint16_t mbw, uint32_t count); +static uint16_t usb0_host_set_dfacc_d1(uint16_t mbw, uint32_t count); + + +/******************************************************************************* +* Function Name: usb0_host_start_send_transfer +* Description : Starts the USB data communication using pipe specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data data Address +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_start_send_transfer (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t status; + uint16_t usefifo; + uint16_t mbw; + + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + usb0_host_clear_bemp_sts(pipe); + usb0_host_clear_brdy_sts(pipe); + usb0_host_clear_nrdy_sts(pipe); + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + + usefifo = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + case USB_HOST_D0FIFO_DMA: + usefifo = USB_HOST_D0USE; + break; + + case USB_HOST_D1FIFO_USE: + case USB_HOST_D1FIFO_DMA: + usefifo = USB_HOST_D1USE; + break; + + default: + usefifo = USB_HOST_CUSE; + break; + }; + + usb0_host_set_curpipe(USB_HOST_PIPE0, usefifo, USB_HOST_NO, mbw); + + usb0_host_clear_transaction_counter(pipe); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + status = usb0_host_write_buffer(pipe); + + if (status != USB_HOST_FIFOERROR) + { + usb0_host_set_pid_buf(pipe); + } + + return status; +} + +/******************************************************************************* +* Function Name: usb0_host_write_buffer +* Description : Writes data in the buffer allocated in the pipe specified by +* : the argument. The FIFO for using is set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_write_buffer (uint16_t pipe) +{ + uint16_t status; + uint16_t usefifo; + + g_usb0_host_PipeIgnore[pipe] = 0; + usefifo = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + status = usb0_host_write_buffer_d0(pipe); + break; + + case USB_HOST_D1FIFO_USE: + status = usb0_host_write_buffer_d1(pipe); + break; + + case USB_HOST_D0FIFO_DMA: + status = usb0_host_write_dma_d0(pipe); + break; + + case USB_HOST_D1FIFO_DMA: + status = usb0_host_write_dma_d1(pipe); + break; + + default: + status = usb0_host_write_buffer_c(pipe); + break; + }; + + switch (status) + { + case USB_HOST_WRITING: /* Continue of data write */ + usb0_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + usb0_host_enable_brdy_int(pipe); /* Enable Ready Interrupt */ + break; + + case USB_HOST_WRITEEND: /* End of data write */ + case USB_HOST_WRITESHRT: /* End of data write */ + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + + usb0_host_clear_nrdy_sts(pipe); + usb0_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + + /* for last transfer */ + usb0_host_enable_bemp_int(pipe); /* Enable Empty Interrupt */ + break; + + case USB_HOST_WRITEDMA: /* DMA write */ + usb0_host_clear_nrdy_sts(pipe); + usb0_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + usb0_host_disable_bemp_int(pipe); /* Disable Empty Interrupt */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_write_buffer_c +* Description : Writes data in the buffer allocated in the pipe specified in +* : the argument. Writes data by CPU transfer using CFIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_write_buffer_c (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + + if (pipe == USB_HOST_PIPE0) + { + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_CFIFO_WRITE, mbw); + } + else + { + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_NO, mbw); + } + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb0_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb0_host_write_c_fifo(pipe, (uint16_t)count); + + if (g_usb0_host_data_count[pipe] < (uint32_t)size) + { + g_usb0_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB200.CFIFOCTR, + USB_CFIFOCTR_BVAL_SHIFT, + USB_CFIFOCTR_BVAL) == 0) + { + USB200.CFIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb0_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_write_buffer_d0 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by CPU transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_write_buffer_d0 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D0USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb0_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb0_host_write_d0_fifo(pipe, (uint16_t)count); + + if (g_usb0_host_data_count[pipe] < (uint32_t)size) + { + g_usb0_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB200.D0FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + USB200.D0FIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb0_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_write_buffer_d1 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by CPU transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_write_buffer_d1 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D1USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb0_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb0_host_write_d1_fifo(pipe, (uint16_t)count); + + if (g_usb0_host_data_count[pipe] < (uint32_t)size) + { + g_usb0_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB200.D1FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + USB200.D1FIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb0_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_write_dma_d0 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by DMA transfer using D0FIFO. +* : The DMA-ch for using is specified by Userdef_USB_usb0_host_start_dma(). +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND : Write end +* : USB_HOST_WRITESHRT : short data +* : USB_HOST_WRITING : Continue of data write +* : USB_HOST_WRITEDMA : Write DMA +* : USB_HOST_FIFOERROR : FIFO status +*******************************************************************************/ +static uint16_t usb0_host_write_dma_d0 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + count = g_usb0_host_data_count[pipe]; + + if (count != 0) + { + g_usb0_host_DmaPipe[USB_HOST_D0FIFO] = pipe; + + if ((count % size) != 0) + { + g_usb0_host_DmaBval[USB_HOST_D0FIFO] = 1; + } + else + { + g_usb0_host_DmaBval[USB_HOST_D0FIFO] = 0; + } + + dfacc = usb0_host_set_dfacc_d0(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 0; /* 8bit transfer */ + } + + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].fifo = USB_HOST_D0FIFO_DMA; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].dir = USB_HOST_BUF2FIFO; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].buffer = (uint32_t)g_usb0_host_data_pointer[pipe]; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].bytes = count; + + Userdef_USB_usb0_host_start_dma(&g_usb0_host_DmaInfo[USB_HOST_D0FIFO], dfacc); + + usb0_host_set_curpipe2(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw, dfacc); + + RZA_IO_RegWrite_16(&USB200.D0FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + + g_usb0_host_data_count[pipe] = 0; + g_usb0_host_data_pointer[pipe] += count; + + status = USB_HOST_WRITEDMA; /* DMA write */ + } + else + { + if (RZA_IO_RegRead_16(&USB200.D0FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + RZA_IO_RegWrite_16(&USB200.D0FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); /* Short Packet */ + } + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_write_dma_d1 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by DMA transfer using D1FIFO. +* : The DMA-ch for using is specified by Userdef_USB_usb0_host_start_dma(). +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND : Write end +* : USB_HOST_WRITESHRT : short data +* : USB_HOST_WRITING : Continue of data write +* : USB_HOST_WRITEDMA : Write DMA +* : USB_HOST_FIFOERROR : FIFO status +*******************************************************************************/ +static uint16_t usb0_host_write_dma_d1 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + count = g_usb0_host_data_count[pipe]; + + if (count != 0) + { + g_usb0_host_DmaPipe[USB_HOST_D1FIFO] = pipe; + + if ((count % size) != 0) + { + g_usb0_host_DmaBval[USB_HOST_D1FIFO] = 1; + } + else + { + g_usb0_host_DmaBval[USB_HOST_D1FIFO] = 0; + } + + dfacc = usb0_host_set_dfacc_d1(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 0; /* 8bit transfer */ + } + + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].fifo = USB_HOST_D1FIFO_DMA; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].dir = USB_HOST_BUF2FIFO; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].buffer = (uint32_t)g_usb0_host_data_pointer[pipe]; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].bytes = count; + + Userdef_USB_usb0_host_start_dma(&g_usb0_host_DmaInfo[USB_HOST_D1FIFO], dfacc); + + usb0_host_set_curpipe2(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw, dfacc); + + RZA_IO_RegWrite_16(&USB200.D1FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + + g_usb0_host_data_count[pipe] = 0; + g_usb0_host_data_pointer[pipe] += count; + + status = USB_HOST_WRITEDMA; /* DMA write */ + } + else + { + if (RZA_IO_RegRead_16(&USB200.D1FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + RZA_IO_RegWrite_16(&USB200.D1FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); /* Short Packet */ + } + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_transfer +* Description : Starts USB data reception using the pipe specified in the argument. +* : The FIFO for using is set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +void usb0_host_start_receive_transfer (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t usefifo; + + usb0_host_clear_bemp_sts(pipe); + usb0_host_clear_brdy_sts(pipe); + usb0_host_clear_nrdy_sts(pipe); + + usefifo = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + usb0_host_start_receive_trns_d0(pipe, size, data); + break; + + case USB_HOST_D1FIFO_USE: + usb0_host_start_receive_trns_d1(pipe, size, data); + break; + + case USB_HOST_D0FIFO_DMA: + usb0_host_start_receive_dma_d0(pipe, size, data); + break; + + case USB_HOST_D1FIFO_DMA: + usb0_host_start_receive_dma_d1(pipe, size, data); + break; + + default: + usb0_host_start_receive_trns_c(pipe, size, data); + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_trns_c +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using CFIFO. +* : When storing data in the buffer allocated in the pipe specified in the +* : argument, BRDY interrupt is generated to read data +* : in the interrupt. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb0_host_start_receive_trns_c (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb0_host_set_pid_nak(pipe); + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_PipeIgnore[pipe] = 0; + + g_usb0_host_PipeDataSize[pipe] = size; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_CFIFO_READ, mbw); + USB200.CFIFOCTR = USB_HOST_BITBCLR; + + usb0_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + + usb0_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_trns_d0 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, BRDY interrupt is generated to read data in the +* : interrupt. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb0_host_start_receive_trns_d0 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb0_host_set_pid_nak(pipe); + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_PipeIgnore[pipe] = 0; + + g_usb0_host_PipeDataSize[pipe] = size; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, mbw); + + usb0_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + + usb0_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_trns_d1 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using D1FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, BRDY interrupt is generated to read data. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb0_host_start_receive_trns_d1 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb0_host_set_pid_nak(pipe); + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_PipeIgnore[pipe] = 0; + + g_usb0_host_PipeDataSize[pipe] = size; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, mbw); + + usb0_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + + usb0_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_dma_d0 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by DMA transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, delivered read request to DMAC to read data from +* : the buffer by DMAC. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb0_host_start_receive_dma_d0 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb0_host_set_pid_nak(pipe); + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_PipeIgnore[pipe] = 0; + + g_usb0_host_PipeDataSize[pipe] = 0; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, mbw); + + usb0_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + usb0_host_read_dma(pipe); + + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + } + else + { + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + } + + usb0_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_dma_d1 +* Description : Read data from the buffer allocated in the pipe specified in the argument. +* : Reads data by DMA transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, delivered read request to DMAC to read data from +* : the buffer by DMAC. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb0_host_start_receive_dma_d1 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb0_host_set_pid_nak(pipe); + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_PipeIgnore[pipe] = 0; + + g_usb0_host_PipeDataSize[pipe] = 0; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, mbw); + + usb0_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + usb0_host_read_dma(pipe); + + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + } + else + { + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + } + + usb0_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_read_buffer +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Uses FIF0 set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_read_buffer (uint16_t pipe) +{ + uint16_t status; + + g_usb0_host_PipeIgnore[pipe] = 0; + + if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_USE) + { + status = usb0_host_read_buffer_d0(pipe); + } + else if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_USE) + { + status = usb0_host_read_buffer_d1(pipe); + } + else + { + status = usb0_host_read_buffer_c(pipe); + } + + switch (status) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb0_host_disable_brdy_int(pipe); + g_usb0_host_PipeDataSize[pipe] -= g_usb0_host_data_count[pipe]; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + break; + + case USB_HOST_READOVER: /* buffer over */ + if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_USE) + { + USB200.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_USE) + { + USB200.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + USB200.CFIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#else + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; +#endif + g_usb0_host_PipeDataSize[pipe] -= g_usb0_host_data_count[pipe]; + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_buffer_c +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using CFIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_read_buffer_c (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb0_host_data_count[pipe]; + } + else if (g_usb0_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + } + + if (count == 0) /* 0 length packet */ + { + USB200.CFIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb0_host_read_c_fifo(pipe, (uint16_t)count); + } + + g_usb0_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_buffer_d0 +* Description : Reads data from the buffer allocated in the pipe specified in +* : the argument. +* : Reads data by CPU transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_read_buffer_d0 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t pipebuf_size; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D0USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb0_host_data_count[pipe]; + } + else if (g_usb0_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + else + { + pipebuf_size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + } + } + + if (count == 0) /* 0 length packet */ + { + USB200.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb0_host_read_d0_fifo(pipe, (uint16_t)count); + } + + g_usb0_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_buffer_d1 +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by CPU transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_read_buffer_d1 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t pipebuf_size; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D1USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb0_host_data_count[pipe]; + } + else if (g_usb0_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) !=0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + else + { + pipebuf_size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + } + } + + if (count == 0) /* 0 length packet */ + { + USB200.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb0_host_read_d1_fifo(pipe, (uint16_t)count); + } + + g_usb0_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_dma +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by DMA transfer using D0FIFO or D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_read_dma (uint16_t pipe) +{ + uint16_t status; + + g_usb0_host_PipeIgnore[pipe] = 0; + + if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_DMA) + { + status = usb0_host_read_dma_d0(pipe); + } + else + { + status = usb0_host_read_dma_d1(pipe); + } + + switch (status) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READZERO: /* End of data read */ + usb0_host_disable_brdy_int(pipe); + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb0_host_disable_brdy_int(pipe); + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + g_usb0_host_PipeDataSize[pipe] -= g_usb0_host_data_count[pipe]; + } + break; + + case USB_HOST_READOVER: /* buffer over */ + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + g_usb0_host_PipeDataSize[pipe] -= g_usb0_host_data_count[pipe]; + } +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#else + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; +#endif + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_dma_d0 +* Description : Writes data in the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by DMA transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +static uint16_t usb0_host_read_dma_d0 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + uint16_t pipebuf_size; + + g_usb0_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_READY; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + count = g_usb0_host_data_count[pipe]; + status = USB_HOST_READING; + } + else + { + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + count = g_usb0_host_data_count[pipe]; + } + else if (g_usb0_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + else + { + pipebuf_size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + } + } + + if (count == 0) /* 0 length packet */ + { + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + USB200.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear B_CLR */ + status = USB_HOST_READZERO; /* Null Packet receive */ + } + else + { + usb0_host_set_curpipe(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + /* transaction counter No set */ + /* FRDY = 1, DTLN = 0 -> BRDY */ + } + } + else + { + dfacc = usb0_host_set_dfacc_d0(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 0; /* 8bit transfer */ + } + + g_usb0_host_DmaPipe[USB_HOST_D0FIFO] = pipe; /* not use in read operation */ + g_usb0_host_DmaBval[USB_HOST_D0FIFO] = 0; /* not use in read operation */ + + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].fifo = USB_HOST_D0FIFO_DMA; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].dir = USB_HOST_FIFO2BUF; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].buffer = (uint32_t)g_usb0_host_data_pointer[pipe]; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].bytes = count; + + if (status == USB_HOST_READING) + { + g_usb0_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_BUSY; + } + else + { + g_usb0_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_BUSYEND; + } + + Userdef_USB_usb0_host_start_dma(&g_usb0_host_DmaInfo[USB_HOST_D0FIFO], dfacc); + + usb0_host_set_curpipe2(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw, dfacc); + + RZA_IO_RegWrite_16(&USB200.D0FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + g_usb0_host_data_count[pipe] -= count; + g_usb0_host_data_pointer[pipe] += count; + g_usb0_host_PipeDataSize[pipe] += count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_dma_d1 +* Description : Reads data from the buffer allocated in the pipe specified in +* : the argument. +* : Reads data by DMA transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +static uint16_t usb0_host_read_dma_d1 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + uint16_t pipebuf_size; + + g_usb0_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_READY; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + count = g_usb0_host_data_count[pipe]; + status = USB_HOST_READING; + } + else + { + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + count = g_usb0_host_data_count[pipe]; + } + else if (g_usb0_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + else + { + pipebuf_size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + } + } + + if (count == 0) /* 0 length packet */ + { + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + USB200.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + status = USB_HOST_READZERO; /* Null Packet receive */ + } + else + { + usb0_host_set_curpipe(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + /* transaction counter No set */ + /* FRDY = 1, DTLN = 0 -> BRDY */ + } + } + else + { + dfacc = usb0_host_set_dfacc_d1(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 0; /* 8bit transfer */ + } + + g_usb0_host_DmaPipe[USB_HOST_D1FIFO] = pipe; /* not use in read operation */ + g_usb0_host_DmaBval[USB_HOST_D1FIFO] = 0; /* not use in read operation */ + + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].fifo = USB_HOST_D1FIFO_DMA; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].dir = USB_HOST_FIFO2BUF; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].buffer = (uint32_t)g_usb0_host_data_pointer[pipe]; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].bytes = count; + + if (status == USB_HOST_READING) + { + g_usb0_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_BUSY; + } + else + { + g_usb0_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_BUSYEND; + } + + Userdef_USB_usb0_host_start_dma(&g_usb0_host_DmaInfo[USB_HOST_D1FIFO], dfacc); + + usb0_host_set_curpipe2(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw, dfacc); + + RZA_IO_RegWrite_16(&USB200.D1FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + g_usb0_host_data_count[pipe] -= count; + g_usb0_host_data_pointer[pipe] += count; + g_usb0_host_PipeDataSize[pipe] += count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_change_fifo_port +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument. After allocating FIF0, waits in the software +* : till the corresponding pipe becomes ready. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* Return Value : USB_HOST_FIFOERROR ; Error +* : Others ; CFIFOCTR/D0FIFOCTR/D1FIFOCTR Register Value +*******************************************************************************/ +uint16_t usb0_host_change_fifo_port (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw) +{ + uint16_t buffer; + uint32_t loop; + volatile uint32_t loop2; + + usb0_host_set_curpipe(pipe, fifosel, isel, mbw); + + for (loop = 0; loop < 4; loop++) + { + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB200.CFIFOCTR; + break; + + case USB_HOST_D0USE: + case USB_HOST_D0DMA: + buffer = USB200.D0FIFOCTR; + break; + + case USB_HOST_D1USE: + case USB_HOST_D1DMA: + buffer = USB200.D1FIFOCTR; + break; + + default: + buffer = 0; + break; + } + + if ((buffer & USB_HOST_BITFRDY) == USB_HOST_BITFRDY) + { + return buffer; + } + + loop2 = 25; + + while (loop2-- > 0) + { + /* wait */ + } + } + + return USB_HOST_FIFOERROR; +} + +/******************************************************************************* +* Function Name: usb0_host_set_curpipe +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* Return Value : none +*******************************************************************************/ +void usb0_host_set_curpipe (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw) +{ + uint16_t buffer; + uint32_t loop; + volatile uint32_t loop2; + + g_usb0_host_mbw[pipe] = mbw; + + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB200.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(~isel & USB_HOST_BITISEL); + USB200.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(isel | pipe | mbw); + USB200.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D0DMA: + case USB_HOST_D0USE: + buffer = USB200.D0FIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + USB200.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB200.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D1DMA: + case USB_HOST_D1USE: + buffer = USB200.D1FIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + USB200.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB200.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + default: + break; + } + + /* Cautions !!! + * Depending on the external bus speed of CPU, you may need to wait for 450ns here. + * For details, please look at the data sheet. */ + loop2 = 100; + + while (loop2-- > 0) + { + /* wait */ + } +} + +/******************************************************************************* +* Function Name: usb0_host_set_curpipe2 +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument.(DFACC) +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* : uint16_t dfacc ; DFACC Access mode +* Return Value : none +*******************************************************************************/ +void usb0_host_set_curpipe2 (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw, uint16_t dfacc) +{ + uint16_t buffer; + uint32_t loop; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + uint32_t dummy; +#endif + volatile uint32_t loop2; + + g_usb0_host_mbw[pipe] = mbw; + + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB200.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(~isel & USB_HOST_BITISEL); + USB200.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(isel | pipe | mbw); + USB200.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D0DMA: + case USB_HOST_D0USE: + buffer = USB200.D0FIFOSEL; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + + if (dfacc != 0) + { + buffer |= (uint16_t)(USB_HOST_BITMBW_32); + } +#else + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); +#endif + USB200.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + +#ifdef __USB_HOST_DF_ACC_ENABLE__ + if (dfacc != 0) + { + dummy = USB200.D0FIFO.UINT32; + } +#endif + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB200.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D1DMA: + case USB_HOST_D1USE: + buffer = USB200.D1FIFOSEL; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + + if (dfacc != 0) + { + buffer |= (uint16_t)(USB_HOST_BITMBW_32); + } +#else + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); +#endif + USB200.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + +#ifdef __USB_HOST_DF_ACC_ENABLE__ + if (dfacc != 0) + { + dummy = USB200.D1FIFO.UINT32; + loop = dummy; // avoid warning. + } +#endif + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB200.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + default: + break; + } + + /* Cautions !!! + * Depending on the external bus speed of CPU, you may need to wait for 450ns here. + * For details, please look at the data sheet. */ + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } +} + +/******************************************************************************* +* Function Name: usb0_host_write_c_fifo +* Description : Writes data in CFIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_write_c_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB200.CFIFO.UINT8[HH] = *g_usb0_host_data_pointer[pipe]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB200.CFIFO.UINT16[H] = *((uint16_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB200.CFIFO.UINT32 = *((uint32_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_read_c_fifo +* Description : Reads data from CFIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_read_c_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb0_host_data_pointer[pipe] = USB200.CFIFO.UINT8[HH]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb0_host_data_pointer[pipe]) = USB200.CFIFO.UINT16[H]; + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb0_host_data_pointer[pipe]) = USB200.CFIFO.UINT32; + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_write_d0_fifo +* Description : Writes data in D0FIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_write_d0_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB200.D0FIFO.UINT8[HH] = *g_usb0_host_data_pointer[pipe]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB200.D0FIFO.UINT16[H] = *((uint16_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB200.D0FIFO.UINT32 = *((uint32_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_read_d0_fifo +* Description : Reads data from D0FIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating DOFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t Pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_read_d0_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb0_host_data_pointer[pipe] = USB200.D0FIFO.UINT8[HH]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb0_host_data_pointer[pipe]) = USB200.D0FIFO.UINT16[H]; + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb0_host_data_pointer[pipe]) = USB200.D0FIFO.UINT32; + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_write_d1_fifo +* Description : Writes data in D1FIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating D1FIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_write_d1_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB200.D1FIFO.UINT8[HH] = *g_usb0_host_data_pointer[pipe]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB200.D1FIFO.UINT16[H] = *((uint16_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB200.D1FIFO.UINT32 = *((uint32_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_read_d1_fifo +* Description : Reads data from D1FIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating D1FIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_read_d1_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb0_host_data_pointer[pipe] = USB200.D1FIFO.UINT8[HH]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb0_host_data_pointer[pipe]) = USB200.D1FIFO.UINT16[H]; + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb0_host_data_pointer[pipe]) = USB200.D1FIFO.UINT32; + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_com_get_dmasize +* Description : Calculates access width of DMA transfer by the argument to + return as the Return Value. +* Arguments : uint32_t trncount : transfer byte +* : uint32_t dtptr : transfer data pointer +* Return Value : DMA transfer size : 0 8bit +* : : 1 16bit +* : : 2 32bit +*******************************************************************************/ +static uint32_t usb0_host_com_get_dmasize (uint32_t trncount, uint32_t dtptr) +{ + uint32_t size; + + if (((trncount & 0x0001) != 0) || ((dtptr & 0x00000001) != 0)) + { + /* When transfer byte count is odd */ + /* or transfer data area is 8-bit alignment */ + size = 0; /* 8bit */ + } + else if (((trncount & 0x0003) != 0) || ((dtptr & 0x00000003) != 0)) + { + /* When the transfer byte count is multiples of 2 */ + /* or the transfer data area is 16-bit alignment */ + size = 1; /* 16bit */ + } + else + { + /* When the transfer byte count is multiples of 4 */ + /* or the transfer data area is 32-bit alignment */ + size = 2; /* 32bit */ + } + + return size; +} + +/******************************************************************************* +* Function Name: usb0_host_get_mbw +* Description : Calculates access width of DMA to return the value set in MBW. +* Arguments : uint32_t trncount : transfer byte +* : uint32_t dtptr : transfer data pointer +* Return Value : FIFO transfer size : USB_HOST_BITMBW_8 8bit +* : : USB_HOST_BITMBW_16 16bit +* : : USB_HOST_BITMBW_32 32bit +*******************************************************************************/ +uint16_t usb0_host_get_mbw (uint32_t trncount, uint32_t dtptr) +{ + uint32_t size; + uint16_t mbw; + + size = usb0_host_com_get_dmasize(trncount, dtptr); + + if (size == 0) + { + /* 8bit */ + mbw = USB_HOST_BITMBW_8; + } + else if (size == 1) + { + /* 16bit */ + mbw = USB_HOST_BITMBW_16; + } + else + { + /* 32bit */ + mbw = USB_HOST_BITMBW_32; + } + + return mbw; +} + +/******************************************************************************* +* Function Name: usb0_host_set_transaction_counter +* Description : Sets transaction counter by the argument(PIPEnTRN). +* : Clears transaction before setting to enable transaction counter setting. +* Arguments : uint16_t pipe ; Pipe number +* : uint32_t bsize : Data transfer size +* Return Value : none +*******************************************************************************/ +static void usb0_host_set_transaction_counter (uint16_t pipe, uint32_t bsize) +{ + uint16_t mxps; + uint16_t cnt; + + if (bsize == 0) + { + return; + } + + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if ((bsize % mxps) == 0) + { + cnt = (uint16_t)(bsize / mxps); + } + else + { + cnt = (uint16_t)((bsize / mxps) + 1); + } + + switch (pipe) + { + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE1TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE1TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE2TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE2TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE3TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE3TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE4TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE4TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE5TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE5TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE9TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE9TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_clear_transaction_counter +* Description : Clears the transaction counter by the argument. +* : After executing this function, the transaction counter is invalid. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb0_host_clear_transaction_counter (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE1TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE2TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE3TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE4TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE5TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE9TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_stop_transfer +* Description : Stops the USB transfer in the pipe specified by the argument. +* : After stopping the USB transfer, clears the buffer allocated in +* : the pipe. +* : After executing this function, allocation in FIF0 becomes USB_HOST_PIPE0; +* : invalid. After executing this function, BRDY/NRDY/BEMP interrupt +* : in the corresponding pipe becomes invalid. Sequence bit is also +* : cleared. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_stop_transfer (uint16_t pipe) +{ + uint16_t usefifo; + uint32_t remain; + + usb0_host_set_pid_nak(pipe); + + usefifo = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + usb0_host_clear_transaction_counter(pipe); + USB200.D0FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D1FIFO_USE: + usb0_host_clear_transaction_counter(pipe); + USB200.D1FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D0FIFO_DMA: + remain = Userdef_USB_usb0_host_stop_dma0(); + usb0_host_dma_stop_d0(pipe, remain); + usb0_host_clear_transaction_counter(pipe); + USB200.D0FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D1FIFO_DMA: + remain = Userdef_USB_usb0_host_stop_dma1(); + usb0_host_dma_stop_d1(pipe, remain); + usb0_host_clear_transaction_counter(pipe); + USB200.D1FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + default: + usb0_host_clear_transaction_counter(pipe); + USB200.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + } + + /* Interrupt of pipe set is disabled */ + usb0_host_disable_brdy_int(pipe); + usb0_host_disable_nrdy_int(pipe); + usb0_host_disable_bemp_int(pipe); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + usb0_host_set_csclr(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_set_dfacc_d0 +* Description : Sets the DFACC setting value in D0FIFO using the transfer size. +* Arguments : uint16_t mbw ; MBW +* : uint16_t count ; data count +* Return Value : DFACC Access mode +*******************************************************************************/ +static uint16_t usb0_host_set_dfacc_d0 (uint16_t mbw, uint32_t count) +{ + uint16_t dfacc = 0; + +#ifndef __USB_HOST_DF_ACC_ENABLE__ + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; +#else + if (mbw == USB_HOST_BITMBW_32) + { + if ((count % 32) == 0) + { + /* 32byte transfer */ + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 2, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 2; + } + else if ((count % 16) == 0) + { + /* 16byte transfer */ + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 1, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 1; + } + else + { + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + } + else if (mbw == USB_HOST_BITMBW_16) + { + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + else + { + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } +#endif + + return dfacc; +} + +/******************************************************************************* +* Function Name: usb0_host_set_dfacc_d1 +* Description : Sets the DFACC setting value in D1FIFO using the transfer size. +* Arguments : uint16_t mbw ; MBW +* : uint16_t count ; data count +* Return Value : DFACC Access mode +*******************************************************************************/ +static uint16_t usb0_host_set_dfacc_d1 (uint16_t mbw, uint32_t count) +{ + uint16_t dfacc = 0; + +#ifndef __USB_HOST_DF_ACC_ENABLE__ + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; +#else + if (mbw == USB_HOST_BITMBW_32) + { + if ((count % 32) == 0) + { + /* 32byte transfer */ + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 2, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 2; + } + else if ((count % 16) == 0) + { + /* 16byte transfer */ + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 1, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 1; + } + else + { + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + } + else if (mbw == USB_HOST_BITMBW_16) + { + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + else + { + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } +#endif + + return dfacc; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/src/common/usb0_host_dma.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,355 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_dma.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +/* #include "usb0_host_dmacdrv.h" */ + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +static void usb0_host_dmaint(uint16_t fifo); +static void usb0_host_dmaint_buf2fifo(uint16_t pipe); +static void usb0_host_dmaint_fifo2buf(uint16_t pipe); + + +/******************************************************************************* +* Function Name: usb0_host_dma_stop_d0 +* Description : D0FIFO DMA stop +* Arguments : uint16_t pipe : pipe number +* : uint32_t remain : transfer byte +* Return Value : none +*******************************************************************************/ +void usb0_host_dma_stop_d0 (uint16_t pipe, uint32_t remain) +{ + uint16_t dtln; + uint16_t dfacc; + uint16_t buffer; + uint16_t sds_b = 1; + + dfacc = RZA_IO_RegRead_16(&USB200.D0FBCFG, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + if (dfacc == 2) + { + sds_b = 32; + } + else if (dfacc == 1) + { + sds_b = 16; + } + else + { + if (g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size == 2) + { + sds_b = 4; + } + else if (g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size == 1) + { + sds_b = 2; + } + else + { + sds_b = 1; + } + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + if (g_usb0_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + buffer = USB200.D0FIFOCTR; + dtln = (buffer & USB_HOST_BITDTLN); + + if ((dtln % sds_b) != 0) + { + remain += (sds_b - (dtln % sds_b)); + } + g_usb0_host_PipeDataSize[pipe] = (g_usb0_host_data_count[pipe] - remain); + g_usb0_host_data_count[pipe] = remain; + } + } + + RZA_IO_RegWrite_16(&USB200.D0FIFOSEL, + 0, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); +} + +/******************************************************************************* +* Function Name: usb0_host_dma_stop_d1 +* Description : D1FIFO DMA stop +* Arguments : uint16_t pipe : pipe number +* : uint32_t remain : transfer byte +* Return Value : none +*******************************************************************************/ +void usb0_host_dma_stop_d1 (uint16_t pipe, uint32_t remain) +{ + uint16_t dtln; + uint16_t dfacc; + uint16_t buffer; + uint16_t sds_b = 1; + + dfacc = RZA_IO_RegRead_16(&USB200.D1FBCFG, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + if (dfacc == 2) + { + sds_b = 32; + } + else if (dfacc == 1) + { + sds_b = 16; + } + else + { + if (g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size == 2) + { + sds_b = 4; + } + else if (g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size == 1) + { + sds_b = 2; + } + else + { + sds_b = 1; + } + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + if (g_usb0_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + buffer = USB200.D1FIFOCTR; + dtln = (buffer & USB_HOST_BITDTLN); + + if ((dtln % sds_b) != 0) + { + remain += (sds_b - (dtln % sds_b)); + } + g_usb0_host_PipeDataSize[pipe] = (g_usb0_host_data_count[pipe] - remain); + g_usb0_host_data_count[pipe] = remain; + } + } + + RZA_IO_RegWrite_16(&USB200.D1FIFOSEL, + 0, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); +} + +/******************************************************************************* +* Function Name: usb0_host_dma_interrupt_d0fifo +* Description : This function is DMA interrupt handler entry. +* : Execute usb1_host_dmaint() after disabling DMA interrupt in this function. +* : Disable DMA interrupt to DMAC executed when USB_HOST_D0FIFO_DMA is +* : specified by dma->fifo. +* : Register this function as DMA complete interrupt. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb0_host_dma_interrupt_d0fifo (uint32_t int_sense) +{ + usb0_host_dmaint(USB_HOST_D0FIFO); + g_usb0_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_READY; +} + +/******************************************************************************* +* Function Name: usb0_host_dma_interrupt_d1fifo +* Description : This function is DMA interrupt handler entry. +* : Execute usb0_host_dmaint() after disabling DMA interrupt in this function. +* : Disable DMA interrupt to DMAC executed when USB_HOST_D1FIFO_DMA is +* : specified by dma->fifo. +* : Register this function as DMA complete interrupt. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb0_host_dma_interrupt_d1fifo (uint32_t int_sense) +{ + usb0_host_dmaint(USB_HOST_D1FIFO); + g_usb0_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_READY; +} + +/******************************************************************************* +* Function Name: usb0_host_dmaint +* Description : This function is DMA transfer end interrupt +* Arguments : uint16_t fifo ; fifo number +* : ; USB_HOST_D0FIFO +* : ; USB_HOST_D1FIFO +* Return Value : none +*******************************************************************************/ +static void usb0_host_dmaint (uint16_t fifo) +{ + uint16_t pipe; + + pipe = g_usb0_host_DmaPipe[fifo]; + + if (g_usb0_host_DmaInfo[fifo].dir == USB_HOST_BUF2FIFO) + { + usb0_host_dmaint_buf2fifo(pipe); + } + else + { + usb0_host_dmaint_fifo2buf(pipe); + } +} + +/******************************************************************************* +* Function Name: usb0_host_dmaint_fifo2buf +* Description : Executes read completion from FIFO by DMAC. +* Arguments : uint16_t pipe : pipe number +* Return Value : none +*******************************************************************************/ +static void usb0_host_dmaint_fifo2buf (uint16_t pipe) +{ + uint32_t remain; + uint16_t useport; + + if (g_usb0_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + useport = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + if (useport == USB_HOST_D0FIFO_DMA) + { + remain = Userdef_USB_usb0_host_stop_dma0(); + usb0_host_dma_stop_d0(pipe, remain); + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + if (g_usb0_host_DmaStatus[USB_HOST_D0FIFO] == USB_HOST_DMA_BUSYEND) + { + USB200.D0FIFOCTR = USB_HOST_BITBCLR; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + else + { + usb0_host_enable_brdy_int(pipe); + } + } + } + else + { + remain = Userdef_USB_usb0_host_stop_dma1(); + usb0_host_dma_stop_d1(pipe, remain); + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + if (g_usb0_host_DmaStatus[USB_HOST_D1FIFO] == USB_HOST_DMA_BUSYEND) + { + USB200.D1FIFOCTR = USB_HOST_BITBCLR; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + else + { + usb0_host_enable_brdy_int(pipe); + } + } + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_dmaint_buf2fifo +* Description : Executes write completion in FIFO by DMAC. +* Arguments : uint16_t pipe : pipe number +* Return Value : none +*******************************************************************************/ +static void usb0_host_dmaint_buf2fifo (uint16_t pipe) +{ + uint16_t useport; + uint32_t remain; + + useport = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + if (useport == USB_HOST_D0FIFO_DMA) + { + remain = Userdef_USB_usb0_host_stop_dma0(); + usb0_host_dma_stop_d0(pipe, remain); + + if (g_usb0_host_DmaBval[USB_HOST_D0FIFO] != 0) + { + RZA_IO_RegWrite_16(&USB200.D0FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); + } + } + else + { + remain = Userdef_USB_usb0_host_stop_dma1(); + usb0_host_dma_stop_d1(pipe, remain); + + if (g_usb0_host_DmaBval[USB_HOST_D1FIFO] != 0) + { + RZA_IO_RegWrite_16(&USB200.D1FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); + } + } + + usb0_host_enable_bemp_int(pipe); +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/src/common/usb0_host_intrn.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,285 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_intrn.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#if(1) /* ohci_wrapp */ +#include "ohci_wrapp_RZ_A1_local.h" +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_brdy_int +* Description : Executes BRDY interrupt(USB_HOST_PIPE1-9). +* : According to the pipe that interrupt is generated in, +* : reads/writes buffer allocated in the pipe. +* : This function is executed in the BRDY interrupt handler. +* : This function clears BRDY interrupt status and BEMP interrupt +* : status. +* Arguments : uint16_t status ; BRDYSTS Register Value +* : uint16_t int_enb ; BRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_brdy_int (uint16_t status, uint16_t int_enb) +{ + uint32_t int_sense = 0; + uint16_t pipe; + uint16_t pipebit; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + pipebit = g_usb0_host_bit_set[pipe]; + + if ((status & pipebit) && (int_enb & pipebit)) + { + USB200.BRDYSTS = (uint16_t)~pipebit; + USB200.BEMPSTS = (uint16_t)~pipebit; + + if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_DMA) + { + if (g_usb0_host_DmaStatus[USB_HOST_D0FIFO] != USB_HOST_DMA_READY) + { + usb0_host_dma_interrupt_d0fifo(int_sense); + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + usb0_host_read_dma(pipe); + usb0_host_disable_brdy_int(pipe); + } + else + { + USB200.D0FIFOCTR = USB_HOST_BITBCLR; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + } + else if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_DMA) + { + if (g_usb0_host_DmaStatus[USB_HOST_D1FIFO] != USB_HOST_DMA_READY) + { + usb0_host_dma_interrupt_d1fifo(int_sense); + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + usb0_host_read_dma(pipe); + usb0_host_disable_brdy_int(pipe); + } + else + { + USB200.D1FIFOCTR = USB_HOST_BITBCLR; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + } + else + { + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 0) + { + usb0_host_read_buffer(pipe); + } + else + { + usb0_host_write_buffer(pipe); + } + } +#if(1) /* ohci_wrapp */ + switch (g_usb0_host_pipe_status[pipe]) + { + case USB_HOST_PIPE_DONE: + ohciwrapp_loc_TransEnd(pipe, TD_CC_NOERROR); + break; + case USB_HOST_PIPE_NORES: + case USB_HOST_PIPE_STALL: + case USB_HOST_PIPE_ERROR: + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); + break; + default: + /* Do Nothing */ + break; + } +#endif + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_nrdy_int +* Description : Executes NRDY interrupt(USB_HOST_PIPE1-9). +* : Checks NRDY interrupt cause by PID. When the cause if STALL, +* : regards the pipe state as STALL and ends the processing. +* : Then the cause is not STALL, increments the error count to +* : communicate again. When the error count is 3, determines +* : the pipe state as USB_HOST_PIPE_NORES and ends the processing. +* : This function is executed in the NRDY interrupt handler. +* : This function clears NRDY interrupt status. +* Arguments : uint16_t status ; NRDYSTS Register Value +* : uint16_t int_enb ; NRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_nrdy_int (uint16_t status, uint16_t int_enb) +{ + uint16_t pid; + uint16_t pipe; + uint16_t bitcheck; + + bitcheck = (uint16_t)(status & int_enb); + + USB200.NRDYSTS = (uint16_t)~status; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + if ((bitcheck&g_usb0_host_bit_set[pipe]) == g_usb0_host_bit_set[pipe]) + { + if (RZA_IO_RegRead_16(&USB200.SYSCFG0, + USB_SYSCFG_DCFM_SHIFT, + USB_SYSCFG_DCFM) == 1) + { + if (g_usb0_host_pipe_status[pipe] == USB_HOST_PIPE_WAIT) + { + pid = usb0_host_get_pid(pipe); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_STALL; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); +#endif + } + else + { +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_NORES; + ohciwrapp_loc_TransEnd(pipe, TD_CC_DEVICENOTRESPONDING); +#else + g_usb0_host_PipeIgnore[pipe]++; + + if (g_usb0_host_PipeIgnore[pipe] == 3) + { + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_NORES; + } + else + { + usb0_host_set_pid_buf(pipe); + } +#endif + } + } + } + else + { + /* USB Function */ + } + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_bemp_int +* Description : Executes BEMP interrupt(USB_HOST_PIPE1-9). +* Arguments : uint16_t status ; BEMPSTS Register Value +* : uint16_t int_enb ; BEMPENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_bemp_int (uint16_t status, uint16_t int_enb) +{ + uint16_t pid; + uint16_t pipe; + uint16_t bitcheck; + uint16_t inbuf; + + bitcheck = (uint16_t)(status & int_enb); + + USB200.BEMPSTS = (uint16_t)~status; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + if ((bitcheck&g_usb0_host_bit_set[pipe]) == g_usb0_host_bit_set[pipe]) + { + pid = usb0_host_get_pid(pipe); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_STALL; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); +#endif + } + else + { + inbuf = usb0_host_get_inbuf(pipe); + + if (inbuf == 0) + { + usb0_host_disable_bemp_int(pipe); + usb0_host_set_pid_nak(pipe); + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_NOERROR); +#endif + } + } + } + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/src/common/usb0_host_lib.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,1580 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_lib.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#if(1) /* ohci_wrapp */ +#include "MBRZA1H.h" /* INTC Driver Header */ +#else +#include "devdrv_intc.h" /* INTC Driver Header */ +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_enable_brdy_int +* Description : Enables BRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : BRDY. Enables BRDY interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_enable_brdy_int (uint16_t pipe) +{ + /* enable brdy interrupt */ + USB200.BRDYENB |= (uint16_t)g_usb0_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb0_host_disable_brdy_int +* Description : Disables BRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : BRDY. Enables BRDY interrupt in the pipe specified by the argument +* : in the disabled status. After disabling BRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_disable_brdy_int (uint16_t pipe) +{ + /* disable brdy interrupt */ + USB200.BRDYENB &= (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_clear_brdy_sts +* Description : Clear BRDY interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_clear_brdy_sts (uint16_t pipe) +{ + /* clear brdy status */ + USB200.BRDYSTS = (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_enable_bemp_int +* Description : Enables BEMP interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : BEMP. Enables BEMP interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BEMP, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_enable_bemp_int (uint16_t pipe) +{ + /* enable bemp interrupt */ + USB200.BEMPENB |= (uint16_t)g_usb0_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb0_host_disable_bemp_int +* Description : Disables BEMP interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : BEMP. Enables BEMP interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BEMP, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_disable_bemp_int (uint16_t pipe) +{ + /* disable bemp interrupt */ + USB200.BEMPENB &= (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_clear_bemp_sts +* Description : Clear BEMP interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_clear_bemp_sts (uint16_t pipe) +{ + /* clear bemp status */ + USB200.BEMPSTS = (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_enable_nrdy_int +* Description : Enables NRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : NRDY. Enables NRDY interrupt in the pipe specified by the argument +* : in the disabled status. After enabling NRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_enable_nrdy_int (uint16_t pipe) +{ + /* enable nrdy interrupt */ + USB200.NRDYENB |= (uint16_t)g_usb0_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb0_host_disable_nrdy_int +* Description : Disables NRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : NRDY. Disables NRDY interrupt in the pipe specified by the argument +* : in the disabled status. After disabling NRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_disable_nrdy_int (uint16_t pipe) +{ + /* disable nrdy interrupt */ + USB200.NRDYENB &= (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_clear_nrdy_sts +* Description : Clear NRDY interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_clear_nrdy_sts (uint16_t pipe) +{ + /* clear nrdy status */ + USB200.NRDYSTS = (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_is_hispeed +* Description : Returns the result of USB reset hand shake (RHST) as +* : return value. +* Arguments : none +* Return Value : USB_HOST_HIGH_SPEED ; Hi-Speed +* : USB_HOST_FULL_SPEED ; Full-Speed +* : USB_HOST_LOW_SPEED ; Low-Speed +* : USB_HOST_NON_SPEED ; error +*******************************************************************************/ +uint16_t usb0_host_is_hispeed (void) +{ + uint16_t rhst; + uint16_t speed; + + rhst = RZA_IO_RegRead_16(&USB200.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (rhst == USB_HOST_HSMODE) + { + speed = USB_HOST_HIGH_SPEED; + } + else if (rhst == USB_HOST_FSMODE) + { + speed = USB_HOST_FULL_SPEED; + } + else if (rhst == USB_HOST_LSMODE) + { + speed = USB_HOST_LOW_SPEED; + } + else + { + speed = USB_HOST_NON_SPEED; + } + + return speed; +} + +/******************************************************************************* +* Function Name: usb0_host_is_hispeed_enable +* Description : Returns the USB High-Speed connection enabled status as +* : return value. +* Arguments : none +* Return Value : USB_HOST_YES : Hi-Speed Enable +* : USB_HOST_NO : Hi-Speed Disable +*******************************************************************************/ +uint16_t usb0_host_is_hispeed_enable (void) +{ + uint16_t ret; + + ret = USB_HOST_NO; + + if (RZA_IO_RegRead_16(&USB200.SYSCFG0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE) == 1) + { + ret = USB_HOST_YES; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_host_set_pid_buf +* Description : Enables communicaqtion in the pipe specified by the argument +* : (BUF). +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_pid_buf (uint16_t pipe) +{ + uint16_t pid; + + pid = usb0_host_get_pid(pipe); + + if (pid == USB_HOST_PID_STALL2) + { + usb0_host_set_pid_nak(pipe); + } + + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + USB_HOST_PID_BUF, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_set_pid_nak +* Description : Disables communication (NAK) in the pipe specified by the argument. +* : When the pipe status was enabling communication (BUF) before +* : executing before executing this function, waits in the software +* : until the pipe becomes ready after setting disabled. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_pid_nak (uint16_t pipe) +{ + uint16_t pid; + uint16_t pbusy; + uint32_t loop; + + pid = usb0_host_get_pid(pipe); + + if (pid == USB_HOST_PID_STALL2) + { + usb0_host_set_pid_stall(pipe); + } + + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + USB_HOST_PID_NAK, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + + if (pid == USB_HOST_PID_BUF) + { + for (loop = 0; loop < 200; loop++) + { + switch (pipe) + { + case USB_HOST_PIPE0: + pbusy = RZA_IO_RegRead_16(&USB200.DCPCTR, + USB_DCPCTR_PBUSY_SHIFT, + USB_DCPCTR_PBUSY); + break; + + case USB_HOST_PIPE1: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE1CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE2: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE2CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE3: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE3CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE4: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE4CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE5: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE5CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE6: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE6CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE7: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE7CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE8: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE8CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE9: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE9CTR, + USB_PIPEnCTR_9_PBUSY_SHIFT, + USB_PIPEnCTR_9_PBUSY); + break; + + default: + pbusy = 1; + break; + } + + if (pbusy == 0) + { + break; + } + + Userdef_USB_usb0_host_delay_500ns(); + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_set_pid_stall +* Description : Disables communication (STALL) in the pipe specified by the +* : argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_pid_stall (uint16_t pipe) +{ + uint16_t pid; + + pid = usb0_host_get_pid(pipe); + + if (pid == USB_HOST_PID_BUF) + { + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + USB_HOST_PID_STALL2, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + } + else + { + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + USB_HOST_PID_STALL, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_clear_pid_stall +* Description : Disables communication (NAK) in the pipe specified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_clear_pid_stall (uint16_t pipe) +{ + usb0_host_set_pid_nak(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_get_pid +* Description : Returns the pipe state specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : PID +*******************************************************************************/ +uint16_t usb0_host_get_pid (uint16_t pipe) +{ + uint16_t pid; + + switch (pipe) + { + case USB_HOST_PIPE0: + pid = RZA_IO_RegRead_16(&USB200.DCPCTR, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + pid = RZA_IO_RegRead_16(&USB200.PIPE1CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + pid = RZA_IO_RegRead_16(&USB200.PIPE2CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + pid = RZA_IO_RegRead_16(&USB200.PIPE3CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + pid = RZA_IO_RegRead_16(&USB200.PIPE4CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + pid = RZA_IO_RegRead_16(&USB200.PIPE5CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + pid = RZA_IO_RegRead_16(&USB200.PIPE6CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + pid = RZA_IO_RegRead_16(&USB200.PIPE7CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + pid = RZA_IO_RegRead_16(&USB200.PIPE8CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + pid = RZA_IO_RegRead_16(&USB200.PIPE9CTR, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + pid = 0; + break; + } + + return pid; +} + +/******************************************************************************* +* Function Name: usb0_host_set_csclr +* Description : CSPLIT status clear setting of sprit transaction in specified +* : pipe is performed. +* : When SQSET bit or SQCLR bit, and SQSET bit or SQCLR bit +* : in DCPCTR register are continuously changed (when the sequence +* : toggle bit of data PID is continuously changed over two or more pipes), +* : the access cycle with 120 ns and more than 5 cycle bus clock is necessary. +* : Do not set both SQCLR bit and SQSET bit to 1 at the same time. +* : In addition, both bits should be operated after PID is set to NAK. +* : However, when it is set to the isochronous transfer as the transfer type +* : (TYPE=11), writing in SQSET bit is disabled. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_csclr (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + 1, + USB_DCPCTR_CSCLR_SHIFT, + USB_DCPCTR_CSCLR); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + 1, + USB_PIPEnCTR_9_CSCLR_SHIFT, + USB_PIPEnCTR_9_CSCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_set_sqclr +* Description : Sets the sequence bit of the pipe specified by the argument to +* : DATA0. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_sqclr (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + 1, + USB_DCPCTR_SQCLR_SHIFT, + USB_DCPCTR_SQCLR); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + 1, + USB_PIPEnCTR_9_SQCLR_SHIFT, + USB_PIPEnCTR_9_SQCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_set_sqset +* Description : Sets the sequence bit of the pipe specified by the argument to +* : DATA1. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_sqset (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + 1, + USB_DCPCTR_SQSET_SHIFT, + USB_DCPCTR_SQSET); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + 1, + USB_PIPEnCTR_9_SQSET_SHIFT, + USB_PIPEnCTR_9_SQSET); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_get_sqmon +* Description : Toggle bit of specified pipe is obtained +* Arguments : uint16_t pipe ; Pipe number +* Return Value : sqmon +*******************************************************************************/ +uint16_t usb0_host_get_sqmon (uint16_t pipe) +{ + uint16_t sqmon; + + switch (pipe) + { + case USB_HOST_PIPE0: + sqmon = RZA_IO_RegRead_16(&USB200.DCPCTR, + USB_DCPCTR_SQMON_SHIFT, + USB_DCPCTR_SQMON); + break; + + case USB_HOST_PIPE1: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE1CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE2: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE2CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE3: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE3CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE4: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE4CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE5: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE5CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE6: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE6CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE7: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE7CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE8: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE8CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE9: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE9CTR, + USB_PIPEnCTR_9_SQMON_SHIFT, + USB_PIPEnCTR_9_SQMON); + break; + + default: + sqmon = 0; + break; + } + + return sqmon; +} + +/******************************************************************************* +* Function Name: usb0_host_aclrm +* Description : The buffer of specified pipe is initialized +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb0_host_aclrm (uint16_t pipe) +{ + usb0_host_set_aclrm(pipe); + usb0_host_clr_aclrm(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_set_aclrm +* Description : The auto buffer clear mode of specified pipe is enabled +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb0_host_set_aclrm (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + 1, + USB_PIPEnCTR_9_ACLRM_SHIFT, + USB_PIPEnCTR_9_ACLRM); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_clr_aclrm +* Description : The auto buffer clear mode of specified pipe is enabled +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb0_host_clr_aclrm (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + 0, + USB_PIPEnCTR_9_ACLRM_SHIFT, + USB_PIPEnCTR_9_ACLRM); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_get_inbuf +* Description : Returns INBUFM of the pipe specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : inbuf +*******************************************************************************/ +uint16_t usb0_host_get_inbuf (uint16_t pipe) +{ + uint16_t inbuf; + + switch (pipe) + { + case USB_HOST_PIPE0: + inbuf = 0; + break; + + case USB_HOST_PIPE1: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE1CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE2: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE2CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE3: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE3CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE4: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE4CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE5: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE5CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE6: + inbuf = 0; + break; + + case USB_HOST_PIPE7: + inbuf = 0; + break; + + case USB_HOST_PIPE8: + inbuf = 0; + break; + + case USB_HOST_PIPE9: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE9CTR, + USB_PIPEnCTR_9_INBUFM_SHIFT, + USB_PIPEnCTR_9_INBUFM); + break; + + default: + inbuf = 0; + break; + } + + return inbuf; +} + +/******************************************************************************* +* Function Name: usb0_host_setting_interrupt +* Description : Sets the USB module interrupt level. +* Arguments : uint8_t level ; interrupt level +* Return Value : none +*******************************************************************************/ +void usb0_host_setting_interrupt (uint8_t level) +{ +#if(1) /* ohci_wrapp */ + IRQn_Type d0fifo_dmaintid; + IRQn_Type d1fifo_dmaintid; + + InterruptHandlerRegister(USBI0_IRQn, usb0_host_interrupt); + GIC_SetPriority(USBI0_IRQn, level); + GIC_EnableIRQ(USBI0_IRQn); + + d0fifo_dmaintid = (IRQn_Type)Userdef_USB_usb0_host_d0fifo_dmaintid(); + + if (d0fifo_dmaintid != 0xFFFF) + { + InterruptHandlerRegister(d0fifo_dmaintid, usb0_host_dma_interrupt_d0fifo); + GIC_SetPriority(d0fifo_dmaintid, level); + GIC_EnableIRQ(d0fifo_dmaintid); + } + + d1fifo_dmaintid = (IRQn_Type)Userdef_USB_usb0_host_d1fifo_dmaintid(); + + if (d1fifo_dmaintid != 0xFFFF) + { + InterruptHandlerRegister(d1fifo_dmaintid, usb0_host_dma_interrupt_d1fifo); + GIC_SetPriority(d1fifo_dmaintid, level); + GIC_EnableIRQ(d1fifo_dmaintid); + } +#else + uint16_t d0fifo_dmaintid; + uint16_t d1fifo_dmaintid; + + R_INTC_RegistIntFunc(INTC_ID_USBI0, usb0_host_interrupt); + R_INTC_SetPriority(INTC_ID_USBI0, level); + R_INTC_Enable(INTC_ID_USBI0); + + d0fifo_dmaintid = Userdef_USB_usb0_host_d0fifo_dmaintid(); + + if (d0fifo_dmaintid != 0xFFFF) + { + R_INTC_RegistIntFunc(d0fifo_dmaintid, usb0_host_dma_interrupt_d0fifo); + R_INTC_SetPriority(d0fifo_dmaintid, level); + R_INTC_Enable(d0fifo_dmaintid); + } + + d1fifo_dmaintid = Userdef_USB_usb0_host_d1fifo_dmaintid(); + + if (d1fifo_dmaintid != 0xFFFF) + { + R_INTC_RegistIntFunc(d1fifo_dmaintid, usb0_host_dma_interrupt_d1fifo); + R_INTC_SetPriority(d1fifo_dmaintid, level); + R_INTC_Enable(d1fifo_dmaintid); + } +#endif +} + +/******************************************************************************* +* Function Name: usb0_host_reset_module +* Description : Initializes the USB module. +* : Enables providing clock to the USB module. +* : Sets USB bus wait register. +* Arguments : uint16_t clockmode ; 48MHz ; USBHCLOCK_X1_48MHZ +* : ; 12MHz ; USBHCLOCK_EXTAL_12MHZ +* Return Value : none +*******************************************************************************/ +void usb0_host_reset_module (uint16_t clockmode) +{ + if (RZA_IO_RegRead_16(&USB200.SYSCFG0, + USB_SYSCFG_UPLLE_SHIFT, + USB_SYSCFG_UPLLE) == 1) + { + if ((USB200.SYSCFG0 & USB_HOST_BITUCKSEL) != clockmode) + { + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + USB200.SYSCFG0 = 0; + USB200.SYSCFG0 = (USB_HOST_BITUPLLE | clockmode); + Userdef_USB_usb0_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + else + { + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + Userdef_USB_usb0_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + } + else + { + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + USB200.SYSCFG0 = 0; + USB200.SYSCFG0 = (USB_HOST_BITUPLLE | clockmode); + Userdef_USB_usb0_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + + USB200.BUSWAIT = (uint16_t)(USB_HOST_BUSWAIT_05 & USB_HOST_BITBWAIT); +} + +/******************************************************************************* +* Function Name: usb0_host_get_buf_size +* Description : Obtains pipe buffer size specified by the argument and +* : maximum packet size of the USB device in use. +* : When USB_HOST_PIPE0 is specified by the argument, obtains the maximum +* : packet size of the USB device using the corresponding pipe. +* : For the case that USB_HOST_PIPE0 is not assigned by the argument, when the +* : corresponding pipe is in continuous transfer mode, +* : obtains the buffer size allocated in the corresponcing pipe, +* : when incontinuous transfer, obtains maximum packet size. +* Arguments : uint16_t ; pipe Number +* Return Value : Maximum packet size or buffer size +*******************************************************************************/ +uint16_t usb0_host_get_buf_size (uint16_t pipe) +{ + uint16_t size; + uint16_t bufsize; + + if (pipe == USB_HOST_PIPE0) + { + size = RZA_IO_RegRead_16(&USB200.DCPMAXP, + USB_DCPMAXP_MXPS_SHIFT, + USB_DCPMAXP_MXPS); + } + else + { + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_CNTMD_SHIFT, USB_PIPECFG_CNTMD) == 1) + { + bufsize = RZA_IO_RegRead_16(&g_usb0_host_pipebuf[pipe], USB_PIPEBUF_BUFSIZE_SHIFT, USB_PIPEBUF_BUFSIZE); + size = (uint16_t)((bufsize + 1) * USB_HOST_PIPExBUF); + } + else + { + size = RZA_IO_RegRead_16(&g_usb0_host_pipemaxp[pipe], USB_PIPEMAXP_MXPS_SHIFT, USB_PIPEMAXP_MXPS); + } + } + return size; +} + +/******************************************************************************* +* Function Name: usb0_host_get_mxps +* Description : Obtains maximum packet size of the USB device using the pipe +* : specified by the argument. +* Arguments : uint16_t ; Pipe Number +* Return Value : Max Packet Size +*******************************************************************************/ +uint16_t usb0_host_get_mxps (uint16_t pipe) +{ + uint16_t size; + + if (pipe == USB_HOST_PIPE0) + { + size = RZA_IO_RegRead_16(&USB200.DCPMAXP, + USB_DCPMAXP_MXPS_SHIFT, + USB_DCPMAXP_MXPS); + } + else + { + size = RZA_IO_RegRead_16(&g_usb0_host_pipemaxp[pipe], USB_PIPEMAXP_MXPS_SHIFT, USB_PIPEMAXP_MXPS); + } + + return size; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/src/host/usb0_host_controlrw.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,434 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_controlrw.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_CtrlTransStart +* Description : Executes USB control transfer. +* Arguments : uint16_t devadr ; device address +* : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* : uint8_t *Buf ; Data buffer +* Return Value : DEVDRV_SUCCESS ; SUCCESS +* : DEVDRV_ERROR ; ERROR +*******************************************************************************/ +int32_t usb0_host_CtrlTransStart (uint16_t devadr, uint16_t Req, uint16_t Val, + uint16_t Indx, uint16_t Len, uint8_t * Buf) +{ + if (g_usb0_host_UsbDeviceSpeed == USB_HOST_LOW_SPEED) + { + RZA_IO_RegWrite_16(&USB200.SOFCFG, + 1, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + else + { + RZA_IO_RegWrite_16(&USB200.SOFCFG, + 0, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + + USB200.DCPMAXP = (uint16_t)((uint16_t)(devadr << 12) + g_usb0_host_default_max_packet[devadr]); + + if (g_usb0_host_pipe_status[USB_HOST_PIPE0] == USB_HOST_PIPE_IDLE) + { + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_WAIT; + g_usb0_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + g_usb0_host_CmdStage = (USB_HOST_STAGE_SETUP | USB_HOST_CMD_IDLE); + + if (Len == 0) + { + g_usb0_host_CmdStage |= USB_HOST_MODE_NO_DATA; /* No-data Control */ + } + else + { + if ((Req & 0x0080) != 0) + { + g_usb0_host_CmdStage |= USB_HOST_MODE_READ; /* Control Read */ + } + else + { + g_usb0_host_CmdStage |= USB_HOST_MODE_WRITE; /* Control Write */ + } + } + + g_usb0_host_SavReq = Req; /* save request */ + g_usb0_host_SavVal = Val; + g_usb0_host_SavIndx = Indx; + g_usb0_host_SavLen = Len; + } + else + { + if ((g_usb0_host_SavReq != Req) || (g_usb0_host_SavVal != Val) + || (g_usb0_host_SavIndx != Indx) || (g_usb0_host_SavLen != Len)) + { + return DEVDRV_ERROR; + } + } + + switch ((g_usb0_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + /* --------------- SETUP STAGE --------------- */ + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_IDLE): + usb0_host_SetupStage(Req, Val, Indx, Len); + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_DONE): /* goto next stage */ + g_usb0_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + switch ((g_usb0_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_WRITE: + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_DATA; + break; + + case USB_HOST_MODE_READ: + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_DATA; + break; + + case USB_HOST_MODE_NO_DATA: + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_STATUS; + break; + + default: + break; + } + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_NORES): + if (g_usb0_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb0_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_IDLE; + } + break; + + /* --------------- DATA STAGE --------------- */ + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_IDLE): + switch ((g_usb0_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_WRITE: + usb0_host_CtrlWriteStart((uint32_t)Len, Buf); + break; + + case USB_HOST_MODE_READ: + usb0_host_CtrlReadStart((uint32_t)Len, Buf); + break; + + default: + break; + } + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DONE): /* goto next stage */ + g_usb0_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_STATUS; + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_NORES): + if (g_usb0_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb0_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DOING; + usb0_host_clear_pid_stall(USB_HOST_PIPE0); + usb0_host_set_pid_buf(USB_HOST_PIPE0); + } + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_STALL): + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + break; + + /* --------------- STATUS STAGE --------------- */ + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_IDLE): + usb0_host_StatusStage(); + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DONE): /* end of Control transfer */ + usb0_host_set_pid_nak(USB_HOST_PIPE0); + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_DONE; /* exit DONE */ + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_NORES): + if (g_usb0_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb0_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DOING; + usb0_host_clear_pid_stall(USB_HOST_PIPE0); + usb0_host_set_pid_buf(USB_HOST_PIPE0); + } + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_STALL): + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + break; + + default: + break; + } + + if (g_usb0_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_WAIT) + { + RZA_IO_RegWrite_16(&USB200.SOFCFG, + 0, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb0_host_SetupStage +* Description : Executes USB control transfer/set up stage. +* Arguments : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* Return Value : none +*******************************************************************************/ +void usb0_host_SetupStage (uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len) +{ + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DOING; + + USB200.INTSTS1 = (uint16_t)~(USB_HOST_BITSACK | USB_HOST_BITSIGN); /* Status Clear */ + USB200.USBREQ = Req; + USB200.USBVAL = Val; + USB200.USBINDX = Indx; + USB200.USBLENG = Len; + USB200.DCPCTR = USB_HOST_BITSUREQ; /* PID=NAK & Send Setup */ +} + +/******************************************************************************* +* Function Name: usb0_host_StatusStage +* Description : Executes USB control transfer/status stage. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_StatusStage (void) +{ + uint8_t Buf1[16]; + + switch ((g_usb0_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_READ: + usb0_host_CtrlWriteStart((uint32_t)0, (uint8_t *)&Buf1); + break; + + case USB_HOST_MODE_WRITE: + usb0_host_CtrlReadStart((uint32_t)0, (uint8_t *)&Buf1); + break; + + case USB_HOST_MODE_NO_DATA: + usb0_host_CtrlReadStart((uint32_t)0, (uint8_t *)&Buf1); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_CtrlWriteStart +* Description : Executes USB control transfer/data stage(write). +* Arguments : uint32_t Bsize ; Data Size +* : uint8_t *Table ; Data Table Address +* Return Value : USB_HOST_WRITESHRT ; End of data write +* : USB_HOST_WRITEEND ; End of data write (not null) +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_FIFOERROR ; FIFO access error +*******************************************************************************/ +uint16_t usb0_host_CtrlWriteStart (uint32_t Bsize, uint8_t * Table) +{ + uint16_t EndFlag_K; + uint16_t mbw; + + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DOING; + + usb0_host_set_pid_nak(USB_HOST_PIPE0); /* Set NAK */ + g_usb0_host_data_count[USB_HOST_PIPE0] = Bsize; /* Transfer size set */ + g_usb0_host_data_pointer[USB_HOST_PIPE0] = Table; /* Transfer address set */ + + USB200.DCPCTR = USB_HOST_BITSQSET; /* SQSET=1, PID=NAK */ +#if(1) /* ohci_wrapp */ + Userdef_USB_usb0_host_delay_10us(3); +#endif + RZA_IO_RegWrite_16(&USB200.DCPCFG, + 1, + USB_DCPCFG_DIR_SHIFT, + USB_DCPCFG_DIR); + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[USB_HOST_PIPE0], (uint32_t)g_usb0_host_data_pointer[USB_HOST_PIPE0]); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_BITISEL, mbw); + USB200.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + + usb0_host_clear_pid_stall(USB_HOST_PIPE0); + EndFlag_K = usb0_host_write_buffer_c(USB_HOST_PIPE0); + /* Host Control sequence */ + switch (EndFlag_K) + { + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_STATUS; + usb0_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb0_host_enable_bemp_int(USB_HOST_PIPE0); /* Enable Empty Interrupt */ + break; + + case USB_HOST_WRITEEND: /* End of data write (not null) */ + case USB_HOST_WRITING: /* Continue of data write */ + usb0_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb0_host_enable_bemp_int(USB_HOST_PIPE0); /* Enable Empty Interrupt */ + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + break; + + default: + break; + } + usb0_host_set_pid_buf(USB_HOST_PIPE0); /* Set BUF */ + return (EndFlag_K); /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_CtrlReadStart +* Description : Executes USB control transfer/data stage(read). +* Arguments : uint32_t Bsize ; Data Size +* : uint8_t *Table ; Data Table Address +* Return Value : none +*******************************************************************************/ +void usb0_host_CtrlReadStart (uint32_t Bsize, uint8_t * Table) +{ + uint16_t mbw; + + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DOING; + + usb0_host_set_pid_nak(USB_HOST_PIPE0); /* Set NAK */ + g_usb0_host_data_count[USB_HOST_PIPE0] = Bsize; /* Transfer size set */ + g_usb0_host_data_pointer[USB_HOST_PIPE0] = Table; /* Transfer address set */ + + USB200.DCPCTR = USB_HOST_BITSQSET; /* SQSET=1, PID=NAK */ +#if(1) /* ohci_wrapp */ + Userdef_USB_usb0_host_delay_10us(3); +#endif + RZA_IO_RegWrite_16(&USB200.DCPCFG, + 0, + USB_DCPCFG_DIR_SHIFT, + USB_DCPCFG_DIR); + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[USB_HOST_PIPE0], (uint32_t)g_usb0_host_data_pointer[USB_HOST_PIPE0]); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_NO, mbw); + USB200.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + + usb0_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb0_host_enable_brdy_int(USB_HOST_PIPE0); /* Ok */ + usb0_host_clear_pid_stall(USB_HOST_PIPE0); + usb0_host_set_pid_buf(USB_HOST_PIPE0); /* Set BUF */ +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/src/host/usb0_host_drv_api.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,889 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_drv_api.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb0_host_resetEP(USB_HOST_CFG_PIPETBL_t *tbl); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_api_host_init +* Description : Initializes USB module in the USB host mode. +* : USB connection is executed when executing this function in +* : the states that USB device isconnected to the USB port. +* Arguments : uint8_t int_level : USB Module interrupt level +* : USBU16 mode : USB_HOST_HIGH_SPEED +* : USB_HOST_FULL_SPEED +* : uint16_t clockmode : USB Clock mode +* Return Value : USB detach or attach +* : USB_HOST_ATTACH +* : USB_HOST_DETACH +*******************************************************************************/ +uint16_t usb0_api_host_init (uint8_t int_level, uint16_t mode, uint16_t clockmode) +{ + uint16_t connect; + volatile uint8_t dummy_buf; + + CPG.STBCR7 &= 0xfd; /*The clock of USB0 modules is permitted */ + dummy_buf = CPG.STBCR7; /* (Dummy read) */ + + g_usb0_host_SupportUsbDeviceSpeed = mode; + + usb0_host_setting_interrupt(int_level); + usb0_host_reset_module(clockmode); + + g_usb0_host_bchg_flag = USB_HOST_NO; + g_usb0_host_detach_flag = USB_HOST_NO; + g_usb0_host_attach_flag = USB_HOST_NO; + + g_usb0_host_driver_state = USB_HOST_DRV_DETACHED; + g_usb0_host_default_max_packet[USB_HOST_DEVICE_0] = 64; + + usb0_host_InitModule(); + + connect = usb0_host_CheckAttach(); + + if (connect == USB_HOST_ATTACH) + { + g_usb0_host_attach_flag = USB_HOST_YES; + } + else + { + usb0_host_UsbDetach2(); + } + + return connect; +} + +#if(1) /* ohci_wrapp */ +#else +/******************************************************************************* +* Function Name: usb0_api_host_enumeration +* Description : Initializes USB module in the USB host mode. +* : USB connection is executed when executing this function in +* : the states that USB device isconnected to the USB port. +* Arguments : uint16_t devadr : device address +* Return Value : DEVDRV_USBH_DETACH_ERR : device detach +* : DEVDRV_SUCCESS : device enumeration success +* : DEVDRV_ERROR : device enumeration error +*******************************************************************************/ +int32_t usb0_api_host_enumeration (uint16_t devadr) +{ + int32_t ret; + uint16_t driver_sts; + + g_usb0_host_setUsbAddress = devadr; + + while (1) + { + driver_sts = usb0_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + ret = DEVDRV_USBH_DETACH_ERR; + break; + } + else if (driver_sts == USB_HOST_DRV_CONFIGURED) + { + ret = DEVDRV_SUCCESS; + break; + } + else if (driver_sts == USB_HOST_DRV_STALL) + { + ret = DEVDRV_ERROR; + break; + } + else if (driver_sts == USB_HOST_DRV_NORES) + { + ret = DEVDRV_ERROR; + break; + } + else + { + /* Do Nothing */ + } + } + + if (driver_sts == USB_HOST_DRV_NORES) + { + while (1) + { + driver_sts = usb0_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + break; + } + } + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_api_host_detach +* Description : USB detach routine +* Arguments : none +* Return Value : USB_HOST_DETACH : USB detach +* : USB_HOST_ATTACH : USB attach +* : DEVDRV_ERROR : error +*******************************************************************************/ +int32_t usb0_api_host_detach (void) +{ + int32_t ret; + uint16_t driver_sts; + + while (1) + { + driver_sts = usb0_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + ret = USB_HOST_DETACH; + break; + } + else if (driver_sts == USB_HOST_DRV_CONFIGURED) + { + ret = USB_HOST_ATTACH; + break; + } + else if (driver_sts == USB_HOST_DRV_STALL) + { + ret = DEVDRV_ERROR; + break; + } + else if (driver_sts == USB_HOST_DRV_NORES) + { + ret = DEVDRV_ERROR; + break; + } + else + { + /* Do Nothing */ + } + } + + if (driver_sts == USB_HOST_DRV_NORES) + { + while (1) + { + driver_sts = usb0_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + break; + } + } + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_api_host_data_in +* Description : Executes USB transfer as data-in in the argument specified pipe. +* Arguments : uint16_t devadr ; device address +* : uint16_t Pipe ; Pipe Number +* : uint32_t Size ; Data Size +* : uint8_t *data_buf ; Data data_buf Address +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_data_in (uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t * data_buf) +{ + int32_t ret; + + if (Pipe == USB_HOST_PIPE0) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipemaxp[Pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL) != devadr) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[Pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 1) + { + return DEVDRV_ERROR; + } + + if (g_usb0_host_pipe_status[Pipe] == USB_HOST_PIPE_IDLE) + { + usb0_host_start_receive_transfer(Pipe, Size, data_buf); + } + else + { + return DEVDRV_ERROR; /* Now pipe is busy */ + } + + /* waiting for completing routine */ + do + { + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb0_host_pipe_status[Pipe] != USB_HOST_PIPE_IDLE) && (g_usb0_host_pipe_status[Pipe] != USB_HOST_PIPE_WAIT)) + { + break; + } + + } while (1); + + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb0_host_pipe_status[Pipe]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + usb0_host_stop_transfer(Pipe); + + g_usb0_host_pipe_status[Pipe] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_api_host_data_out +* Description : Executes USB transfer as data-out in the argument specified pipe. +* Arguments : uint16_t devadr ; device address +* : uint16_t Pipe ; Pipe Number +* : uint32_t Size ; Data Size +* : uint8_t *data_buf ; Data data_buf Address +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_data_out (uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t * data_buf) +{ + int32_t ret; + + if (Pipe == USB_HOST_PIPE0) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipemaxp[Pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL) != devadr) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[Pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 0) + { + return DEVDRV_ERROR; + } + + if (g_usb0_host_pipe_status[Pipe] == USB_HOST_PIPE_IDLE) + { + usb0_host_start_send_transfer(Pipe, Size, data_buf); + } + else + { + return DEVDRV_ERROR; /* Now pipe is busy */ + } + + /* waiting for completing routine */ + do + { + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb0_host_pipe_status[Pipe] != USB_HOST_PIPE_IDLE) && (g_usb0_host_pipe_status[Pipe] != USB_HOST_PIPE_WAIT)) + { + break; + } + + } while (1); + + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb0_host_pipe_status[Pipe]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + usb0_host_stop_transfer(Pipe); + + g_usb0_host_pipe_status[Pipe] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_api_host_control_transfer +* Description : Executes USB control transfer. +* Arguments : uint16_t devadr ; device address +* : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* : uint8_t *buf ; Buffer +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_USBH_DETACH_ERR ; device detach +* : DEVDRV_USBH_CTRL_COM_ERR ; device no response +* : DEVDRV_USBH_STALL ; STALL +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_control_transfer (uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, + uint16_t Len, uint8_t * Buf) +{ + int32_t ret; + + do + { + ret = usb0_host_CtrlTransStart(devadr, Req, Val, Indx, Len, Buf); + + if (ret == DEVDRV_SUCCESS) + { + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb0_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_IDLE) + && (g_usb0_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_WAIT)) + { + break; + } + } + else + { + return DEVDRV_ERROR; + } + } while (1); + + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb0_host_pipe_status[USB_HOST_PIPE0]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_CTRL_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_api_host_set_endpoint +* Description : Sets end point on the information specified in the argument. +* Arguments : uint16_t devadr ; device address +* : uint8_t *configdescriptor ; device configration descriptor +* : USB_HOST_CFG_PIPETBL_t *user_table ; pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_set_endpoint (uint16_t devadr, USB_HOST_CFG_PIPETBL_t * user_table, uint8_t * configdescriptor) +{ + uint16_t ret; + uint32_t end_point; + uint32_t offset; + uint32_t totalLength; + USB_HOST_CFG_PIPETBL_t * pipe_table; + + /* End Point Search */ + end_point = 0; + offset = configdescriptor[0]; + totalLength = (uint16_t)(configdescriptor[2] + ((uint16_t)configdescriptor[3] << 8)); + + do + { + if (configdescriptor[offset + 1] == USB_HOST_ENDPOINT_DESC) + { + pipe_table = &user_table[end_point]; + + if (pipe_table->pipe_number == 0xffff) + { + break; + } + + ret = usb0_api_host_SetEndpointTable(devadr, pipe_table, (uint8_t *)&configdescriptor[offset]); + + if ((ret != USB_HOST_PIPE_IN) && (ret != USB_HOST_PIPE_OUT)) + { + return DEVDRV_ERROR; + } + + ++end_point; + } + + /* Next End Point Search */ + offset += configdescriptor[offset]; + + } while (offset < totalLength); + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb0_api_host_clear_endpoint +* Description : Clears the pipe definition table specified in the argument. +* Arguments : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_clear_endpoint (USB_HOST_CFG_PIPETBL_t * user_table) +{ + uint16_t pipe; + + for (pipe = USB_HOST_PIPE0; pipe <= USB_HOST_MAX_PIPE_NO; ++pipe) + { + if (user_table->pipe_number == 0xffff) + { + break; + } + user_table->pipe_cfg &= (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD); + user_table->pipe_max_pktsize = 0; + user_table->pipe_cycle = 0; + + user_table++; + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb0_api_host_clear_endpoint_pipe +* Description : Clears the pipe definition table specified in the argument. +* Arguments : uint16_t pipe_sel : Pipe Number +* : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_clear_endpoint_pipe (uint16_t pipe_sel, USB_HOST_CFG_PIPETBL_t * user_table) +{ + uint16_t pipe; + + for (pipe = USB_HOST_PIPE0; pipe <= USB_HOST_MAX_PIPE_NO; ++pipe) + { + if (user_table->pipe_number == 0xffff) + { + break; + } + + if (user_table->pipe_number == pipe_sel) + { + user_table->pipe_cfg &= (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD); + user_table->pipe_max_pktsize = 0; + user_table->pipe_cycle = 0; + break; + } + + user_table++; + } + + return DEVDRV_SUCCESS; +} +#endif + +/******************************************************************************* +* Function Name: usb0_api_host_SetEndpointTable +* Description : Sets the end point on the information specified by the argument. +* Arguments : uint16_t devadr : device address +* : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* : uint8_t *Table : Endpoint descriptor +* Return Value : USB_HOST_DIR_H_IN ; IN endpoint +* : USB_HOST_DIR_H_OUT ; OUT endpoint +* : USB_END_POINT_ERROR ; error +*******************************************************************************/ +uint16_t usb0_api_host_SetEndpointTable (uint16_t devadr, USB_HOST_CFG_PIPETBL_t * user_table, uint8_t * Table) +{ + uint16_t PipeCfg; + uint16_t PipeMaxp; + uint16_t pipe_number; + uint16_t ret; + uint16_t ret_flag = 0; // avoid warning. + + pipe_number = user_table->pipe_number; + + if (Table[1] != USB_HOST_ENDPOINT_DESC) + { + return USB_END_POINT_ERROR; + } + + switch (Table[3] & USB_HOST_EP_TYPE) + { + case USB_HOST_EP_CNTRL: + ret_flag = USB_END_POINT_ERROR; + break; + + case USB_HOST_EP_ISO: + if ((pipe_number != USB_HOST_PIPE1) && (pipe_number != USB_HOST_PIPE2)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_ISO; + break; + + case USB_HOST_EP_BULK: + if ((pipe_number < USB_HOST_PIPE1) || (pipe_number > USB_HOST_PIPE5)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_BULK; + break; + + case USB_HOST_EP_INT: + if ((pipe_number < USB_HOST_PIPE6) || (pipe_number > USB_HOST_PIPE9)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_INTERRUPT; + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + + /* Set pipe configuration table */ + if ((Table[2] & USB_HOST_EP_DIR_MASK) == USB_HOST_EP_IN) /* IN(receive) */ + { + if (PipeCfg == USB_HOST_ISO) + { + /* Transfer Type is ISO*/ + PipeCfg |= USB_HOST_DIR_H_IN; + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + case USB_HOST_D0USE: + case USB_HOST_D1USE: + case USB_HOST_D0DMA: + case USB_HOST_D1DMA: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & USB_HOST_DBLBFIELD); + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + } + else + { + /* Transfer Type is BULK or INT */ + PipeCfg |= (USB_HOST_SHTNAKON | USB_HOST_DIR_H_IN); /* Compulsory SHTNAK */ + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + case USB_HOST_D0USE: + case USB_HOST_D1USE: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); + break; + + case USB_HOST_D0DMA: + case USB_HOST_D1DMA: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); +#ifdef __USB_DMA_BFRE_ENABLE__ + /* this routine cannnot be perfomred if read operation is executed in buffer size */ + PipeCfg |= USB_HOST_BFREON; +#endif + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + } + ret = USB_HOST_PIPE_IN; + } + else /* OUT(send) */ + { + if (PipeCfg == USB_HOST_ISO) + { + /* Transfer Type is ISO*/ + PipeCfg |= (uint16_t)(user_table->pipe_cfg & USB_HOST_DBLBFIELD); + } + else + { + /* Transfer Type is BULK or INT */ + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); + } + PipeCfg |= USB_HOST_DIR_H_OUT; + ret = USB_HOST_PIPE_OUT; + } + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + g_usb0_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_CFIFO_USE; + break; + + case USB_HOST_D0USE: + g_usb0_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D0FIFO_USE; + break; + + case USB_HOST_D1USE: + g_usb0_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D1FIFO_USE; + break; + + case USB_HOST_D0DMA: + g_usb0_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D0FIFO_DMA; + break; + + case USB_HOST_D1DMA: + g_usb0_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D1FIFO_DMA; + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + + /* Endpoint number set */ + PipeCfg |= (uint16_t)(Table[2] & USB_HOST_EP_NUM_MASK); + g_usb0_host_PipeTbl[pipe_number] |= (uint16_t)(Table[2] & USB_HOST_EP_NUM_MASK); + + /* Max packet size set */ + PipeMaxp = (uint16_t)((uint16_t)Table[4] | (uint16_t)((uint16_t)Table[5] << 8)); + + if (PipeMaxp == 0u) + { + return USB_END_POINT_ERROR; + } + + /* Set device address */ + PipeMaxp |= (uint16_t)(devadr << 12); + + user_table->pipe_cfg = PipeCfg; + user_table->pipe_max_pktsize = PipeMaxp; + + usb0_host_resetEP(user_table); + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_host_resetEP +* Description : Sets the end point on the information specified by the argument. +* Arguments : USB_HOST_CFG_PIPETBL_t *tbl : pipe table +* Return Value : none +*******************************************************************************/ +static void usb0_host_resetEP (USB_HOST_CFG_PIPETBL_t * tbl) +{ + + uint16_t pipe; + + /* Host pipe */ + /* The pipe number of pipe definition table is obtained */ + pipe = (uint16_t)(tbl->pipe_number & USB_HOST_BITCURPIPE); /* Pipe Number */ + + /* FIFO port access pipe is set to initial value */ + /* The connection with FIFO should be cut before setting the pipe */ + if (RZA_IO_RegRead_16(&USB200.CFIFOSEL, + USB_CFIFOSEL_CURPIPE_SHIFT, + USB_CFIFOSEL_CURPIPE) == pipe) + { + usb0_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + if (RZA_IO_RegRead_16(&USB200.D0FIFOSEL, + USB_DnFIFOSEL_CURPIPE_SHIFT, + USB_DnFIFOSEL_CURPIPE) == pipe) + { + usb0_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + if (RZA_IO_RegRead_16(&USB200.D1FIFOSEL, + USB_DnFIFOSEL_CURPIPE_SHIFT, + USB_DnFIFOSEL_CURPIPE) == pipe) + { + usb0_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + /* Interrupt of pipe set is disabled */ + usb0_host_disable_brdy_int(pipe); + usb0_host_disable_nrdy_int(pipe); + usb0_host_disable_bemp_int(pipe); + + /* Pipe to set is set to NAK */ + usb0_host_set_pid_nak(pipe); + + /* Pipe is set */ + USB200.PIPESEL = pipe; + + USB200.PIPECFG = tbl->pipe_cfg; + USB200.PIPEBUF = tbl->pipe_buf; + USB200.PIPEMAXP = tbl->pipe_max_pktsize; + USB200.PIPEPERI = tbl->pipe_cycle; + + g_usb0_host_pipecfg[pipe] = tbl->pipe_cfg; + g_usb0_host_pipebuf[pipe] = tbl->pipe_buf; + g_usb0_host_pipemaxp[pipe] = tbl->pipe_max_pktsize; + g_usb0_host_pipeperi[pipe] = tbl->pipe_cycle; + + /* Sequence bit clear */ + usb0_host_set_sqclr(pipe); + + usb0_host_aclrm(pipe); + usb0_host_set_csclr(pipe); + + /* Pipe window selection is set to unused */ + USB200.PIPESEL = USB_HOST_PIPE0; + +} + +#if(1) /* ohci_wrapp */ +#else +/******************************************************************************* +* Function Name: usb0_api_host_data_count +* Description : Get g_usb0_host_data_count[pipe] +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t *data_count ; return g_usb0_data_count[pipe] +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_data_count (uint16_t pipe, uint32_t * data_count) +{ + if (pipe > USB_HOST_MAX_PIPE_NO) + { + return DEVDRV_ERROR; + } + + *data_count = g_usb0_host_PipeDataSize[pipe]; + + return DEVDRV_SUCCESS; +} +#endif + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/src/host/usb0_host_global.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,137 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_global.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +const uint16_t g_usb0_host_bit_set[16] = +{ + 0x0001, 0x0002, 0x0004, 0x0008, + 0x0010, 0x0020, 0x0040, 0x0080, + 0x0100, 0x0200, 0x0400, 0x0800, + 0x1000, 0x2000, 0x4000, 0x8000 +}; + +uint32_t g_usb0_host_data_count[USB_HOST_MAX_PIPE_NO + 1]; +uint8_t * g_usb0_host_data_pointer[USB_HOST_MAX_PIPE_NO + 1]; + +uint16_t g_usb0_host_PipeIgnore[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb0_host_PipeTbl[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb0_host_pipe_status[USB_HOST_MAX_PIPE_NO + 1]; +uint32_t g_usb0_host_PipeDataSize[USB_HOST_MAX_PIPE_NO + 1]; + +USB_HOST_DMA_t g_usb0_host_DmaInfo[2]; + +uint16_t g_usb0_host_DmaPipe[2]; +uint16_t g_usb0_host_DmaBval[2]; +uint16_t g_usb0_host_DmaStatus[2]; + +uint16_t g_usb0_host_driver_state; +uint16_t g_usb0_host_ConfigNum; +uint16_t g_usb0_host_CmdStage; +uint16_t g_usb0_host_bchg_flag; +uint16_t g_usb0_host_detach_flag; +uint16_t g_usb0_host_attach_flag; + +uint16_t g_usb0_host_UsbAddress; +uint16_t g_usb0_host_setUsbAddress; +uint16_t g_usb0_host_default_max_packet[USB_HOST_MAX_DEVICE + 1]; +uint16_t g_usb0_host_UsbDeviceSpeed; +uint16_t g_usb0_host_SupportUsbDeviceSpeed; + +uint16_t g_usb0_host_SavReq; +uint16_t g_usb0_host_SavVal; +uint16_t g_usb0_host_SavIndx; +uint16_t g_usb0_host_SavLen; + +uint16_t g_usb0_host_pipecfg[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb0_host_pipebuf[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb0_host_pipemaxp[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb0_host_pipeperi[USB_HOST_MAX_PIPE_NO + 1]; + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_init_pipe_status +* Description : Initialize pipe status. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_init_pipe_status (void) +{ + uint16_t loop; + + g_usb0_host_ConfigNum = 0; + + for (loop = 0; loop < (USB_HOST_MAX_PIPE_NO + 1); ++loop) + { + g_usb0_host_pipe_status[loop] = USB_HOST_PIPE_IDLE; + g_usb0_host_PipeDataSize[loop] = 0; + + /* pipe configuration in usb0_host_resetEP() */ + g_usb0_host_pipecfg[loop] = 0; + g_usb0_host_pipebuf[loop] = 0; + g_usb0_host_pipemaxp[loop] = 0; + g_usb0_host_pipeperi[loop] = 0; + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/src/host/usb0_host_usbint.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,496 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_usbint.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#if(1) /* ohci_wrapp */ +#include "ohci_wrapp_RZ_A1_local.h" +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb0_host_interrupt1(void); +static void usb0_host_BRDYInterrupt(uint16_t Status, uint16_t Int_enbl); +static void usb0_host_NRDYInterrupt(uint16_t Status, uint16_t Int_enbl); +static void usb0_host_BEMPInterrupt(uint16_t Status, uint16_t Int_enbl); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_interrupt +* Description : Executes USB interrupt. +* : Register this function in the USB interrupt handler. +* : Set CFIF0 in the pipe set before the interrupt after executing +* : this function. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb0_host_interrupt (uint32_t int_sense) +{ + uint16_t savepipe1; + uint16_t savepipe2; + uint16_t buffer; + + savepipe1 = USB200.CFIFOSEL; + savepipe2 = USB200.PIPESEL; + usb0_host_interrupt1(); + + /* Control transmission changes ISEL within interruption processing. */ + /* For this reason, write return of ISEL cannot be performed. */ + buffer = USB200.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(savepipe1 & USB_HOST_BITCURPIPE); + USB200.CFIFOSEL = buffer; + USB200.PIPESEL = savepipe2; +} + +/******************************************************************************* +* Function Name: usb0_host_interrupt1 +* Description : Execue the USB interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_interrupt1 (void) +{ + uint16_t intsts0; + uint16_t intsts1; + uint16_t intenb0; + uint16_t intenb1; + uint16_t brdysts; + uint16_t nrdysts; + uint16_t bempsts; + uint16_t brdyenb; + uint16_t nrdyenb; + uint16_t bempenb; + volatile uint16_t dumy_sts; + + intsts0 = USB200.INTSTS0; + intsts1 = USB200.INTSTS1; + intenb0 = USB200.INTENB0; + intenb1 = USB200.INTENB1; + + if ((intsts1 & USB_HOST_BITBCHG) && (intenb1 & USB_HOST_BITBCHGE)) + { + USB200.INTSTS1 = (uint16_t)~USB_HOST_BITBCHG; + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); + g_usb0_host_bchg_flag = USB_HOST_YES; + } + else if ((intsts1 & USB_HOST_BITSACK) && (intenb1 & USB_HOST_BITSACKE)) + { + USB200.INTSTS1 = (uint16_t)~USB_HOST_BITSACK; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); +#else + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; +#endif + } + else if ((intsts1 & USB_HOST_BITSIGN) && (intenb1 & USB_HOST_BITSIGNE)) + { + USB200.INTSTS1 = (uint16_t)~USB_HOST_BITSIGN; +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#else + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_NORES; +#endif + } + else if (((intsts1 & USB_HOST_BITDTCH) == USB_HOST_BITDTCH) + && ((intenb1 & USB_HOST_BITDTCHE) == USB_HOST_BITDTCHE)) + { + USB200.INTSTS1 = (uint16_t)~USB_HOST_BITDTCH; + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); + g_usb0_host_detach_flag = USB_HOST_YES; + + Userdef_USB_usb0_host_detach(); + + usb0_host_UsbDetach2(); + } + else if (((intsts1 & USB_HOST_BITATTCH) == USB_HOST_BITATTCH) + && ((intenb1 & USB_HOST_BITATTCHE) == USB_HOST_BITATTCHE)) + { + USB200.INTSTS1 = (uint16_t)~USB_HOST_BITATTCH; + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); + g_usb0_host_attach_flag = USB_HOST_YES; + + Userdef_USB_usb0_host_attach(); + + usb0_host_UsbAttach(); + } + else if ((intsts0 & intenb0 & (USB_HOST_BITBEMP | USB_HOST_BITNRDY | USB_HOST_BITBRDY))) + { + brdysts = USB200.BRDYSTS; + nrdysts = USB200.NRDYSTS; + bempsts = USB200.BEMPSTS; + brdyenb = USB200.BRDYENB; + nrdyenb = USB200.NRDYENB; + bempenb = USB200.BEMPENB; + + if ((intsts0 & USB_HOST_BITBRDY) && (intenb0 & USB_HOST_BITBRDYE) && (brdysts & brdyenb)) + { + usb0_host_BRDYInterrupt(brdysts, brdyenb); + } + else if ((intsts0 & USB_HOST_BITBEMP) && (intenb0 & USB_HOST_BITBEMPE) && (bempsts & bempenb)) + { + usb0_host_BEMPInterrupt(bempsts, bempenb); + } + else if ((intsts0 & USB_HOST_BITNRDY) && (intenb0 & USB_HOST_BITNRDYE) && (nrdysts & nrdyenb)) + { + usb0_host_NRDYInterrupt(nrdysts, nrdyenb); + } + else + { + /* Do Nothing */ + } + } + else + { + /* Do Nothing */ + } + + /* Three dummy read for clearing interrupt requests */ + dumy_sts = USB200.INTSTS0; + dumy_sts = USB200.INTSTS1; + +} + +/******************************************************************************* +* Function Name: usb0_host_BRDYInterrupt +* Description : Executes USB BRDY interrupt. +* Arguments : uint16_t Status ; BRDYSTS Register Value +* : uint16_t Int_enbl ; BRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_BRDYInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t buffer; + volatile uint16_t dumy_sts; + + if ((Status & g_usb0_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb0_host_bit_set[USB_HOST_PIPE0])) + { + USB200.BRDYSTS = (uint16_t)~g_usb0_host_bit_set[USB_HOST_PIPE0]; + +#if(1) /* ohci_wrapp */ + switch ((g_usb0_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + buffer = usb0_host_read_buffer_c(USB_HOST_PIPE0); + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb0_host_read_buffer_c(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_READOVER: /* buffer over */ + USB200.CFIFOCTR = USB_HOST_BITBCLR; + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + break; + } +#else + switch ((g_usb0_host_CmdStage & (USB_HOST_MODE_FIELD | USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + case (USB_HOST_MODE_NO_DATA | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + buffer = usb0_host_read_buffer_c(USB_HOST_PIPE0); + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case (USB_HOST_MODE_READ | USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb0_host_read_buffer_c(USB_HOST_PIPE0); + + switch (buffer) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case USB_HOST_READOVER: /* buffer over */ + USB200.CFIFOCTR = USB_HOST_BITBCLR; + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + break; + } +#endif + } + else + { + usb0_host_brdy_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB200.BRDYSTS; +} + +/******************************************************************************* +* Function Name: usb0_host_NRDYInterrupt +* Description : Executes USB NRDY interrupt. +* Arguments : uint16_t Status ; NRDYSTS Register Value +* : uint16_t Int_enbl ; NRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_NRDYInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t pid; + volatile uint16_t dumy_sts; + + if ((Status & g_usb0_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb0_host_bit_set[USB_HOST_PIPE0])) + { + USB200.NRDYSTS = (uint16_t)~g_usb0_host_bit_set[USB_HOST_PIPE0]; + pid = usb0_host_get_pid(USB_HOST_PIPE0); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_STALL; +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + } + else if (pid == USB_HOST_PID_NAK) + { + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_NORES; +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + } + else + { + /* Do Nothing */ + } + } + else + { + usb0_host_nrdy_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB200.NRDYSTS; +} + +/******************************************************************************* +* Function Name: usb0_host_BEMPInterrupt +* Description : Executes USB BEMP interrupt. +* Arguments : uint16_t Status ; BEMPSTS Register Value +* : uint16_t Int_enbl ; BEMPENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_BEMPInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t buffer; + uint16_t pid; + volatile uint16_t dumy_sts; + + if ((Status & g_usb0_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb0_host_bit_set[USB_HOST_PIPE0])) + { + USB200.BEMPSTS = (uint16_t)~g_usb0_host_bit_set[USB_HOST_PIPE0]; + pid = usb0_host_get_pid(USB_HOST_PIPE0); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_STALL; +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + } + else + { +#if(1) /* ohci_wrapp */ + switch ((g_usb0_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb0_host_write_buffer(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_WRITING: /* Continue of data write */ + case USB_HOST_WRITEEND: /* End of data write (zero-length) */ + break; + + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_STATUS; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + /* do nothing */ + break; + } +#else + switch ((g_usb0_host_CmdStage & (USB_HOST_MODE_FIELD | USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_MODE_READ | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb0_host_write_buffer(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_WRITING: /* Continue of data write */ + case USB_HOST_WRITEEND: /* End of data write (zero-length) */ + break; + + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_STATUS; + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + default: + /* do nothing */ + break; + } +#endif + } + } + else + { + usb0_host_bemp_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB200.BEMPSTS; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/src/host/usb0_host_usbsig.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,637 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_usbsig.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb0_host_EnableINT_Module(void); +static void usb0_host_Enable_AttachINT(void); +static void usb0_host_Disable_AttachINT(void); +static void usb0_host_Disable_BchgINT(void); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_InitModule +* Description : Initializes the USB module in USB host module. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_InitModule (void) +{ + uint16_t buf1; + uint16_t buf2; + uint16_t buf3; + + usb0_host_init_pipe_status(); + + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 1, + USB_SYSCFG_DCFM_SHIFT, + USB_SYSCFG_DCFM); /* HOST mode */ + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 1, + USB_SYSCFG_DRPD_SHIFT, + USB_SYSCFG_DRPD); /* PORT0 D+, D- setting */ + + do + { + buf1 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb0_host_delay_xms(50); + buf2 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb0_host_delay_xms(50); + buf3 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + + } while ((buf1 != buf2) || (buf1 != buf3)); + + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 1, + USB_SYSCFG_USBE_SHIFT, + USB_SYSCFG_USBE); + + USB200.CFIFOSEL = (uint16_t)(USB_HOST_BITRCNT | USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); + USB200.D0FIFOSEL = (uint16_t)( USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); + USB200.D1FIFOSEL = (uint16_t)( USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); +} + +/******************************************************************************* +* Function Name: usb0_host_CheckAttach +* Description : Returns the USB device connection state. +* Arguments : none +* Return Value : uint16_t ; USB_HOST_ATTACH : Attached +* : ; USB_HOST_DETACH : not Attached +*******************************************************************************/ +uint16_t usb0_host_CheckAttach (void) +{ + uint16_t buf1; + uint16_t buf2; + uint16_t buf3; + uint16_t rhst; + + do + { + buf1 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb0_host_delay_xms(50); + buf2 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb0_host_delay_xms(50); + buf3 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + + } while ((buf1 != buf2) || (buf1 != buf3)); + + rhst = RZA_IO_RegRead_16(&USB200.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (rhst == USB_HOST_UNDECID) + { + if (buf1 == USB_HOST_FS_JSTS) + { + if (g_usb0_host_SupportUsbDeviceSpeed == USB_HOST_HIGH_SPEED) + { + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 1, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + } + else + { + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + } + return USB_HOST_ATTACH; + } + else if (buf1 == USB_HOST_LS_JSTS) + { + /* Low Speed Device */ + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + return USB_HOST_ATTACH; + } + else + { + /* Do Nothing */ + } + } + else if ((rhst == USB_HOST_HSMODE) || (rhst == USB_HOST_FSMODE)) + { + return USB_HOST_ATTACH; + } + else if (rhst == USB_HOST_LSMODE) + { + return USB_HOST_ATTACH; + } + else + { + /* Do Nothing */ + } + + return USB_HOST_DETACH; +} + +/******************************************************************************* +* Function Name: usb0_host_UsbAttach +* Description : Connects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_UsbAttach (void) +{ + usb0_host_EnableINT_Module(); + usb0_host_Disable_BchgINT(); + usb0_host_Disable_AttachINT(); + usb0_host_Enable_DetachINT(); +} + +/******************************************************************************* +* Function Name: usb0_host_UsbDetach +* Description : Disconnects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_UsbDetach (void) +{ + uint16_t pipe; + uint16_t devadr; + + g_usb0_host_driver_state = USB_HOST_DRV_DETACHED; + + /* Terminate all the pipes in which communications on port */ + /* are currently carried out */ + for (pipe = 0; pipe < (USB_HOST_MAX_PIPE_NO + 1); ++pipe) + { + if (g_usb0_host_pipe_status[pipe] != USB_HOST_PIPE_IDLE) + { + if (pipe == USB_HOST_PIPE0) + { + devadr = RZA_IO_RegRead_16(&USB200.DCPMAXP, + USB_DCPMAXP_DEVSEL_SHIFT, + USB_DCPMAXP_DEVSEL); + } + else + { + devadr = RZA_IO_RegRead_16(&g_usb0_host_pipemaxp[pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL); + } + + if (devadr == g_usb0_host_UsbAddress) + { + usb0_host_stop_transfer(pipe); + } + + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_IDLE; + } + } + + g_usb0_host_ConfigNum = 0; + g_usb0_host_UsbAddress = 0; + g_usb0_host_default_max_packet[USB_HOST_DEVICE_0] = 64; + + usb0_host_UsbDetach2(); +} + +/******************************************************************************* +* Function Name: usb0_host_UsbDetach2 +* Description : Disconnects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_UsbDetach2 (void) +{ + usb0_host_Disable_DetachINT(); + usb0_host_Disable_BchgINT(); + usb0_host_Enable_AttachINT(); +} + +/******************************************************************************* +* Function Name: usb0_host_UsbBusReset +* Description : Issues the USB bus reset signal. +* Arguments : none +* Return Value : uint16_t ; RHST +*******************************************************************************/ +uint16_t usb0_host_UsbBusReset (void) +{ + uint16_t buffer; + uint16_t loop; + + RZA_IO_RegWrite_16(&USB200.DVSTCTR0, + 1, + USB_DVSTCTR0_USBRST_SHIFT, + USB_DVSTCTR0_USBRST); + RZA_IO_RegWrite_16(&USB200.DVSTCTR0, + 0, + USB_DVSTCTR0_UACT_SHIFT, + USB_DVSTCTR0_UACT); + + Userdef_USB_usb0_host_delay_xms(50); + + buffer = USB200.DVSTCTR0; + buffer &= (uint16_t)(~(USB_HOST_BITRST)); + buffer |= USB_HOST_BITUACT; + USB200.DVSTCTR0 = buffer; + + Userdef_USB_usb0_host_delay_xms(20); + + for (loop = 0, buffer = USB_HOST_HSPROC; loop < 3; ++loop) + { + buffer = RZA_IO_RegRead_16(&USB200.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (buffer == USB_HOST_HSPROC) + { + Userdef_USB_usb0_host_delay_xms(10); + } + else + { + break; + } + } + + return buffer; +} + +/******************************************************************************* +* Function Name: usb0_host_UsbResume +* Description : Issues the USB resume signal. +* Arguments : none +* Return Value : int32_t ; DEVDRV_SUCCESS +* : ; DEVDRV_ERROR +*******************************************************************************/ +int32_t usb0_host_UsbResume (void) +{ + uint16_t buf; + + if ((g_usb0_host_driver_state & USB_HOST_DRV_SUSPEND) == 0) + { + /* not SUSPEND */ + return DEVDRV_ERROR; + } + + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); + RZA_IO_RegWrite_16(&USB200.DVSTCTR0, + 1, + USB_DVSTCTR0_RESUME_SHIFT, + USB_DVSTCTR0_RESUME); + Userdef_USB_usb0_host_delay_xms(20); + + buf = USB200.DVSTCTR0; + buf &= (uint16_t)(~(USB_HOST_BITRESUME)); + buf |= USB_HOST_BITUACT; + USB200.DVSTCTR0 = buf; + + g_usb0_host_driver_state &= (uint16_t)~USB_HOST_DRV_SUSPEND; + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb0_host_UsbSuspend +* Description : Issues the USB suspend signal. +* Arguments : none +* Return Value : int32_t ; DEVDRV_SUCCESS :not SUSPEND +* : ; DEVDRV_ERROR :SUSPEND +*******************************************************************************/ +int32_t usb0_host_UsbSuspend (void) +{ + uint16_t buf; + + if ((g_usb0_host_driver_state & USB_HOST_DRV_SUSPEND) != 0) + { + /* SUSPEND */ + return DEVDRV_ERROR; + } + + RZA_IO_RegWrite_16(&USB200.DVSTCTR0, + 0, + USB_DVSTCTR0_UACT_SHIFT, + USB_DVSTCTR0_UACT); + + Userdef_USB_usb0_host_delay_xms(5); + + buf = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + if ((buf != USB_HOST_FS_JSTS) && (buf != USB_HOST_LS_JSTS)) + { + usb0_host_UsbDetach(); + } + else + { + g_usb0_host_driver_state |= USB_HOST_DRV_SUSPEND; + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb0_host_Enable_DetachINT +* Description : Enables the USB disconnection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_Enable_DetachINT (void) +{ + USB200.INTSTS1 = (uint16_t)(~(USB_HOST_BITDTCH)); + RZA_IO_RegWrite_16(&USB200.INTENB1, + 1, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); +} + +/******************************************************************************* +* Function Name: usb0_host_Disable_DetachINT +* Description : Disables the USB disconnection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_Disable_DetachINT (void) +{ + USB200.INTSTS1 = (uint16_t)(~(USB_HOST_BITDTCH)); + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); +} + +/******************************************************************************* +* Function Name: usb0_host_Enable_AttachINT +* Description : Enables the USB connection detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_Enable_AttachINT (void) +{ + USB200.INTSTS1 = (uint16_t)(~(USB_HOST_BITATTCH)); + RZA_IO_RegWrite_16(&USB200.INTENB1, + 1, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); +} + +/******************************************************************************* +* Function Name: usb0_host_Disable_AttachINT +* Description : Disables the USB connection detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_Disable_AttachINT (void) +{ + USB200.INTSTS1 = (uint16_t)(~(USB_HOST_BITATTCH)); + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); +} + +/******************************************************************************* +* Function Name: usb0_host_Disable_BchgINT +* Description : Disables the USB bus change detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_Disable_BchgINT (void) +{ + USB200.INTSTS1 = (uint16_t)(~(USB_HOST_BITBCHG)); + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); +} + +/******************************************************************************* +* Function Name: usb0_host_set_devadd +* Description : DEVADDn register is set by specified value +* Arguments : uint16_t addr : Device address +* : uint16_t *devadd : Set value +* Return Value : none +*******************************************************************************/ +void usb0_host_set_devadd (uint16_t addr, uint16_t * devadd) +{ + uint16_t * ptr; + uint16_t ret_flag = DEVDRV_FLAG_ON; // avoid warning. + + switch (addr) + { + case USB_HOST_DEVICE_0: + ptr = (uint16_t *)&USB200.DEVADD0; + break; + + case USB_HOST_DEVICE_1: + ptr = (uint16_t *)&USB200.DEVADD1; + break; + + case USB_HOST_DEVICE_2: + ptr = (uint16_t *)&USB200.DEVADD2; + break; + + case USB_HOST_DEVICE_3: + ptr = (uint16_t *)&USB200.DEVADD3; + break; + + case USB_HOST_DEVICE_4: + ptr = (uint16_t *)&USB200.DEVADD4; + break; + + case USB_HOST_DEVICE_5: + ptr = (uint16_t *)&USB200.DEVADD5; + break; + + case USB_HOST_DEVICE_6: + ptr = (uint16_t *)&USB200.DEVADD6; + break; + + case USB_HOST_DEVICE_7: + ptr = (uint16_t *)&USB200.DEVADD7; + break; + + case USB_HOST_DEVICE_8: + ptr = (uint16_t *)&USB200.DEVADD8; + break; + + case USB_HOST_DEVICE_9: + ptr = (uint16_t *)&USB200.DEVADD9; + break; + + case USB_HOST_DEVICE_10: + ptr = (uint16_t *)&USB200.DEVADDA; + break; + + default: + ret_flag = DEVDRV_FLAG_OFF; + break; + } + + if (ret_flag == DEVDRV_FLAG_ON) + { + *ptr = (uint16_t)(*devadd & USB_HOST_DEVADD_MASK); + } +} + +/******************************************************************************* +* Function Name: usb0_host_get_devadd +* Description : DEVADDn register is obtained +* Arguments : uint16_t addr : Device address +* : uint16_t *devadd : USB_HOST_DEVADD register value +* Return Value : none +*******************************************************************************/ +void usb0_host_get_devadd (uint16_t addr, uint16_t * devadd) +{ + uint16_t * ptr; + uint16_t ret_flag = DEVDRV_FLAG_ON; // avoid warning. + + switch (addr) + { + case USB_HOST_DEVICE_0: + ptr = (uint16_t *)&USB200.DEVADD0; + break; + + case USB_HOST_DEVICE_1: + ptr = (uint16_t *)&USB200.DEVADD1; + break; + + case USB_HOST_DEVICE_2: + ptr = (uint16_t *)&USB200.DEVADD2; + break; + + case USB_HOST_DEVICE_3: + ptr = (uint16_t *)&USB200.DEVADD3; + break; + + case USB_HOST_DEVICE_4: + ptr = (uint16_t *)&USB200.DEVADD4; + break; + + case USB_HOST_DEVICE_5: + ptr = (uint16_t *)&USB200.DEVADD5; + break; + + case USB_HOST_DEVICE_6: + ptr = (uint16_t *)&USB200.DEVADD6; + break; + + case USB_HOST_DEVICE_7: + ptr = (uint16_t *)&USB200.DEVADD7; + break; + + case USB_HOST_DEVICE_8: + ptr = (uint16_t *)&USB200.DEVADD8; + break; + + case USB_HOST_DEVICE_9: + ptr = (uint16_t *)&USB200.DEVADD9; + break; + + case USB_HOST_DEVICE_10: + ptr = (uint16_t *)&USB200.DEVADDA; + break; + + default: + ret_flag = DEVDRV_FLAG_OFF; + break; + } + + if (ret_flag == DEVDRV_FLAG_ON) + { + *devadd = *ptr; + } +} + +/******************************************************************************* +* Function Name: usb0_host_EnableINT_Module +* Description : Enables BEMP/NRDY/BRDY interrupt and SIGN/SACK interrupt. +* : Enables NRDY/BEMP interrupt in the pipe0. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_EnableINT_Module (void) +{ + uint16_t buf; + + buf = USB200.INTENB0; + buf |= (USB_HOST_BITBEMPE | USB_HOST_BITNRDYE | USB_HOST_BITBRDYE); + USB200.INTENB0 = buf; + + buf = USB200.INTENB1; + buf |= (USB_HOST_BITSIGNE | USB_HOST_BITSACKE); + USB200.INTENB1 = buf; + + usb0_host_enable_nrdy_int(USB_HOST_PIPE0); + usb0_host_enable_bemp_int(USB_HOST_PIPE0); +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/src/userdef/usb0_host_dmacdrv.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,698 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_dmacdrv.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "r_typedefs.h" +#include "iodefine.h" +#include "rza_io_regrw.h" +#include "usb0_host_dmacdrv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define DMAC_INDEFINE (255) /* Macro definition when REQD bit is not used */ + +/* ==== Request setting information for on-chip peripheral module ==== */ +typedef enum dmac_peri_req_reg_type +{ + DMAC_REQ_MID, + DMAC_REQ_RID, + DMAC_REQ_AM, + DMAC_REQ_LVL, + DMAC_REQ_REQD +} dmac_peri_req_reg_type_t; + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +/* ==== Prototype declaration ==== */ + +/* ==== Global variable ==== */ +/* On-chip peripheral module request setting table */ +static const uint8_t usb0_host_dmac_peri_req_init_table[8][5] = +{ + /* MID,RID, AM,LVL,REQD */ + { 32, 3, 2, 1, 1}, /* USB_0 channel 0 transmit FIFO empty */ + { 32, 3, 2, 1, 0}, /* USB_0 channel 0 receive FIFO full */ + { 33, 3, 2, 1, 1}, /* USB_0 channel 1 transmit FIFO empty */ + { 33, 3, 2, 1, 0}, /* USB_0 channel 1 receive FIFO full */ + { 34, 3, 2, 1, 1}, /* USB_1 channel 0 transmit FIFO empty */ + { 34, 3, 2, 1, 0}, /* USB_1 channel 0 receive FIFO full */ + { 35, 3, 2, 1, 1}, /* USB_1 channel 1 transmit FIFO empty */ + { 35, 3, 2, 1, 0}, /* USB_1 channel 1 receive FIFO full */ +}; + + +/******************************************************************************* +* Function Name: usb0_host_DMAC1_PeriReqInit +* Description : Sets the register mode for DMA mode and the on-chip peripheral +* : module request for transfer request for DMAC channel 1. +* : Executes DMAC initial setting using the DMA information +* : specified by the argument *trans_info and the enabled/disabled +* : continuous transfer specified by the argument continuation. +* : Registers DMAC channel 1 interrupt handler function and sets +* : the interrupt priority level. Then enables transfer completion +* : interrupt. +* Arguments : dmac_transinfo_t * trans_info : Setting information to DMAC +* : : register +* : uint32_t dmamode : DMA mode (only for DMAC_MODE_REGISTER) +* : uint32_t continuation : Set continuous transfer to be valid +* : : after DMA transfer has been completed +* : DMAC_SAMPLE_CONTINUATION : Execute continuous transfer +* : DMAC_SAMPLE_SINGLE : Do not execute continuous +* : : transfer +* : uint32_t request_factor : Factor for on-chip peripheral module +* : : request +* : DMAC_REQ_OSTM0TINT : OSTM_0 compare match +* : DMAC_REQ_OSTM1TINT : OSTM_1 compare match +* : DMAC_REQ_TGI0A : MTU2_0 input capture/compare match +* : : +* : uint32_t req_direction : Setting value of CHCFG_n register +* : : REQD bit +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC1_PeriReqInit (const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction) +{ + /* ==== Register mode ==== */ + if (DMAC_MODE_REGISTER == dmamode) + { + /* ==== Next0 register set ==== */ + DMAC1.N0SA_n = trans_info->src_addr; /* Start address of transfer source */ + DMAC1.N0DA_n = trans_info->dst_addr; /* Start address of transfer destination */ + DMAC1.N0TB_n = trans_info->count; /* Total transfer byte count */ + + /* DAD : Transfer destination address counting direction */ + /* SAD : Transfer source address counting direction */ + /* DDS : Transfer destination transfer size */ + /* SDS : Transfer source transfer size */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + trans_info->daddr_dir, + DMAC1_CHCFG_n_DAD_SHIFT, + DMAC1_CHCFG_n_DAD); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + trans_info->saddr_dir, + DMAC1_CHCFG_n_SAD_SHIFT, + DMAC1_CHCFG_n_SAD); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + trans_info->dst_size, + DMAC1_CHCFG_n_DDS_SHIFT, + DMAC1_CHCFG_n_DDS); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + trans_info->src_size, + DMAC1_CHCFG_n_SDS_SHIFT, + DMAC1_CHCFG_n_SDS); + + /* DMS : Register mode */ + /* RSEL : Select Next0 register set */ + /* SBE : No discharge of buffer data when aborted */ + /* DEM : No DMA interrupt mask */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_DMS_SHIFT, + DMAC1_CHCFG_n_DMS); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_RSEL_SHIFT, + DMAC1_CHCFG_n_RSEL); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_SBE_SHIFT, + DMAC1_CHCFG_n_SBE); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_DEM_SHIFT, + DMAC1_CHCFG_n_DEM); + + /* ---- Continuous transfer ---- */ + if (DMAC_SAMPLE_CONTINUATION == continuation) + { + /* REN : Execute continuous transfer */ + /* RSW : Change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 1, + DMAC1_CHCFG_n_REN_SHIFT, + DMAC1_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 1, + DMAC1_CHCFG_n_RSW_SHIFT, + DMAC1_CHCFG_n_RSW); + } + /* ---- Single transfer ---- */ + else + { + /* REN : Do not execute continuous transfer */ + /* RSW : Do not change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_REN_SHIFT, + DMAC1_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_RSW_SHIFT, + DMAC1_CHCFG_n_RSW); + } + + /* TM : Single transfer */ + /* SEL : Channel setting */ + /* HIEN, LOEN : On-chip peripheral module request */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_TM_SHIFT, + DMAC1_CHCFG_n_TM); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 1, + DMAC1_CHCFG_n_SEL_SHIFT, + DMAC1_CHCFG_n_SEL); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 1, + DMAC1_CHCFG_n_HIEN_SHIFT, + DMAC1_CHCFG_n_HIEN); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_LOEN_SHIFT, + DMAC1_CHCFG_n_LOEN); + + /* ---- Set factor by specified on-chip peripheral module request ---- */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_AM], + DMAC1_CHCFG_n_AM_SHIFT, + DMAC1_CHCFG_n_AM); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_LVL], + DMAC1_CHCFG_n_LVL_SHIFT, + DMAC1_CHCFG_n_LVL); + if (usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD] != DMAC_INDEFINE) + { + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD], + DMAC1_CHCFG_n_REQD_SHIFT, + DMAC1_CHCFG_n_REQD); + } + else + { + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + req_direction, + DMAC1_CHCFG_n_REQD_SHIFT, + DMAC1_CHCFG_n_REQD); + } + RZA_IO_RegWrite_32(&DMAC01.DMARS, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_RID], + DMAC01_DMARS_CH1_RID_SHIFT, + DMAC01_DMARS_CH1_RID); + RZA_IO_RegWrite_32(&DMAC01.DMARS, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_MID], + DMAC01_DMARS_CH1_MID_SHIFT, + DMAC01_DMARS_CH1_MID); + + /* PR : Round robin mode */ + RZA_IO_RegWrite_32(&DMAC07.DCTRL_0_7, + 1, + DMAC07_DCTRL_0_7_PR_SHIFT, + DMAC07_DCTRL_0_7_PR); + } +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC1_Open +* Description : Enables DMAC channel 1 transfer. +* Arguments : uint32_t req : DMAC request mode +* Return Value : 0 : Succeeded in enabling DMA transfer +* : -1 : Failed to enable DMA transfer (due to DMA operation) +*******************************************************************************/ +int32_t usb0_host_DMAC1_Open (uint32_t req) +{ + int32_t ret; + volatile uint8_t dummy; + + /* Transferable? */ + if ((0 == RZA_IO_RegRead_32(&DMAC1.CHSTAT_n, + DMAC1_CHSTAT_n_EN_SHIFT, + DMAC1_CHSTAT_n_EN)) && + (0 == RZA_IO_RegRead_32(&DMAC1.CHSTAT_n, + DMAC1_CHSTAT_n_TACT_SHIFT, + DMAC1_CHSTAT_n_TACT))) + { + /* Clear Channel Status Register */ + RZA_IO_RegWrite_32(&DMAC1.CHCTRL_n, + 1, + DMAC1_CHCTRL_n_SWRST_SHIFT, + DMAC1_CHCTRL_n_SWRST); + dummy = RZA_IO_RegRead_32(&DMAC1.CHCTRL_n, + DMAC1_CHCTRL_n_SWRST_SHIFT, + DMAC1_CHCTRL_n_SWRST); + /* Enable DMA transfer */ + RZA_IO_RegWrite_32(&DMAC1.CHCTRL_n, + 1, + DMAC1_CHCTRL_n_SETEN_SHIFT, + DMAC1_CHCTRL_n_SETEN); + + /* ---- Request by software ---- */ + if (DMAC_REQ_MODE_SOFT == req) + { + /* DMA transfer Request by software */ + RZA_IO_RegWrite_32(&DMAC1.CHCTRL_n, + 1, + DMAC1_CHCTRL_n_STG_SHIFT, + DMAC1_CHCTRL_n_STG); + } + + ret = 0; + } + else + { + ret = -1; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC1_Close +* Description : Aborts DMAC channel 1 transfer. Returns the remaining transfer +* : byte count at the time of DMA transfer abort to the argument +* : *remain. +* Arguments : uint32_t * remain : Remaining transfer byte count when +* : : DMA transfer is aborted +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC1_Close (uint32_t * remain) +{ + + /* ==== Abort transfer ==== */ + RZA_IO_RegWrite_32(&DMAC1.CHCTRL_n, + 1, + DMAC1_CHCTRL_n_CLREN_SHIFT, + DMAC1_CHCTRL_n_CLREN); + + while (1 == RZA_IO_RegRead_32(&DMAC1.CHSTAT_n, + DMAC1_CHSTAT_n_TACT_SHIFT, + DMAC1_CHSTAT_n_TACT)) + { + /* Loop until transfer is aborted */ + } + + while (1 == RZA_IO_RegRead_32(&DMAC1.CHSTAT_n, + DMAC1_CHSTAT_n_EN_SHIFT, + DMAC1_CHSTAT_n_EN)) + { + /* Loop until 0 is set in EN before checking the remaining transfer byte count */ + } + /* ==== Obtain remaining transfer byte count ==== */ + *remain = DMAC1.CRTB_n; +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC1_Load_Set +* Description : Sets the transfer source address, transfer destination +* : address, and total transfer byte count respectively +* : specified by the argument src_addr, dst_addr, and count to +* : DMAC channel 1 as DMA transfer information. +* : Sets the register set selected by the CHCFG_n register +* : RSEL bit from the Next0 or Next1 register set. +* : This function should be called when DMA transfer of DMAC +* : channel 1 is aboted. +* Arguments : uint32_t src_addr : Transfer source address +* : uint32_t dst_addr : Transfer destination address +* : uint32_t count : Total transfer byte count +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC1_Load_Set (uint32_t src_addr, uint32_t dst_addr, uint32_t count) +{ + uint8_t reg_set; + + /* Obtain register set in use */ + reg_set = RZA_IO_RegRead_32(&DMAC1.CHSTAT_n, + DMAC1_CHSTAT_n_SR_SHIFT, + DMAC1_CHSTAT_n_SR); + + /* ==== Load ==== */ + if (0 == reg_set) + { + /* ---- Next0 Register Set ---- */ + DMAC1.N0SA_n = src_addr; /* Start address of transfer source */ + DMAC1.N0DA_n = dst_addr; /* Start address of transfer destination */ + DMAC1.N0TB_n = count; /* Total transfer byte count */ + } + else + { + /* ---- Next1 Register Set ---- */ + DMAC1.N1SA_n = src_addr; /* Start address of transfer source */ + DMAC1.N1DA_n = dst_addr; /* Start address of transfer destination */ + DMAC1.N1TB_n = count; /* Total transfer byte count */ + } +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC2_PeriReqInit +* Description : Sets the register mode for DMA mode and the on-chip peripheral +* : module request for transfer request for DMAC channel 2. +* : Executes DMAC initial setting using the DMA information +* : specified by the argument *trans_info and the enabled/disabled +* : continuous transfer specified by the argument continuation. +* : Registers DMAC channel 2 interrupt handler function and sets +* : the interrupt priority level. Then enables transfer completion +* : interrupt. +* Arguments : dmac_transinfo_t * trans_info : Setting information to DMAC +* : : register +* : uint32_t dmamode : DMA mode (only for DMAC_MODE_REGISTER) +* : uint32_t continuation : Set continuous transfer to be valid +* : : after DMA transfer has been completed +* : DMAC_SAMPLE_CONTINUATION : Execute continuous transfer +* : DMAC_SAMPLE_SINGLE : Do not execute continuous +* : : transfer +* : uint32_t request_factor : Factor for on-chip peripheral module +* : : request +* : DMAC_REQ_OSTM0TINT : OSTM_0 compare match +* : DMAC_REQ_OSTM1TINT : OSTM_1 compare match +* : DMAC_REQ_TGI0A : MTU2_0 input capture/compare match +* : : +* : uint32_t req_direction : Setting value of CHCFG_n register +* : : REQD bit +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC2_PeriReqInit (const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction) +{ + /* ==== Register mode ==== */ + if (DMAC_MODE_REGISTER == dmamode) + { + /* ==== Next0 register set ==== */ + DMAC2.N0SA_n = trans_info->src_addr; /* Start address of transfer source */ + DMAC2.N0DA_n = trans_info->dst_addr; /* Start address of transfer destination */ + DMAC2.N0TB_n = trans_info->count; /* Total transfer byte count */ + + /* DAD : Transfer destination address counting direction */ + /* SAD : Transfer source address counting direction */ + /* DDS : Transfer destination transfer size */ + /* SDS : Transfer source transfer size */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + trans_info->daddr_dir, + DMAC2_CHCFG_n_DAD_SHIFT, + DMAC2_CHCFG_n_DAD); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + trans_info->saddr_dir, + DMAC2_CHCFG_n_SAD_SHIFT, + DMAC2_CHCFG_n_SAD); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + trans_info->dst_size, + DMAC2_CHCFG_n_DDS_SHIFT, + DMAC2_CHCFG_n_DDS); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + trans_info->src_size, + DMAC2_CHCFG_n_SDS_SHIFT, + DMAC2_CHCFG_n_SDS); + + /* DMS : Register mode */ + /* RSEL : Select Next0 register set */ + /* SBE : No discharge of buffer data when aborted */ + /* DEM : No DMA interrupt mask */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_DMS_SHIFT, + DMAC2_CHCFG_n_DMS); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_RSEL_SHIFT, + DMAC2_CHCFG_n_RSEL); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_SBE_SHIFT, + DMAC2_CHCFG_n_SBE); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_DEM_SHIFT, + DMAC2_CHCFG_n_DEM); + + /* ---- Continuous transfer ---- */ + if (DMAC_SAMPLE_CONTINUATION == continuation) + { + /* REN : Execute continuous transfer */ + /* RSW : Change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 1, + DMAC2_CHCFG_n_REN_SHIFT, + DMAC2_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 1, + DMAC2_CHCFG_n_RSW_SHIFT, + DMAC2_CHCFG_n_RSW); + } + /* ---- Single transfer ---- */ + else + { + /* REN : Do not execute continuous transfer */ + /* RSW : Do not change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_REN_SHIFT, + DMAC2_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_RSW_SHIFT, + DMAC2_CHCFG_n_RSW); + } + + /* TM : Single transfer */ + /* SEL : Channel setting */ + /* HIEN, LOEN : On-chip peripheral module request */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_TM_SHIFT, + DMAC2_CHCFG_n_TM); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 2, + DMAC2_CHCFG_n_SEL_SHIFT, + DMAC2_CHCFG_n_SEL); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 1, + DMAC2_CHCFG_n_HIEN_SHIFT, + DMAC2_CHCFG_n_HIEN); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_LOEN_SHIFT, + DMAC2_CHCFG_n_LOEN); + + /* ---- Set factor by specified on-chip peripheral module request ---- */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_AM], + DMAC2_CHCFG_n_AM_SHIFT, + DMAC2_CHCFG_n_AM); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_LVL], + DMAC2_CHCFG_n_LVL_SHIFT, + DMAC2_CHCFG_n_LVL); + if (usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD] != DMAC_INDEFINE) + { + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD], + DMAC2_CHCFG_n_REQD_SHIFT, + DMAC2_CHCFG_n_REQD); + } + else + { + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + req_direction, + DMAC2_CHCFG_n_REQD_SHIFT, + DMAC2_CHCFG_n_REQD); + } + RZA_IO_RegWrite_32(&DMAC23.DMARS, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_RID], + DMAC23_DMARS_CH2_RID_SHIFT, + DMAC23_DMARS_CH2_RID); + RZA_IO_RegWrite_32(&DMAC23.DMARS, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_MID], + DMAC23_DMARS_CH2_MID_SHIFT, + DMAC23_DMARS_CH2_MID); + + /* PR : Round robin mode */ + RZA_IO_RegWrite_32(&DMAC07.DCTRL_0_7, + 1, + DMAC07_DCTRL_0_7_PR_SHIFT, + DMAC07_DCTRL_0_7_PR); + } +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC2_Open +* Description : Enables DMAC channel 2 transfer. +* Arguments : uint32_t req : DMAC request mode +* Return Value : 0 : Succeeded in enabling DMA transfer +* : -1 : Failed to enable DMA transfer (due to DMA operation) +*******************************************************************************/ +int32_t usb0_host_DMAC2_Open (uint32_t req) +{ + int32_t ret; + volatile uint8_t dummy; + + /* Transferable? */ + if ((0 == RZA_IO_RegRead_32(&DMAC2.CHSTAT_n, + DMAC2_CHSTAT_n_EN_SHIFT, + DMAC2_CHSTAT_n_EN)) && + (0 == RZA_IO_RegRead_32(&DMAC2.CHSTAT_n, + DMAC2_CHSTAT_n_TACT_SHIFT, + DMAC2_CHSTAT_n_TACT))) + { + /* Clear Channel Status Register */ + RZA_IO_RegWrite_32(&DMAC2.CHCTRL_n, + 1, + DMAC2_CHCTRL_n_SWRST_SHIFT, + DMAC2_CHCTRL_n_SWRST); + dummy = RZA_IO_RegRead_32(&DMAC2.CHCTRL_n, + DMAC2_CHCTRL_n_SWRST_SHIFT, + DMAC2_CHCTRL_n_SWRST); + /* Enable DMA transfer */ + RZA_IO_RegWrite_32(&DMAC2.CHCTRL_n, + 1, + DMAC2_CHCTRL_n_SETEN_SHIFT, + DMAC2_CHCTRL_n_SETEN); + + /* ---- Request by software ---- */ + if (DMAC_REQ_MODE_SOFT == req) + { + /* DMA transfer Request by software */ + RZA_IO_RegWrite_32(&DMAC2.CHCTRL_n, + 1, + DMAC2_CHCTRL_n_STG_SHIFT, + DMAC2_CHCTRL_n_STG); + } + + ret = 0; + } + else + { + ret = -1; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC2_Close +* Description : Aborts DMAC channel 2 transfer. Returns the remaining transfer +* : byte count at the time of DMA transfer abort to the argument +* : *remain. +* Arguments : uint32_t * remain : Remaining transfer byte count when +* : : DMA transfer is aborted +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC2_Close (uint32_t * remain) +{ + + /* ==== Abort transfer ==== */ + RZA_IO_RegWrite_32(&DMAC2.CHCTRL_n, + 1, + DMAC2_CHCTRL_n_CLREN_SHIFT, + DMAC2_CHCTRL_n_CLREN); + + while (1 == RZA_IO_RegRead_32(&DMAC2.CHSTAT_n, + DMAC2_CHSTAT_n_TACT_SHIFT, + DMAC2_CHSTAT_n_TACT)) + { + /* Loop until transfer is aborted */ + } + + while (1 == RZA_IO_RegRead_32(&DMAC2.CHSTAT_n, + DMAC2_CHSTAT_n_EN_SHIFT, + DMAC2_CHSTAT_n_EN)) + { + /* Loop until 0 is set in EN before checking the remaining transfer byte count */ + } + /* ==== Obtain remaining transfer byte count ==== */ + *remain = DMAC2.CRTB_n; +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC2_Load_Set +* Description : Sets the transfer source address, transfer destination +* : address, and total transfer byte count respectively +* : specified by the argument src_addr, dst_addr, and count to +* : DMAC channel 2 as DMA transfer information. +* : Sets the register set selected by the CHCFG_n register +* : RSEL bit from the Next0 or Next1 register set. +* : This function should be called when DMA transfer of DMAC +* : channel 2 is aboted. +* Arguments : uint32_t src_addr : Transfer source address +* : uint32_t dst_addr : Transfer destination address +* : uint32_t count : Total transfer byte count +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC2_Load_Set (uint32_t src_addr, uint32_t dst_addr, uint32_t count) +{ + uint8_t reg_set; + + /* Obtain register set in use */ + reg_set = RZA_IO_RegRead_32(&DMAC2.CHSTAT_n, + DMAC2_CHSTAT_n_SR_SHIFT, + DMAC2_CHSTAT_n_SR); + + /* ==== Load ==== */ + if (0 == reg_set) + { + /* ---- Next0 Register Set ---- */ + DMAC2.N0SA_n = src_addr; /* Start address of transfer source */ + DMAC2.N0DA_n = dst_addr; /* Start address of transfer destination */ + DMAC2.N0TB_n = count; /* Total transfer byte count */ + } + else + { + /* ---- Next1 Register Set ---- */ + DMAC2.N1SA_n = src_addr; /* Start address of transfer source */ + DMAC2.N1DA_n = dst_addr; /* Start address of transfer destination */ + DMAC2.N1TB_n = count; /* Total transfer byte count */ + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb0/src/userdef/usb0_host_userdef.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,778 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_userdef.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include <stdio.h> +#include "cmsis_os.h" +#include "r_typedefs.h" +#include "iodefine.h" +#include "devdrv_usb_host_api.h" +#include "usb0_host.h" +#include "MBRZA1H.h" /* INTC Driver Header */ +#include "usb0_host_dmacdrv.h" +#include "ohci_wrapp_RZ_A1_local.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define DUMMY_ACCESS OSTM0CNT + +/* #define CACHE_WRITEBACK */ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +extern int32_t io_cwb(unsigned long start, unsigned long end); + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb0_host_enable_dmac0(uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc); +static void usb0_host_enable_dmac1(uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc); +static void Userdef_USB_usb0_host_delay_10us_2(void); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_d0fifo_dmaintid +* Description : get D0FIFO DMA Interrupt ID +* Arguments : none +* Return Value : D0FIFO DMA Interrupt ID +*******************************************************************************/ +uint16_t Userdef_USB_usb0_host_d0fifo_dmaintid (void) +{ +#if(1) /* ohci_wrapp */ + return 0xFFFF; +#else + return DMAINT1_IRQn; +#endif +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_d1fifo_dmaintid +* Description : get D1FIFO DMA Interrupt ID +* Arguments : none +* Return Value : D1FIFO DMA Interrupt ID +*******************************************************************************/ +uint16_t Userdef_USB_usb0_host_d1fifo_dmaintid (void) +{ +#if(1) /* ohci_wrapp */ + return 0xFFFF; +#else + return DMAINT2_IRQn; +#endif +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_attach +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_attach (void) +{ +// printf("\n"); +// printf("channel 0 attach device\n"); +// printf("\n"); + ohciwrapp_loc_Connect(1); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_detach +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_detach (void) +{ +// printf("\n"); +// printf("channel 0 detach device\n"); +// printf("\n"); + ohciwrapp_loc_Connect(0); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_delay_1ms +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_delay_1ms (void) +{ + osDelay(1); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_delay_xms +* Description : Wait for the software in the period of time specified by the +* : argument. +* : Alter this function according to the user's system. +* Arguments : uint32_t msec ; Wait Time (msec) +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_delay_xms (uint32_t msec) +{ + osDelay(msec); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_delay_10us +* Description : Waits for software for the period specified by the argument. +* : Alter this function according to the user's system. +* Arguments : uint32_t usec ; Wait Time(x 10usec) +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_delay_10us (uint32_t usec) +{ + volatile int i; + + /* Wait 10us (Please change for your MCU) */ + for (i = 0; i < usec; ++i) + { + Userdef_USB_usb0_host_delay_10us_2(); + } +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_delay_10us_2 +* Description : Waits for software for the period specified by the argument. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +static void Userdef_USB_usb0_host_delay_10us_2 (void) +{ + volatile int i; + volatile unsigned long tmp; + + /* Wait 1us (Please change for your MCU) */ + for (i = 0; i < 14; ++i) + { + tmp = DUMMY_ACCESS; + } +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_delay_500ns +* Description : Wait for software for 500ns. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_delay_500ns (void) +{ + volatile int i; + volatile unsigned long tmp; + + /* Wait 500ns (Please change for your MCU) */ + /* Wait 500ns I clock 266MHz */ + tmp = DUMMY_ACCESS; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_start_dma +* Description : Enables DMA transfer on the information specified by the argument. +* : Set DMAC register by this function to enable DMA transfer. +* : After executing this function, USB module is set to start DMA +* : transfer. DMA transfer should not wait for DMA transfer complete. +* Arguments : USB_HOST_DMA_t *dma : DMA parameter +* : typedef struct{ +* : uint32_t fifo; FIFO for using +* : uint32_t buffer; Start address of transfer source/destination +* : uint32_t bytes; Transfer size(Byte) +* : uint32_t dir; Transfer direction(0:Buffer->FIFO, 1:FIFO->Buffer) +* : uint32_t size; DMA transfer size +* : } USB_HOST_DMA_t; +* : uint16_t dfacc ; 0 : cycle steal mode +* : 1 : 16byte continuous mode +* : 2 : 32byte continuous mode +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_start_dma (USB_HOST_DMA_t * dma, uint16_t dfacc) +{ + uint32_t trncount; + uint32_t src; + uint32_t dst; + uint32_t size; + uint32_t dir; +#ifdef CACHE_WRITEBACK + uint32_t ptr; +#endif + + trncount = dma->bytes; + dir = dma->dir; + + if (dir == USB_HOST_FIFO2BUF) + { + /* DxFIFO determination */ + dst = dma->buffer; +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB200.D1FIFO.UINT32); + } + size = dma->size; + + if (size == 0) + { + src += 3; /* byte access */ + } + else if (size == 1) + { + src += 2; /* short access */ + } + else + { + /* Do Nothing */ + } +#else + size = dma->size; + + if (size == 2) + { + /* 32bit access */ + if (dfacc == 2) + { + /* 32byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFOB0); + } + else + { + src = (uint32_t)(&USB200.D1FIFOB0); + } + } + else if (dfacc == 1) + { + /* 16byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFOB0); + } + else + { + src = (uint32_t)(&USB200.D1FIFOB0); + } + } + else + { + /* normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB200.D1FIFO.UINT32); + } + } + } + else if (size == 1) + { + /* 16bit access */ + dfacc = 0; /* force normal access */ + + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB200.D1FIFO.UINT32); + } + src += 2; /* short access */ + } + else + { + /* 8bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB200.D1FIFO.UINT32); + } + src += 3; /* byte access */ + } +#endif + } + else + { + /* DxFIFO determination */ + src = dma->buffer; +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB200.D1FIFO.UINT32); + } + size = dma->size; + + if (size == 0) + { + dst += 3; /* byte access */ + } + else if (size == 1) + { + dst += 2; /* short access */ + } + else + { + /* Do Nothing */ + } +#else + size = dma->size; + if (size == 2) + { + /* 32bit access */ + if (dfacc == 2) + { + /* 32byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFOB0); + } + else + { + dst = (uint32_t)(&USB200.D1FIFOB0); + } + } + else if (dfacc == 1) + { + /* 16byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFOB0); + } + else + { + dst = (uint32_t)(&USB200.D1FIFOB0); + } + } + else + { + /* normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB200.D1FIFO.UINT32); + } + } + } + else if (size == 1) + { + /* 16bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB200.D1FIFO.UINT32); + } + dst += 2; /* short access */ + } + else + { + /* 8bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB200.D1FIFO.UINT32); + } + dst += 3; /* byte access */ + } +#endif + } + +#ifdef CACHE_WRITEBACK + ptr = (uint32_t)dma->buffer; + if ((ptr & 0x20000000ul) == 0) + { + io_cwb((uint32_t)ptr,(uint32_t)(ptr)+trncount); + } +#endif + + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + usb0_host_enable_dmac0(src, dst, trncount, size, dir, dma->fifo, dfacc); + } + else + { + usb0_host_enable_dmac1(src, dst, trncount, size, dir, dma->fifo, dfacc); + } +} + +/******************************************************************************* +* Function Name: usb0_host_enable_dmac0 +* Description : Enables DMA transfer on the information specified by the argument. +* Arguments : uint32_t src : src address +* : uint32_t dst : dst address +* : uint32_t count : transfer byte +* : uint32_t size : transfer size +* : uint32_t dir : direction +* : uint32_t fifo : FIFO(D0FIFO or D1FIFO) +* : uint16_t dfacc : 0 : normal access +* : : 1 : 16byte access +* : : 2 : 32byte access +* Return Value : none +*******************************************************************************/ +static void usb0_host_enable_dmac0 (uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc) +{ + dmac_transinfo_t trans_info; + uint32_t request_factor = 0; + int32_t ret; + + /* ==== Variable setting for DMAC initialization ==== */ + trans_info.src_addr = (uint32_t)src; /* Start address of transfer source */ + trans_info.dst_addr = (uint32_t)dst; /* Start address of transfer destination */ + trans_info.count = (uint32_t)count; /* Total byte count to be transferred */ +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } +#else + if (dfacc == 2) + { + /* 32byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_256; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_256; /* Transfer destination transfer size */ + } + else if (dfacc == 1) + { + /* 16byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_128; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_128; /* Transfer destination transfer size */ + } + else + { + /* normal access */ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } + } +#endif + + if (dir == USB_HOST_FIFO2BUF) + { + request_factor = DMAC_REQ_USB0_DMA0_RX; /* USB_0 channel 0 receive FIFO full */ + trans_info.saddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer destination address */ + } + else if (dir == USB_HOST_BUF2FIFO) + { + request_factor = DMAC_REQ_USB0_DMA0_TX; /* USB_0 channel 0 receive FIFO empty */ + trans_info.saddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer destination address */ + } + else + { + /* Do Nothing */ + } + + /* ==== DMAC initialization ==== */ + usb0_host_DMAC1_PeriReqInit((const dmac_transinfo_t *)&trans_info, + DMAC_MODE_REGISTER, + DMAC_SAMPLE_SINGLE, + request_factor, + 0); /* Don't care DMAC_REQ_REQD is setting in usb0_host_DMAC1_PeriReqInit() */ + + /* ==== DMAC startup ==== */ + ret = usb0_host_DMAC1_Open(DMAC_REQ_MODE_PERI); + + if (ret != 0) + { +// printf("DMAC1 Open error!!\n"); + } + + return; +} + +/******************************************************************************* +* Function Name: usb0_host_enable_dmac1 +* Description : Enables DMA transfer on the information specified by the argument. +* Arguments : uint32_t src : src address +* : uint32_t dst : dst address +* : uint32_t count : transfer byte +* : uint32_t size : transfer size +* : uint32_t dir : direction +* : uint32_t fifo : FIFO(D0FIFO or D1FIFO) +* : uint16_t dfacc : 0 : normal access +* : : 1 : 16byte access +* : : 2 : 32byte access +* Return Value : none +*******************************************************************************/ +static void usb0_host_enable_dmac1 (uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc) +{ + dmac_transinfo_t trans_info; + uint32_t request_factor = 0; + int32_t ret; + + /* ==== Variable setting for DMAC initialization ==== */ + trans_info.src_addr = (uint32_t)src; /* Start address of transfer source */ + trans_info.dst_addr = (uint32_t)dst; /* Start address of transfer destination */ + trans_info.count = (uint32_t)count; /* Total byte count to be transferred */ +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } +#else + if (dfacc == 2) + { + /* 32byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_256; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_256; /* Transfer destination transfer size */ + } + else if (dfacc == 1) + { + /* 16byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_128; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_128; /* Transfer destination transfer size */ + } + else + { + /* normal access */ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } + } +#endif + + if (dir == USB_HOST_FIFO2BUF) + { + request_factor =DMAC_REQ_USB0_DMA1_RX; /* USB_0 channel 0 receive FIFO full */ + trans_info.saddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer destination address */ + } + else if (dir == USB_HOST_BUF2FIFO) + { + request_factor =DMAC_REQ_USB0_DMA1_TX; /* USB_0 channel 0 receive FIFO empty */ + trans_info.saddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer destination address */ + } + else + { + /* Do Nothing */ + } + + /* ==== DMAC initialization ==== */ + usb0_host_DMAC2_PeriReqInit((const dmac_transinfo_t *)&trans_info, + DMAC_MODE_REGISTER, + DMAC_SAMPLE_SINGLE, + request_factor, + 0); /* Don't care DMAC_REQ_REQD is setting in usb0_host_DMAC2_PeriReqInit() */ + + /* ==== DMAC startup ==== */ + ret = usb0_host_DMAC2_Open(DMAC_REQ_MODE_PERI); + + if (ret != 0) + { +// printf("DMAC2 Open error!!\n"); + } + + return; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_stop_dma0 +* Description : Disables DMA transfer. +* Arguments : none +* Return Value : uint32_t return Transfer Counter register(DMATCRn) value +* : regarding to the bus width. +* Notice : This function should be executed to DMAC executed at the time +* : of specification of D0_FIF0_DMA in dma->fifo. +*******************************************************************************/ +uint32_t Userdef_USB_usb0_host_stop_dma0 (void) +{ + uint32_t remain; + + /* ==== DMAC release ==== */ + usb0_host_DMAC1_Close(&remain); + + return remain; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_stop_dma1 +* Description : Disables DMA transfer. +* : This function should be executed to DMAC executed at the time +* : of specification of D1_FIF0_DMA in dma->fifo. +* Arguments : none +* Return Value : uint32_t return Transfer Counter register(DMATCRn) value +* : regarding to the bus width. +*******************************************************************************/ +uint32_t Userdef_USB_usb0_host_stop_dma1 (void) +{ + uint32_t remain; + + /* ==== DMAC release ==== */ + usb0_host_DMAC2_Close(&remain); + + return remain; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_notice +* Description : Notice of USER +* Arguments : const char *format +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_notice (const char * format) +{ +// printf(format); + + return; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_user_rdy +* Description : This function notify a user and wait for trigger +* Arguments : const char *format +* : uint16_t data +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_user_rdy (const char * format, uint16_t data) +{ +// printf(format, data); + getchar(); + + return; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/inc/usb1_host.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,156 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB1_HOST_H +#define USB1_HOST_H + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "devdrv_usb_host_api.h" +#include "usb_host.h" + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +extern const uint16_t g_usb1_host_bit_set[]; +extern uint32_t g_usb1_host_data_count[USB_HOST_MAX_PIPE_NO + 1]; +extern uint8_t *g_usb1_host_data_pointer[USB_HOST_MAX_PIPE_NO + 1]; + +extern uint16_t g_usb1_host_PipeIgnore[]; +extern uint16_t g_usb1_host_PipeTbl[]; +extern uint16_t g_usb1_host_pipe_status[]; +extern uint32_t g_usb1_host_PipeDataSize[]; + +extern USB_HOST_DMA_t g_usb1_host_DmaInfo[]; +extern uint16_t g_usb1_host_DmaPipe[]; +extern uint16_t g_usb1_host_DmaBval[]; +extern uint16_t g_usb1_host_DmaStatus[]; + +extern uint16_t g_usb1_host_driver_state; +extern uint16_t g_usb1_host_ConfigNum; +extern uint16_t g_usb1_host_CmdStage; +extern uint16_t g_usb1_host_bchg_flag; +extern uint16_t g_usb1_host_detach_flag; +extern uint16_t g_usb1_host_attach_flag; + +extern uint16_t g_usb1_host_UsbAddress; +extern uint16_t g_usb1_host_setUsbAddress; +extern uint16_t g_usb1_host_default_max_packet[USB_HOST_MAX_DEVICE + 1]; +extern uint16_t g_usb1_host_UsbDeviceSpeed; +extern uint16_t g_usb1_host_SupportUsbDeviceSpeed; + +extern uint16_t g_usb1_host_SavReq; +extern uint16_t g_usb1_host_SavVal; +extern uint16_t g_usb1_host_SavIndx; +extern uint16_t g_usb1_host_SavLen; + +extern uint16_t g_usb1_host_pipecfg[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb1_host_pipebuf[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb1_host_pipemaxp[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb1_host_pipeperi[USB_HOST_MAX_PIPE_NO + 1]; + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +/* ==== common ==== */ +void usb1_host_dma_stop_d0(uint16_t pipe, uint32_t remain); +void usb1_host_dma_stop_d1(uint16_t pipe, uint32_t remain); +uint16_t usb1_host_is_hispeed(void); +uint16_t usb1_host_is_hispeed_enable(void); +uint16_t usb1_host_start_send_transfer(uint16_t pipe, uint32_t size, uint8_t *data); +uint16_t usb1_host_write_buffer(uint16_t pipe); +uint16_t usb1_host_write_buffer_c(uint16_t pipe); +uint16_t usb1_host_write_buffer_d0(uint16_t pipe); +uint16_t usb1_host_write_buffer_d1(uint16_t pipe); +void usb1_host_start_receive_transfer(uint16_t pipe, uint32_t size, uint8_t *data); +uint16_t usb1_host_read_buffer(uint16_t pipe); +uint16_t usb1_host_read_buffer_c(uint16_t pipe); +uint16_t usb1_host_read_buffer_d0(uint16_t pipe); +uint16_t usb1_host_read_buffer_d1(uint16_t pipe); +uint16_t usb1_host_change_fifo_port(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw); +void usb1_host_set_curpipe(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw); +void usb1_host_set_curpipe2(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw, uint16_t dfacc); +uint16_t usb1_host_get_mbw(uint32_t trncount, uint32_t dtptr); +uint16_t usb1_host_read_dma(uint16_t pipe); +void usb1_host_stop_transfer(uint16_t pipe); +void usb1_host_brdy_int(uint16_t status, uint16_t int_enb); +void usb1_host_nrdy_int(uint16_t status, uint16_t int_enb); +void usb1_host_bemp_int(uint16_t status, uint16_t int_enb); +void usb1_host_setting_interrupt(uint8_t level); +void usb1_host_reset_module(uint16_t clockmode); +uint16_t usb1_host_get_buf_size(uint16_t pipe); +uint16_t usb1_host_get_mxps(uint16_t pipe); +void usb1_host_enable_brdy_int(uint16_t pipe); +void usb1_host_disable_brdy_int(uint16_t pipe); +void usb1_host_clear_brdy_sts(uint16_t pipe); +void usb1_host_enable_bemp_int(uint16_t pipe); +void usb1_host_disable_bemp_int(uint16_t pipe); +void usb1_host_clear_bemp_sts(uint16_t pipe); +void usb1_host_enable_nrdy_int(uint16_t pipe); +void usb1_host_disable_nrdy_int(uint16_t pipe); +void usb1_host_clear_nrdy_sts(uint16_t pipe); +void usb1_host_set_pid_buf(uint16_t pipe); +void usb1_host_set_pid_nak(uint16_t pipe); +void usb1_host_set_pid_stall(uint16_t pipe); +void usb1_host_clear_pid_stall(uint16_t pipe); +uint16_t usb1_host_get_pid(uint16_t pipe); +void usb1_host_set_sqclr(uint16_t pipe); +void usb1_host_set_sqset(uint16_t pipe); +void usb1_host_set_csclr(uint16_t pipe); +void usb1_host_aclrm(uint16_t pipe); +void usb1_host_set_aclrm(uint16_t pipe); +void usb1_host_clr_aclrm(uint16_t pipe); +uint16_t usb1_host_get_sqmon(uint16_t pipe); +uint16_t usb1_host_get_inbuf(uint16_t pipe); + +/* ==== host ==== */ +void usb1_host_init_pipe_status(void); +int32_t usb1_host_CtrlTransStart(uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len, uint8_t *Buf); +void usb1_host_SetupStage(uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len); +void usb1_host_CtrlReadStart(uint32_t Bsize, uint8_t *Table); +uint16_t usb1_host_CtrlWriteStart(uint32_t Bsize, uint8_t *Table); +void usb1_host_StatusStage(void); +void usb1_host_get_devadd(uint16_t addr, uint16_t *devadd); +void usb1_host_set_devadd(uint16_t addr, uint16_t *devadd); +void usb1_host_InitModule(void); +uint16_t usb1_host_CheckAttach(void); +void usb1_host_UsbDetach(void); +void usb1_host_UsbDetach2(void); +void usb1_host_UsbAttach(void); +uint16_t usb1_host_UsbBusReset(void); +int32_t usb1_host_UsbResume(void); +int32_t usb1_host_UsbSuspend(void); +void usb1_host_Enable_DetachINT(void); +void usb1_host_Disable_DetachINT(void); +void usb1_host_UsbStateManager(void); + + +#endif /* USB1_HOST_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/inc/usb1_host_api.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,112 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_api.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB1_HOST_API_H +#define USB1_HOST_API_H + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Variable Externs +*******************************************************************************/ + + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +void usb1_host_interrupt(uint32_t int_sense); +void usb1_host_dma_interrupt_d0fifo(uint32_t int_sense); +void usb1_host_dma_interrupt_d1fifo(uint32_t int_sense); + +uint16_t usb1_api_host_init(uint8_t int_level, uint16_t mode, uint16_t clockmode); +int32_t usb1_api_host_enumeration(uint16_t devadr); +int32_t usb1_api_host_detach(void); +int32_t usb1_api_host_data_in(uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t usb1_api_host_data_out(uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t usb1_api_host_control_transfer(uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len, uint8_t *Buf); +int32_t usb1_api_host_set_endpoint(uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t *configdescriptor); +int32_t usb1_api_host_clear_endpoint(USB_HOST_CFG_PIPETBL_t *user_table); +int32_t usb1_api_host_clear_endpoint_pipe(uint16_t pipe_sel, USB_HOST_CFG_PIPETBL_t *user_table); +uint16_t usb1_api_host_SetEndpointTable(uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t *Table); +int32_t usb1_api_host_data_count(uint16_t pipe, uint32_t *data_count); + +int32_t usb1_api_host_GetDeviceDescriptor(uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t usb1_api_host_GetConfigDescriptor(uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t usb1_api_host_SetConfig(uint16_t devadr, uint16_t confignum); +int32_t usb1_api_host_SetInterface(uint16_t devadr, uint16_t interface_alt, uint16_t interface_index); +int32_t usb1_api_host_ClearStall(uint16_t devadr, uint16_t ep_dir); +uint16_t usb1_api_host_GetUsbDeviceState(void); + +void usb1_api_host_elt_4_4(void); +void usb1_api_host_elt_4_5(void); +void usb1_api_host_elt_4_6(void); +void usb1_api_host_elt_4_7(void); +void usb1_api_host_elt_4_8(void); +void usb1_api_host_elt_4_9(void); +void usb1_api_host_elt_get_desc(void); + +void usb1_host_EL_ModeInit(void); +void usb1_host_EL_SetUACT(void); +void usb1_host_EL_ClearUACT(void); +void usb1_host_EL_SetTESTMODE(uint16_t mode); +void usb1_host_EL_ClearNRDYSTS(uint16_t pipe); +uint16_t usb1_host_EL_GetINTSTS1(void); +void usb1_host_EL_UsbBusReset(void); +void usb1_host_EL_UsbAttach(void); +void usb1_host_EL_SetupStage(uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len); +void usb1_host_EL_StatusStage(void); +void usb1_host_EL_CtrlReadStart(uint32_t Bsize, uint8_t *Table); +int32_t usb1_host_EL_UsbSuspend(void); +int32_t usb1_host_EL_UsbResume(void); + +#if 0 /* prototype in devdrv_usb_host_api.h */ +uint16_t Userdef_USB_usb1_host_d0fifo_dmaintid(void); +uint16_t Userdef_USB_usb1_host_d1fifo_dmaintid(void); +void Userdef_USB_usb1_host_attach(void); +void Userdef_USB_usb1_host_detach(void); +void Userdef_USB_usb1_host_delay_1ms(void); +void Userdef_USB_usb1_host_delay_xms(uint32_t msec); +void Userdef_USB_usb1_host_delay_10us(uint32_t usec); +void Userdef_USB_usb1_host_delay_500ns(void); +void Userdef_USB_usb1_host_start_dma(USB_HOST_DMA_t *dma, uint16_t dfacc); +uint32_t Userdef_USB_usb1_host_stop_dma0(void); +uint32_t Userdef_USB_usb1_host_stop_dma1(void); +#endif + +#endif /* USB1_HOST_API_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/inc/usb1_host_dmacdrv.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,139 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_dmacdrv.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB1_HOST_DMACDRV_H +#define USB1_HOST_DMACDRV_H + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ +typedef struct dmac_transinfo +{ + uint32_t src_addr; /* Transfer source address */ + uint32_t dst_addr; /* Transfer destination address */ + uint32_t count; /* Transfer byte count */ + uint32_t src_size; /* Transfer source data size */ + uint32_t dst_size; /* Transfer destination data size */ + uint32_t saddr_dir; /* Transfer source address direction */ + uint32_t daddr_dir; /* Transfer destination address direction */ +} dmac_transinfo_t; + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +/* ==== Transfer specification of the sample program ==== */ +#define DMAC_SAMPLE_SINGLE (0) /* Single transfer */ +#define DMAC_SAMPLE_CONTINUATION (1) /* Continuous transfer (use REN bit) */ + +/* ==== DMA modes ==== */ +#define DMAC_MODE_REGISTER (0) /* Register mode */ +#define DMAC_MODE_LINK (1) /* Link mode */ + +/* ==== Transfer requests ==== */ +#define DMAC_REQ_MODE_EXT (0) /* External request */ +#define DMAC_REQ_MODE_PERI (1) /* On-chip peripheral module request */ +#define DMAC_REQ_MODE_SOFT (2) /* Auto-request (request by software) */ + +/* ==== DMAC transfer sizes ==== */ +#define DMAC_TRANS_SIZE_8 (0) /* 8 bits */ +#define DMAC_TRANS_SIZE_16 (1) /* 16 bits */ +#define DMAC_TRANS_SIZE_32 (2) /* 32 bits */ +#define DMAC_TRANS_SIZE_64 (3) /* 64 bits */ +#define DMAC_TRANS_SIZE_128 (4) /* 128 bits */ +#define DMAC_TRANS_SIZE_256 (5) /* 256 bits */ +#define DMAC_TRANS_SIZE_512 (6) /* 512 bits */ +#define DMAC_TRANS_SIZE_1024 (7) /* 1024 bits */ + +/* ==== Address increment for transferring ==== */ +#define DMAC_TRANS_ADR_NO_INC (1) /* Not increment */ +#define DMAC_TRANS_ADR_INC (0) /* Increment */ + +/* ==== Method for detecting DMA request ==== */ +#define DMAC_REQ_DET_FALL (0) /* Falling edge detection */ +#define DMAC_REQ_DET_RISE (1) /* Rising edge detection */ +#define DMAC_REQ_DET_LOW (2) /* Low level detection */ +#define DMAC_REQ_DET_HIGH (3) /* High level detection */ + +/* ==== Request Direction ==== */ +#define DMAC_REQ_DIR_SRC (0) /* DMAREQ is the source/ DMAACK is active when reading */ +#define DMAC_REQ_DIR_DST (1) /* DMAREQ is the destination/ DMAACK is active when writing */ + +/* ==== Descriptors ==== */ +#define DMAC_DESC_HEADER (0) /* Header */ +#define DMAC_DESC_SRC_ADDR (1) /* Source Address */ +#define DMAC_DESC_DST_ADDR (2) /* Destination Address */ +#define DMAC_DESC_COUNT (3) /* Transaction Byte */ +#define DMAC_DESC_CHCFG (4) /* Channel Confg */ +#define DMAC_DESC_CHITVL (5) /* Channel Interval */ +#define DMAC_DESC_CHEXT (6) /* Channel Extension */ +#define DMAC_DESC_LINK_ADDR (7) /* Link Address */ + +/* ==== On-chip peripheral module requests ===== */ +typedef enum dmac_request_factor +{ + DMAC_REQ_USB0_DMA0_TX, /* USB_0 channel 0 transmit FIFO empty */ + DMAC_REQ_USB0_DMA0_RX, /* USB_0 channel 0 receive FIFO full */ + DMAC_REQ_USB0_DMA1_TX, /* USB_0 channel 1 transmit FIFO empty */ + DMAC_REQ_USB0_DMA1_RX, /* USB_0 channel 1 receive FIFO full */ + DMAC_REQ_USB1_DMA0_TX, /* USB_1 channel 0 transmit FIFO empty */ + DMAC_REQ_USB1_DMA0_RX, /* USB_1 channel 0 receive FIFO full */ + DMAC_REQ_USB1_DMA1_TX, /* USB_1 channel 1 transmit FIFO empty */ + DMAC_REQ_USB1_DMA1_RX, /* USB_1 channel 1 receive FIFO full */ +} dmac_request_factor_t; + + +/******************************************************************************* +Variable Externs +*******************************************************************************/ + + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +void usb1_host_DMAC3_PeriReqInit(const dmac_transinfo_t *trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction); +int32_t usb1_host_DMAC3_Open(uint32_t req); +void usb1_host_DMAC3_Close(uint32_t *remain); +void usb1_host_DMAC3_Load_Set(uint32_t src_addr, uint32_t dst_addr, uint32_t count); + +void usb1_host_DMAC4_PeriReqInit(const dmac_transinfo_t *trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction); +int32_t usb1_host_DMAC4_Open(uint32_t req); +void usb1_host_DMAC4_Close(uint32_t *remain); +void usb1_host_DMAC4_Load_Set(uint32_t src_addr, uint32_t dst_addr, uint32_t count); + +#endif /* USB1_HOST_DMACDRV_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/src/common/usb1_host_dataio.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,2835 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_dataio.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +static uint16_t g_usb1_host_mbw[(USB_HOST_MAX_PIPE_NO + 1)]; + +static void usb1_host_start_receive_trns_c(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb1_host_start_receive_trns_d0(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb1_host_start_receive_trns_d1(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb1_host_start_receive_dma_d0(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb1_host_start_receive_dma_d1(uint16_t pipe, uint32_t size, uint8_t *data); +static uint16_t usb1_host_read_dma_d0(uint16_t pipe); +static uint16_t usb1_host_read_dma_d1(uint16_t pipe); +static uint16_t usb1_host_write_dma_d0(uint16_t pipe); +static uint16_t usb1_host_write_dma_d1(uint16_t pipe); + +static void usb1_host_read_c_fifo(uint16_t pipe, uint16_t count); +static void usb1_host_write_c_fifo(uint16_t Pipe, uint16_t count); +static void usb1_host_read_d0_fifo(uint16_t pipe, uint16_t count); +static void usb1_host_write_d0_fifo(uint16_t pipe, uint16_t count); +static void usb1_host_read_d1_fifo(uint16_t pipe, uint16_t count); +static void usb1_host_write_d1_fifo(uint16_t pipe, uint16_t count); + +static void usb1_host_clear_transaction_counter(uint16_t pipe); +static void usb1_host_set_transaction_counter(uint16_t pipe, uint32_t count); + +static uint32_t usb1_host_com_get_dmasize(uint32_t trncount, uint32_t dtptr); + +static uint16_t usb1_host_set_dfacc_d0(uint16_t mbw, uint32_t count); +static uint16_t usb1_host_set_dfacc_d1(uint16_t mbw, uint32_t count); + + +/******************************************************************************* +* Function Name: usb1_host_start_send_transfer +* Description : Starts the USB data communication using pipe specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data data Address +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_start_send_transfer (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t status; + uint16_t usefifo; + uint16_t mbw; + + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + usb1_host_clear_bemp_sts(pipe); + usb1_host_clear_brdy_sts(pipe); + usb1_host_clear_nrdy_sts(pipe); + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + + usefifo = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + case USB_HOST_D0FIFO_DMA: + usefifo = USB_HOST_D0USE; + break; + + case USB_HOST_D1FIFO_USE: + case USB_HOST_D1FIFO_DMA: + usefifo = USB_HOST_D1USE; + break; + + default: + usefifo = USB_HOST_CUSE; + break; + }; + + usb1_host_set_curpipe(USB_HOST_PIPE0, usefifo, USB_HOST_NO, mbw); + + usb1_host_clear_transaction_counter(pipe); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + status = usb1_host_write_buffer(pipe); + + if (status != USB_HOST_FIFOERROR) + { + usb1_host_set_pid_buf(pipe); + } + + return status; +} + +/******************************************************************************* +* Function Name: usb1_host_write_buffer +* Description : Writes data in the buffer allocated in the pipe specified by +* : the argument. The FIFO for using is set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_write_buffer (uint16_t pipe) +{ + uint16_t status; + uint16_t usefifo; + + g_usb1_host_PipeIgnore[pipe] = 0; + usefifo = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + status = usb1_host_write_buffer_d0(pipe); + break; + + case USB_HOST_D1FIFO_USE: + status = usb1_host_write_buffer_d1(pipe); + break; + + case USB_HOST_D0FIFO_DMA: + status = usb1_host_write_dma_d0(pipe); + break; + + case USB_HOST_D1FIFO_DMA: + status = usb1_host_write_dma_d1(pipe); + break; + + default: + status = usb1_host_write_buffer_c(pipe); + break; + }; + + switch (status) + { + case USB_HOST_WRITING: /* Continue of data write */ + usb1_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + usb1_host_enable_brdy_int(pipe); /* Enable Ready Interrupt */ + break; + + case USB_HOST_WRITEEND: /* End of data write */ + case USB_HOST_WRITESHRT: /* End of data write */ + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + + usb1_host_clear_nrdy_sts(pipe); + usb1_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + + /* for last transfer */ + usb1_host_enable_bemp_int(pipe); /* Enable Empty Interrupt */ + break; + + case USB_HOST_WRITEDMA: /* DMA write */ + usb1_host_clear_nrdy_sts(pipe); + usb1_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + usb1_host_disable_bemp_int(pipe); /* Disable Empty Interrupt */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_write_buffer_c +* Description : Writes data in the buffer allocated in the pipe specified in +* : the argument. Writes data by CPU transfer using CFIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_write_buffer_c (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + + if (pipe == USB_HOST_PIPE0) + { + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_CFIFO_WRITE, mbw); + } + else + { + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_NO, mbw); + } + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb1_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb1_host_write_c_fifo(pipe, (uint16_t)count); + + if (g_usb1_host_data_count[pipe] < (uint32_t)size) + { + g_usb1_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB201.CFIFOCTR, + USB_CFIFOCTR_BVAL_SHIFT, + USB_CFIFOCTR_BVAL) == 0) + { + USB201.CFIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb1_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_write_buffer_d0 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by CPU transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_write_buffer_d0 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D0USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb1_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb1_host_write_d0_fifo(pipe, (uint16_t)count); + + if (g_usb1_host_data_count[pipe] < (uint32_t)size) + { + g_usb1_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB201.D0FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + USB201.D0FIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb1_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_write_buffer_d1 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by CPU transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_write_buffer_d1 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D1USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb1_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb1_host_write_d1_fifo(pipe, (uint16_t)count); + + if (g_usb1_host_data_count[pipe] < (uint32_t)size) + { + g_usb1_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB201.D1FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + USB201.D1FIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb1_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_write_dma_d0 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by DMA transfer using D0FIFO. +* : The DMA-ch for using is specified by Userdef_USB_usb1_host_start_dma(). +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND : Write end +* : USB_HOST_WRITESHRT : short data +* : USB_HOST_WRITING : Continue of data write +* : USB_HOST_WRITEDMA : Write DMA +* : USB_HOST_FIFOERROR : FIFO status +*******************************************************************************/ +static uint16_t usb1_host_write_dma_d0 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + count = g_usb1_host_data_count[pipe]; + + if (count != 0) + { + g_usb1_host_DmaPipe[USB_HOST_D0FIFO] = pipe; + + if ((count % size) != 0) + { + g_usb1_host_DmaBval[USB_HOST_D0FIFO] = 1; + } + else + { + g_usb1_host_DmaBval[USB_HOST_D0FIFO] = 0; + } + + dfacc = usb1_host_set_dfacc_d0(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 0; /* 8bit transfer */ + } + + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].fifo = USB_HOST_D0FIFO_DMA; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].dir = USB_HOST_BUF2FIFO; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].buffer = (uint32_t)g_usb1_host_data_pointer[pipe]; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].bytes = count; + + Userdef_USB_usb1_host_start_dma(&g_usb1_host_DmaInfo[USB_HOST_D0FIFO], dfacc); + + usb1_host_set_curpipe2(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw, dfacc); + + RZA_IO_RegWrite_16(&USB201.D0FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + + g_usb1_host_data_count[pipe] = 0; + g_usb1_host_data_pointer[pipe] += count; + + status = USB_HOST_WRITEDMA; /* DMA write */ + } + else + { + if (RZA_IO_RegRead_16(&USB201.D0FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + RZA_IO_RegWrite_16(&USB201.D0FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); /* Short Packet */ + } + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_write_dma_d1 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by DMA transfer using D1FIFO. +* : The DMA-ch for using is specified by Userdef_USB_usb1_host_start_dma(). +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND : Write end +* : USB_HOST_WRITESHRT : short data +* : USB_HOST_WRITING : Continue of data write +* : USB_HOST_WRITEDMA : Write DMA +* : USB_HOST_FIFOERROR : FIFO status +*******************************************************************************/ +static uint16_t usb1_host_write_dma_d1 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + count = g_usb1_host_data_count[pipe]; + + if (count != 0) + { + g_usb1_host_DmaPipe[USB_HOST_D1FIFO] = pipe; + + if ((count % size) != 0) + { + g_usb1_host_DmaBval[USB_HOST_D1FIFO] = 1; + } + else + { + g_usb1_host_DmaBval[USB_HOST_D1FIFO] = 0; + } + + dfacc = usb1_host_set_dfacc_d1(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 0; /* 8bit transfer */ + } + + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].fifo = USB_HOST_D1FIFO_DMA; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].dir = USB_HOST_BUF2FIFO; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].buffer = (uint32_t)g_usb1_host_data_pointer[pipe]; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].bytes = count; + + Userdef_USB_usb1_host_start_dma(&g_usb1_host_DmaInfo[USB_HOST_D1FIFO], dfacc); + + usb1_host_set_curpipe2(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw , dfacc); + + RZA_IO_RegWrite_16(&USB201.D1FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + + g_usb1_host_data_count[pipe] = 0; + g_usb1_host_data_pointer[pipe] += count; + + status = USB_HOST_WRITEDMA; /* DMA write */ + } + else + { + if (RZA_IO_RegRead_16(&USB201.D1FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + RZA_IO_RegWrite_16(&USB201.D1FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); /* Short Packet */ + } + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_transfer +* Description : Starts USB data reception using the pipe specified in the argument. +* : The FIFO for using is set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +void usb1_host_start_receive_transfer (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t usefifo; + + usb1_host_clear_bemp_sts(pipe); + usb1_host_clear_brdy_sts(pipe); + usb1_host_clear_nrdy_sts(pipe); + + usefifo = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + usb1_host_start_receive_trns_d0(pipe, size, data); + break; + + case USB_HOST_D1FIFO_USE: + usb1_host_start_receive_trns_d1(pipe, size, data); + break; + + case USB_HOST_D0FIFO_DMA: + usb1_host_start_receive_dma_d0(pipe, size, data); + break; + + case USB_HOST_D1FIFO_DMA: + usb1_host_start_receive_dma_d1(pipe, size, data); + break; + + default: + usb1_host_start_receive_trns_c(pipe, size, data); + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_trns_c +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using CFIFO. +* : When storing data in the buffer allocated in the pipe specified in the +* : argument, BRDY interrupt is generated to read data +* : in the interrupt. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb1_host_start_receive_trns_c (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb1_host_set_pid_nak(pipe); + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_PipeIgnore[pipe] = 0; + + g_usb1_host_PipeDataSize[pipe] = size; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_CFIFO_READ, mbw); + USB201.CFIFOCTR = USB_HOST_BITBCLR; + + usb1_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + + usb1_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_trns_d0 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, BRDY interrupt is generated to read data in the +* : interrupt. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb1_host_start_receive_trns_d0 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb1_host_set_pid_nak(pipe); + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_PipeIgnore[pipe] = 0; + + g_usb1_host_PipeDataSize[pipe] = size; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, mbw); + + usb1_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + + usb1_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_trns_d1 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using D1FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, BRDY interrupt is generated to read data. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb1_host_start_receive_trns_d1 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb1_host_set_pid_nak(pipe); + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_PipeIgnore[pipe] = 0; + + g_usb1_host_PipeDataSize[pipe] = size; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, mbw); + + usb1_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + + usb1_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_dma_d0 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by DMA transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, delivered read request to DMAC to read data from +* : the buffer by DMAC. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb1_host_start_receive_dma_d0 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb1_host_set_pid_nak(pipe); + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_PipeIgnore[pipe] = 0; + + g_usb1_host_PipeDataSize[pipe] = 0; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, mbw); + + usb1_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + usb1_host_read_dma(pipe); + + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + } + else + { + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + } + + usb1_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_dma_d1 +* Description : Read data from the buffer allocated in the pipe specified in the argument. +* : Reads data by DMA transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, delivered read request to DMAC to read data from +* : the buffer by DMAC. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb1_host_start_receive_dma_d1 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb1_host_set_pid_nak(pipe); + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_PipeIgnore[pipe] = 0; + + g_usb1_host_PipeDataSize[pipe] = 0; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, mbw); + + usb1_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + usb1_host_read_dma(pipe); + + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + } + else + { + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + } + + usb1_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_read_buffer +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Uses FIF0 set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_read_buffer (uint16_t pipe) +{ + uint16_t status; + + g_usb1_host_PipeIgnore[pipe] = 0; + + if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_USE) + { + status = usb1_host_read_buffer_d0(pipe); + } + else if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_USE) + { + status = usb1_host_read_buffer_d1(pipe); + } + else + { + status = usb1_host_read_buffer_c(pipe); + } + + switch (status) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb1_host_disable_brdy_int(pipe); + g_usb1_host_PipeDataSize[pipe] -= g_usb1_host_data_count[pipe]; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + break; + + case USB_HOST_READOVER: /* buffer over */ + if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_USE) + { + USB201.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_USE) + { + USB201.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + USB201.CFIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#else + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; +#endif + g_usb1_host_PipeDataSize[pipe] -= g_usb1_host_data_count[pipe]; + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_buffer_c +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using CFIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_read_buffer_c (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb1_host_data_count[pipe]; + } + else if (g_usb1_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + } + + if (count == 0) /* 0 length packet */ + { + USB201.CFIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb1_host_read_c_fifo(pipe, (uint16_t)count); + } + + g_usb1_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_buffer_d0 +* Description : Reads data from the buffer allocated in the pipe specified in +* : the argument. +* : Reads data by CPU transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_read_buffer_d0 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t pipebuf_size; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D0USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb1_host_data_count[pipe]; + } + else if (g_usb1_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + else + { + pipebuf_size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + } + } + + if (count == 0) /* 0 length packet */ + { + USB201.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb1_host_read_d0_fifo(pipe, (uint16_t)count); + } + + g_usb1_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_buffer_d1 +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by CPU transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_read_buffer_d1 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t pipebuf_size; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D1USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb1_host_data_count[pipe]; + } + else if (g_usb1_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) !=0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + else + { + pipebuf_size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + } + } + + if (count == 0) /* 0 length packet */ + { + USB201.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb1_host_read_d1_fifo(pipe, (uint16_t)count); + } + + g_usb1_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_dma +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by DMA transfer using D0FIFO or D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_read_dma (uint16_t pipe) +{ + uint16_t status; + + g_usb1_host_PipeIgnore[pipe] = 0; + + if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_DMA) + { + status = usb1_host_read_dma_d0(pipe); + } + else + { + status = usb1_host_read_dma_d1(pipe); + } + + switch (status) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READZERO: /* End of data read */ + usb1_host_disable_brdy_int(pipe); + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb1_host_disable_brdy_int(pipe); + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + g_usb1_host_PipeDataSize[pipe] -= g_usb1_host_data_count[pipe]; + } + break; + + case USB_HOST_READOVER: /* buffer over */ + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + g_usb1_host_PipeDataSize[pipe] -= g_usb1_host_data_count[pipe]; + } +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#else + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; +#endif + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_dma_d0 +* Description : Writes data in the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by DMA transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +static uint16_t usb1_host_read_dma_d0 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + uint16_t pipebuf_size; + + g_usb1_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_READY; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + count = g_usb1_host_data_count[pipe]; + status = USB_HOST_READING; + } + else + { + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + count = g_usb1_host_data_count[pipe]; + } + else if (g_usb1_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + else + { + pipebuf_size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + } + } + + if (count == 0) /* 0 length packet */ + { + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + USB201.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + status = USB_HOST_READZERO; /* Null Packet receive */ + } + else + { + usb1_host_set_curpipe(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + /* transaction counter No set */ + /* FRDY = 1, DTLN = 0 -> BRDY */ + } + } + else + { + dfacc = usb1_host_set_dfacc_d0(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 0; /* 8bit transfer */ + } + + g_usb1_host_DmaPipe[USB_HOST_D0FIFO] = pipe; /* not use in read operation */ + g_usb1_host_DmaBval[USB_HOST_D0FIFO] = 0; /* not use in read operation */ + + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].fifo = USB_HOST_D0FIFO_DMA; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].dir = USB_HOST_FIFO2BUF; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].buffer = (uint32_t)g_usb1_host_data_pointer[pipe]; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].bytes = count; + + if (status == USB_HOST_READING) + { + g_usb1_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_BUSY; + } + else + { + g_usb1_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_BUSYEND; + } + + Userdef_USB_usb1_host_start_dma(&g_usb1_host_DmaInfo[USB_HOST_D0FIFO], dfacc); + + usb1_host_set_curpipe2(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw , dfacc); + + RZA_IO_RegWrite_16(&USB201.D0FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + g_usb1_host_data_count[pipe] -= count; + g_usb1_host_data_pointer[pipe] += count; + g_usb1_host_PipeDataSize[pipe] += count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_dma_d1 +* Description : Reads data from the buffer allocated in the pipe specified in +* : the argument. +* : Reads data by DMA transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +static uint16_t usb1_host_read_dma_d1 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + uint16_t pipebuf_size; + + g_usb1_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_READY; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + count = g_usb1_host_data_count[pipe]; + status = USB_HOST_READING; + } + else + { + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + count = g_usb1_host_data_count[pipe]; + } + else if (g_usb1_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + else + { + pipebuf_size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + } + } + + if (count == 0) /* 0 length packet */ + { + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + USB201.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + status = USB_HOST_READZERO; /* Null Packet receive */ + } + else + { + usb1_host_set_curpipe(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + /* transaction counter No set */ + /* FRDY = 1, DTLN = 0 -> BRDY */ + } + } + else + { + dfacc = usb1_host_set_dfacc_d1(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 0; /* 8bit transfer */ + } + + g_usb1_host_DmaPipe[USB_HOST_D1FIFO] = pipe; /* not use in read operation */ + g_usb1_host_DmaBval[USB_HOST_D1FIFO] = 0; /* not use in read operation */ + + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].fifo = USB_HOST_D1FIFO_DMA; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].dir = USB_HOST_FIFO2BUF; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].buffer = (uint32_t)g_usb1_host_data_pointer[pipe]; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].bytes = count; + + if (status == USB_HOST_READING) + { + g_usb1_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_BUSY; + } + else + { + g_usb1_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_BUSYEND; + } + + Userdef_USB_usb1_host_start_dma(&g_usb1_host_DmaInfo[USB_HOST_D1FIFO], dfacc); + + usb1_host_set_curpipe2(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw , dfacc); + + RZA_IO_RegWrite_16(&USB201.D1FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + g_usb1_host_data_count[pipe] -= count; + g_usb1_host_data_pointer[pipe] += count; + g_usb1_host_PipeDataSize[pipe] += count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_change_fifo_port +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument. After allocating FIF0, waits in the software +* : till the corresponding pipe becomes ready. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* Return Value : USB_HOST_FIFOERROR ; Error +* : Others ; CFIFOCTR/D0FIFOCTR/D1FIFOCTR Register Value +*******************************************************************************/ +uint16_t usb1_host_change_fifo_port (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw) +{ + uint16_t buffer; + uint32_t loop; + volatile uint32_t loop2; + + usb1_host_set_curpipe(pipe, fifosel, isel, mbw); + + for (loop = 0; loop < 4; loop++) + { + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB201.CFIFOCTR; + break; + + case USB_HOST_D0USE: + case USB_HOST_D0DMA: + buffer = USB201.D0FIFOCTR; + break; + + case USB_HOST_D1USE: + case USB_HOST_D1DMA: + buffer = USB201.D1FIFOCTR; + break; + + default: + buffer = 0; + break; + } + + if ((buffer & USB_HOST_BITFRDY) == USB_HOST_BITFRDY) + { + return buffer; + } + + loop2 = 25; + + while (loop2-- > 0) + { + /* wait */ + } + } + + return USB_HOST_FIFOERROR; +} + +/******************************************************************************* +* Function Name: usb1_host_set_curpipe +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* Return Value : none +*******************************************************************************/ +void usb1_host_set_curpipe (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw) +{ + uint16_t buffer; + uint32_t loop; + volatile uint32_t loop2; + + g_usb1_host_mbw[pipe] = mbw; + + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB201.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(~isel & USB_HOST_BITISEL); + USB201.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(isel | pipe | mbw); + USB201.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D0DMA: + case USB_HOST_D0USE: + buffer = USB201.D0FIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + USB201.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB201.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D1DMA: + case USB_HOST_D1USE: + buffer = USB201.D1FIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + USB201.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB201.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + default: + break; + } + + /* Cautions !!! + * Depending on the external bus speed of CPU, you may need to wait for 450ns here. + * For details, please look at the data sheet. */ + loop2 = 100; + + while (loop2-- > 0) + { + /* wait */ + } +} + +/******************************************************************************* +* Function Name: usb1_host_set_curpipe2 +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument.(DFACC) +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* : uint16_t dfacc ; DFACC Access mode +* Return Value : none +*******************************************************************************/ +void usb1_host_set_curpipe2 (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw, uint16_t dfacc) +{ + uint16_t buffer; + uint32_t loop; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + uint32_t dummy; +#endif + volatile uint32_t loop2; + + g_usb1_host_mbw[pipe] = mbw; + + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB201.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(~isel & USB_HOST_BITISEL); + USB201.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(isel | pipe | mbw); + USB201.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D0DMA: + case USB_HOST_D0USE: + buffer = USB201.D0FIFOSEL; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + + if (dfacc != 0) + { + buffer |= (uint16_t)(USB_HOST_BITMBW_32); + } +#else + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); +#endif + USB201.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + +#ifdef __USB_HOST_DF_ACC_ENABLE__ + if (dfacc != 0) + { + dummy = USB201.D0FIFO.UINT32; + } +#endif + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB201.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D1DMA: + case USB_HOST_D1USE: + buffer = USB201.D1FIFOSEL; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + + if (dfacc != 0) + { + buffer |= (uint16_t)(USB_HOST_BITMBW_32); + } +#else + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); +#endif + USB201.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + +#ifdef __USB_HOST_DF_ACC_ENABLE__ + if (dfacc != 0) + { + dummy = USB201.D1FIFO.UINT32; + loop = dummy; // avoid warning. + } +#endif + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB201.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + default: + break; + } + + /* Cautions !!! + * Depending on the external bus speed of CPU, you may need to wait for 450ns here. + * For details, please look at the data sheet. */ + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } +} + +/******************************************************************************* +* Function Name: usb1_host_write_c_fifo +* Description : Writes data in CFIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_write_c_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB201.CFIFO.UINT8[HH] = *g_usb1_host_data_pointer[pipe]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB201.CFIFO.UINT16[H] = *((uint16_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB201.CFIFO.UINT32 = *((uint32_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_read_c_fifo +* Description : Reads data from CFIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_read_c_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb1_host_data_pointer[pipe] = USB201.CFIFO.UINT8[HH]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb1_host_data_pointer[pipe]) = USB201.CFIFO.UINT16[H]; + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb1_host_data_pointer[pipe]) = USB201.CFIFO.UINT32; + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_write_d0_fifo +* Description : Writes data in D0FIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_write_d0_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB201.D0FIFO.UINT8[HH] = *g_usb1_host_data_pointer[pipe]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB201.D0FIFO.UINT16[H] = *((uint16_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB201.D0FIFO.UINT32 = *((uint32_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_read_d0_fifo +* Description : Reads data from D0FIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating DOFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t Pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_read_d0_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb1_host_data_pointer[pipe] = USB201.D0FIFO.UINT8[HH]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb1_host_data_pointer[pipe]) = USB201.D0FIFO.UINT16[H]; + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb1_host_data_pointer[pipe]) = USB201.D0FIFO.UINT32; + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_write_d1_fifo +* Description : Writes data in D1FIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating D1FIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_write_d1_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB201.D1FIFO.UINT8[HH] = *g_usb1_host_data_pointer[pipe]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB201.D1FIFO.UINT16[H] = *((uint16_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB201.D1FIFO.UINT32 = *((uint32_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_read_d1_fifo +* Description : Reads data from D1FIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating D1FIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_read_d1_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb1_host_data_pointer[pipe] = USB201.D1FIFO.UINT8[HH]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb1_host_data_pointer[pipe]) = USB201.D1FIFO.UINT16[H]; + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb1_host_data_pointer[pipe]) = USB201.D1FIFO.UINT32; + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_com_get_dmasize +* Description : Calculates access width of DMA transfer by the argument to + return as the Return Value. +* Arguments : uint32_t trncount : transfer byte +* : uint32_t dtptr : transfer data pointer +* Return Value : DMA transfer size : 0 8bit +* : : 1 16bit +* : : 2 32bit +*******************************************************************************/ +static uint32_t usb1_host_com_get_dmasize (uint32_t trncount, uint32_t dtptr) +{ + uint32_t size; + + if (((trncount & 0x0001) != 0) || ((dtptr & 0x00000001) != 0)) + { + /* When transfer byte count is odd */ + /* or transfer data area is 8-bit alignment */ + size = 0; /* 8bit */ + } + else if (((trncount & 0x0003) != 0) || ((dtptr & 0x00000003) != 0)) + { + /* When the transfer byte count is multiples of 2 */ + /* or the transfer data area is 16-bit alignment */ + size = 1; /* 16bit */ + } + else + { + /* When the transfer byte count is multiples of 4 */ + /* or the transfer data area is 32-bit alignment */ + size = 2; /* 32bit */ + } + + return size; +} + +/******************************************************************************* +* Function Name: usb1_host_get_mbw +* Description : Calculates access width of DMA to return the value set in MBW. +* Arguments : uint32_t trncount : transfer byte +* : uint32_t dtptr : transfer data pointer +* Return Value : FIFO transfer size : USB_HOST_BITMBW_8 8bit +* : : USB_HOST_BITMBW_16 16bit +* : : USB_HOST_BITMBW_32 32bit +*******************************************************************************/ +uint16_t usb1_host_get_mbw (uint32_t trncount, uint32_t dtptr) +{ + uint32_t size; + uint16_t mbw; + + size = usb1_host_com_get_dmasize(trncount, dtptr); + + if (size == 0) + { + /* 8bit */ + mbw = USB_HOST_BITMBW_8; + } + else if (size == 1) + { + /* 16bit */ + mbw = USB_HOST_BITMBW_16; + } + else + { + /* 32bit */ + mbw = USB_HOST_BITMBW_32; + } + + return mbw; +} + +/******************************************************************************* +* Function Name: usb1_host_set_transaction_counter +* Description : Sets transaction counter by the argument(PIPEnTRN). +* : Clears transaction before setting to enable transaction counter setting. +* Arguments : uint16_t pipe ; Pipe number +* : uint32_t bsize : Data transfer size +* Return Value : none +*******************************************************************************/ +static void usb1_host_set_transaction_counter (uint16_t pipe, uint32_t bsize) +{ + uint16_t mxps; + uint16_t cnt; + + if (bsize == 0) + { + return; + } + + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if ((bsize % mxps) == 0) + { + cnt = (uint16_t)(bsize / mxps); + } + else + { + cnt = (uint16_t)((bsize / mxps) + 1); + } + + switch (pipe) + { + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE1TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE1TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE2TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE2TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE3TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE3TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE4TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE4TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE5TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE5TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE9TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE9TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_clear_transaction_counter +* Description : Clears the transaction counter by the argument. +* : After executing this function, the transaction counter is invalid. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb1_host_clear_transaction_counter (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE1TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE2TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE3TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE4TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE5TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE9TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_stop_transfer +* Description : Stops the USB transfer in the pipe specified by the argument. +* : After stopping the USB transfer, clears the buffer allocated in +* : the pipe. +* : After executing this function, allocation in FIF0 becomes USB_HOST_PIPE0; +* : invalid. After executing this function, BRDY/NRDY/BEMP interrupt +* : in the corresponding pipe becomes invalid. Sequence bit is also +* : cleared. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_stop_transfer (uint16_t pipe) +{ + uint16_t usefifo; + uint32_t remain; + + usb1_host_set_pid_nak(pipe); + + usefifo = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + usb1_host_clear_transaction_counter(pipe); + USB201.D0FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D1FIFO_USE: + usb1_host_clear_transaction_counter(pipe); + USB201.D1FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D0FIFO_DMA: + remain = Userdef_USB_usb1_host_stop_dma0(); + usb1_host_dma_stop_d0(pipe, remain); + usb1_host_clear_transaction_counter(pipe); + USB201.D0FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D1FIFO_DMA: + remain = Userdef_USB_usb1_host_stop_dma1(); + usb1_host_dma_stop_d1(pipe, remain); + usb1_host_clear_transaction_counter(pipe); + USB201.D1FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + default: + usb1_host_clear_transaction_counter(pipe); + USB201.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + } + + /* Interrupt of pipe set is disabled */ + usb1_host_disable_brdy_int(pipe); + usb1_host_disable_nrdy_int(pipe); + usb1_host_disable_bemp_int(pipe); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + usb1_host_set_csclr(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_set_dfacc_d0 +* Description : Sets the DFACC setting value in D0FIFO using the transfer size. +* Arguments : uint16_t mbw ; MBW +* : uint16_t count ; data count +* Return Value : DFACC Access mode +*******************************************************************************/ +static uint16_t usb1_host_set_dfacc_d0 (uint16_t mbw, uint32_t count) +{ + uint16_t dfacc = 0; + +#ifndef __USB_HOST_DF_ACC_ENABLE__ + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; +#else + if (mbw == USB_HOST_BITMBW_32) + { + if ((count % 32) == 0) + { + /* 32byte transfer */ + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 2, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 2; + } + else if ((count % 16) == 0) + { + /* 16byte transfer */ + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 1, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 1; + } + else + { + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + } + else if (mbw == USB_HOST_BITMBW_16) + { + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + else + { + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } +#endif + + return dfacc; +} + +/******************************************************************************* +* Function Name: usb1_host_set_dfacc_d1 +* Description : Sets the DFACC setting value in D0FIFO using the transfer size. +* Arguments : uint16_t mbw ; MBW +* : uint16_t count ; data count +* Return Value : DFACC Access mode +*******************************************************************************/ +static uint16_t usb1_host_set_dfacc_d1 (uint16_t mbw, uint32_t count) +{ + uint16_t dfacc = 0; + +#ifndef __USB_HOST_DF_ACC_ENABLE__ + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; +#else + if (mbw == USB_HOST_BITMBW_32) + { + if ((count % 32) == 0) + { + /* 32byte transfer */ + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 2, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 2; + } + else if ((count % 16) == 0) + { + /* 16byte transfer */ + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 1, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 1; + } + else + { + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + } + else if (mbw == USB_HOST_BITMBW_16) + { + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + else + { + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } +#endif + + return dfacc; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/src/common/usb1_host_dma.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,355 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_dma.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +/* #include "usb1_host_dmacdrv.h" */ + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +static void usb1_host_dmaint(uint16_t fifo); +static void usb1_host_dmaint_buf2fifo(uint16_t pipe); +static void usb1_host_dmaint_fifo2buf(uint16_t pipe); + + +/******************************************************************************* +* Function Name: usb1_host_dma_stop_d0 +* Description : D0FIFO DMA stop +* Arguments : uint16_t pipe : pipe number +* : uint32_t remain : transfer byte +* Return Value : none +*******************************************************************************/ +void usb1_host_dma_stop_d0 (uint16_t pipe, uint32_t remain) +{ + uint16_t dtln; + uint16_t dfacc; + uint16_t buffer; + uint16_t sds_b = 1; + + dfacc = RZA_IO_RegRead_16(&USB201.D0FBCFG, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + if (dfacc == 2) + { + sds_b = 32; + } + else if (dfacc == 1) + { + sds_b = 16; + } + else + { + if (g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size == 2) + { + sds_b = 4; + } + else if (g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size == 1) + { + sds_b = 2; + } + else + { + sds_b = 1; + } + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + if (g_usb1_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + buffer = USB201.D0FIFOCTR; + dtln = (buffer & USB_HOST_BITDTLN); + + if ((dtln % sds_b) != 0) + { + remain += (sds_b - (dtln % sds_b)); + } + g_usb1_host_PipeDataSize[pipe] = (g_usb1_host_data_count[pipe] - remain); + g_usb1_host_data_count[pipe] = remain; + } + } + + RZA_IO_RegWrite_16(&USB201.D0FIFOSEL, + 0, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); +} + +/******************************************************************************* +* Function Name: usb1_host_dma_stop_d1 +* Description : D1FIFO DMA stop +* Arguments : uint16_t pipe : pipe number +* : uint32_t remain : transfer byte +* Return Value : none +*******************************************************************************/ +void usb1_host_dma_stop_d1 (uint16_t pipe, uint32_t remain) +{ + uint16_t dtln; + uint16_t dfacc; + uint16_t buffer; + uint16_t sds_b = 1; + + dfacc = RZA_IO_RegRead_16(&USB201.D1FBCFG, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + if (dfacc == 2) + { + sds_b = 32; + } + else if (dfacc == 1) + { + sds_b = 16; + } + else + { + if (g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size == 2) + { + sds_b = 4; + } + else if (g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size == 1) + { + sds_b = 2; + } + else + { + sds_b = 1; + } + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + if (g_usb1_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + buffer = USB201.D1FIFOCTR; + dtln = (buffer & USB_HOST_BITDTLN); + + if ((dtln % sds_b) != 0) + { + remain += (sds_b - (dtln % sds_b)); + } + g_usb1_host_PipeDataSize[pipe] = (g_usb1_host_data_count[pipe] - remain); + g_usb1_host_data_count[pipe] = remain; + } + } + + RZA_IO_RegWrite_16(&USB201.D1FIFOSEL, + 0, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); +} + +/******************************************************************************* +* Function Name: usb1_host_dma_interrupt_d0fifo +* Description : This function is DMA interrupt handler entry. +* : Execute usb1_host_dmaint() after disabling DMA interrupt in this function. +* : Disable DMA interrupt to DMAC executed when USB_HOST_D0FIFO_DMA is +* : specified by dma->fifo. +* : Register this function as DMA complete interrupt. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb1_host_dma_interrupt_d0fifo (uint32_t int_sense) +{ + usb1_host_dmaint(USB_HOST_D0FIFO); + g_usb1_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_READY; +} + +/******************************************************************************* +* Function Name: usb1_host_dma_interrupt_d1fifo +* Description : This function is DMA interrupt handler entry. +* : Execute usb0_host_dmaint() after disabling DMA interrupt in this function. +* : Disable DMA interrupt to DMAC executed when USB_HOST_D1FIFO_DMA is +* : specified by dma->fifo. +* : Register this function as DMA complete interrupt. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb1_host_dma_interrupt_d1fifo (uint32_t int_sense) +{ + usb1_host_dmaint(USB_HOST_D1FIFO); + g_usb1_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_READY; +} + +/******************************************************************************* +* Function Name: usb1_host_dmaint +* Description : This function is DMA transfer end interrupt +* Arguments : uint16_t fifo ; fifo number +* : ; USB_HOST_D0FIFO +* : ; USB_HOST_D1FIFO +* Return Value : none +*******************************************************************************/ +static void usb1_host_dmaint (uint16_t fifo) +{ + uint16_t pipe; + + pipe = g_usb1_host_DmaPipe[fifo]; + + if (g_usb1_host_DmaInfo[fifo].dir == USB_HOST_BUF2FIFO) + { + usb1_host_dmaint_buf2fifo(pipe); + } + else + { + usb1_host_dmaint_fifo2buf(pipe); + } +} + +/******************************************************************************* +* Function Name: usb1_host_dmaint_fifo2buf +* Description : Executes read completion from FIFO by DMAC. +* Arguments : uint16_t pipe : pipe number +* Return Value : none +*******************************************************************************/ +static void usb1_host_dmaint_fifo2buf (uint16_t pipe) +{ + uint32_t remain; + uint16_t useport; + + if (g_usb1_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + useport = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + if (useport == USB_HOST_D0FIFO_DMA) + { + remain = Userdef_USB_usb1_host_stop_dma0(); + usb1_host_dma_stop_d0(pipe, remain); + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + if (g_usb1_host_DmaStatus[USB_HOST_D0FIFO] == USB_HOST_DMA_BUSYEND) + { + USB201.D0FIFOCTR = USB_HOST_BITBCLR; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + else + { + usb1_host_enable_brdy_int(pipe); + } + } + } + else + { + remain = Userdef_USB_usb1_host_stop_dma1(); + usb1_host_dma_stop_d1(pipe, remain); + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + if (g_usb1_host_DmaStatus[USB_HOST_D1FIFO] == USB_HOST_DMA_BUSYEND) + { + USB201.D1FIFOCTR = USB_HOST_BITBCLR; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + else + { + usb1_host_enable_brdy_int(pipe); + } + } + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_dmaint_buf2fifo +* Description : Executes write completion in FIFO by DMAC. +* Arguments : uint16_t pipe : pipe number +* Return Value : none +*******************************************************************************/ +static void usb1_host_dmaint_buf2fifo (uint16_t pipe) +{ + uint16_t useport; + uint32_t remain; + + useport = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + if (useport == USB_HOST_D0FIFO_DMA) + { + remain = Userdef_USB_usb1_host_stop_dma0(); + usb1_host_dma_stop_d0(pipe, remain); + + if (g_usb1_host_DmaBval[USB_HOST_D0FIFO] != 0) + { + RZA_IO_RegWrite_16(&USB201.D0FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); + } + } + else + { + remain = Userdef_USB_usb1_host_stop_dma1(); + usb1_host_dma_stop_d1(pipe, remain); + + if (g_usb1_host_DmaBval[USB_HOST_D1FIFO] != 0) + { + RZA_IO_RegWrite_16(&USB201.D1FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); + } + } + + usb1_host_enable_bemp_int(pipe); +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/src/common/usb1_host_intrn.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,285 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_intrn.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#if(1) /* ohci_wrapp */ +#include "ohci_wrapp_RZ_A1_local.h" +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_brdy_int +* Description : Executes BRDY interrupt(USB_HOST_PIPE1-9). +* : According to the pipe that interrupt is generated in, +* : reads/writes buffer allocated in the pipe. +* : This function is executed in the BRDY interrupt handler. +* : This function clears BRDY interrupt status and BEMP interrupt +* : status. +* Arguments : uint16_t status ; BRDYSTS Register Value +* : uint16_t int_enb ; BRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_brdy_int (uint16_t status, uint16_t int_enb) +{ + uint32_t int_sense = 0; + uint16_t pipe; + uint16_t pipebit; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + pipebit = g_usb1_host_bit_set[pipe]; + + if ((status & pipebit) && (int_enb & pipebit)) + { + USB201.BRDYSTS = (uint16_t)~pipebit; + USB201.BEMPSTS = (uint16_t)~pipebit; + + if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_DMA) + { + if (g_usb1_host_DmaStatus[USB_HOST_D0FIFO] != USB_HOST_DMA_READY) + { + usb1_host_dma_interrupt_d0fifo(int_sense); + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + usb1_host_read_dma(pipe); + usb1_host_disable_brdy_int(pipe); + } + else + { + USB201.D0FIFOCTR = USB_HOST_BITBCLR; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + } + else if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_DMA) + { + if (g_usb1_host_DmaStatus[USB_HOST_D1FIFO] != USB_HOST_DMA_READY) + { + usb1_host_dma_interrupt_d1fifo(int_sense); + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + usb1_host_read_dma(pipe); + usb1_host_disable_brdy_int(pipe); + } + else + { + USB201.D1FIFOCTR = USB_HOST_BITBCLR; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + } + else + { + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 0) + { + usb1_host_read_buffer(pipe); + } + else + { + usb1_host_write_buffer(pipe); + } + } +#if(1) /* ohci_wrapp */ + switch (g_usb1_host_pipe_status[pipe]) + { + case USB_HOST_PIPE_DONE: + ohciwrapp_loc_TransEnd(pipe, TD_CC_NOERROR); + break; + case USB_HOST_PIPE_NORES: + case USB_HOST_PIPE_STALL: + case USB_HOST_PIPE_ERROR: + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); + break; + default: + /* Do Nothing */ + break; + } +#endif + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_nrdy_int +* Description : Executes NRDY interrupt(USB_HOST_PIPE1-9). +* : Checks NRDY interrupt cause by PID. When the cause if STALL, +* : regards the pipe state as STALL and ends the processing. +* : Then the cause is not STALL, increments the error count to +* : communicate again. When the error count is 3, determines +* : the pipe state as USB_HOST_PIPE_NORES and ends the processing. +* : This function is executed in the NRDY interrupt handler. +* : This function clears NRDY interrupt status. +* Arguments : uint16_t status ; NRDYSTS Register Value +* : uint16_t int_enb ; NRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_nrdy_int (uint16_t status, uint16_t int_enb) +{ + uint16_t pid; + uint16_t pipe; + uint16_t bitcheck; + + bitcheck = (uint16_t)(status & int_enb); + + USB201.NRDYSTS = (uint16_t)~status; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + if ((bitcheck&g_usb1_host_bit_set[pipe]) == g_usb1_host_bit_set[pipe]) + { + if (RZA_IO_RegRead_16(&USB201.SYSCFG0, + USB_SYSCFG_DCFM_SHIFT, + USB_SYSCFG_DCFM) == 1) + { + if (g_usb1_host_pipe_status[pipe] == USB_HOST_PIPE_WAIT) + { + pid = usb1_host_get_pid(pipe); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_STALL; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); +#endif + } + else + { +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_NORES; + ohciwrapp_loc_TransEnd(pipe, TD_CC_DEVICENOTRESPONDING); +#else + g_usb1_host_PipeIgnore[pipe]++; + + if (g_usb1_host_PipeIgnore[pipe] == 3) + { + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_NORES; + } + else + { + usb1_host_set_pid_buf(pipe); + } +#endif + } + } + } + else + { + /* USB Function */ + } + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_bemp_int +* Description : Executes BEMP interrupt(USB_HOST_PIPE1-9). +* Arguments : uint16_t status ; BEMPSTS Register Value +* : uint16_t int_enb ; BEMPENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_bemp_int (uint16_t status, uint16_t int_enb) +{ + uint16_t pid; + uint16_t pipe; + uint16_t bitcheck; + uint16_t inbuf; + + bitcheck = (uint16_t)(status & int_enb); + + USB201.BEMPSTS = (uint16_t)~status; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + if ((bitcheck&g_usb1_host_bit_set[pipe]) == g_usb1_host_bit_set[pipe]) + { + pid = usb1_host_get_pid(pipe); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_STALL; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); +#endif + } + else + { + inbuf = usb1_host_get_inbuf(pipe); + + if (inbuf == 0) + { + usb1_host_disable_bemp_int(pipe); + usb1_host_set_pid_nak(pipe); + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_NOERROR); +#endif + } + } + } + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/src/common/usb1_host_lib.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,1598 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_lib.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#if(1) /* ohci_wrapp */ +#include "MBRZA1H.h" /* INTC Driver Header */ +#else +#include "devdrv_intc.h" /* INTC Driver Header */ +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_enable_brdy_int +* Description : Enables BRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : BRDY. Enables BRDY interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_enable_brdy_int (uint16_t pipe) +{ + /* enable brdy interrupt */ + USB201.BRDYENB |= (uint16_t)g_usb1_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb1_host_disable_brdy_int +* Description : Disables BRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : BRDY. Enables BRDY interrupt in the pipe specified by the argument +* : in the disabled status. After disabling BRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_disable_brdy_int (uint16_t pipe) +{ + /* disable brdy interrupt */ + USB201.BRDYENB &= (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_clear_brdy_sts +* Description : Clear BRDY interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_clear_brdy_sts (uint16_t pipe) +{ + /* clear brdy status */ + USB201.BRDYSTS = (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_enable_bemp_int +* Description : Enables BEMP interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : BEMP. Enables BEMP interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BEMP, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_enable_bemp_int (uint16_t pipe) +{ + /* enable bemp interrupt */ + USB201.BEMPENB |= (uint16_t)g_usb1_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb1_host_disable_bemp_int +* Description : Disables BEMP interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : BEMP. Enables BEMP interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BEMP, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_disable_bemp_int (uint16_t pipe) +{ + /* disable bemp interrupt */ + USB201.BEMPENB &= (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_clear_bemp_sts +* Description : Clear BEMP interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_clear_bemp_sts (uint16_t pipe) +{ + /* clear bemp status */ + USB201.BEMPSTS = (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_enable_nrdy_int +* Description : Enables NRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : NRDY. Enables NRDY interrupt in the pipe specified by the argument +* : in the disabled status. After enabling NRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_enable_nrdy_int (uint16_t pipe) +{ + /* enable nrdy interrupt */ + USB201.NRDYENB |= (uint16_t)g_usb1_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb1_host_disable_nrdy_int +* Description : Disables NRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : NRDY. Disables NRDY interrupt in the pipe specified by the argument +* : in the disabled status. After disabling NRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_disable_nrdy_int (uint16_t pipe) +{ + /* disable nrdy interrupt */ + USB201.NRDYENB &= (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_clear_nrdy_sts +* Description : Clear NRDY interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_clear_nrdy_sts (uint16_t pipe) +{ + /* clear nrdy status */ + USB201.NRDYSTS = (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_is_hispeed +* Description : Returns the result of USB reset hand shake (RHST) as +* : return value. +* Arguments : none +* Return Value : USB_HOST_HIGH_SPEED ; Hi-Speed +* : USB_HOST_FULL_SPEED ; Full-Speed +* : USB_HOST_LOW_SPEED ; Low-Speed +* : USB_HOST_NON_SPEED ; error +*******************************************************************************/ +uint16_t usb1_host_is_hispeed (void) +{ + uint16_t rhst; + uint16_t speed; + + rhst = RZA_IO_RegRead_16(&USB201.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (rhst == USB_HOST_HSMODE) + { + speed = USB_HOST_HIGH_SPEED; + } + else if (rhst == USB_HOST_FSMODE) + { + speed = USB_HOST_FULL_SPEED; + } + else if (rhst == USB_HOST_LSMODE) + { + speed = USB_HOST_LOW_SPEED; + } + else + { + speed = USB_HOST_NON_SPEED; + } + + return speed; +} + +/******************************************************************************* +* Function Name: usb1_host_is_hispeed_enable +* Description : Returns the USB High-Speed connection enabled status as +* : return value. +* Arguments : none +* Return Value : USB_HOST_YES : Hi-Speed Enable +* : USB_HOST_NO : Hi-Speed Disable +*******************************************************************************/ +uint16_t usb1_host_is_hispeed_enable (void) +{ + uint16_t ret; + + ret = USB_HOST_NO; + + if (RZA_IO_RegRead_16(&USB201.SYSCFG0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE) == 1) + { + ret = USB_HOST_YES; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_host_set_pid_buf +* Description : Enables communicaqtion in the pipe specified by the argument +* : (BUF). +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_pid_buf (uint16_t pipe) +{ + uint16_t pid; + + pid = usb1_host_get_pid(pipe); + + if (pid == USB_HOST_PID_STALL2) + { + usb1_host_set_pid_nak(pipe); + } + + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + USB_HOST_PID_BUF, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_set_pid_nak +* Description : Disables communication (NAK) in the pipe specified by the argument. +* : When the pipe status was enabling communication (BUF) before +* : executing before executing this function, waits in the software +* : until the pipe becomes ready after setting disabled. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_pid_nak (uint16_t pipe) +{ + uint16_t pid; + uint16_t pbusy; + uint32_t loop; + + pid = usb1_host_get_pid(pipe); + + if (pid == USB_HOST_PID_STALL2) + { + usb1_host_set_pid_stall(pipe); + } + + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + USB_HOST_PID_NAK, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + + if (pid == USB_HOST_PID_BUF) + { + for (loop = 0; loop < 200; loop++) + { + switch (pipe) + { + case USB_HOST_PIPE0: + pbusy = RZA_IO_RegRead_16(&USB201.DCPCTR, + USB_DCPCTR_PBUSY_SHIFT, + USB_DCPCTR_PBUSY); + break; + + case USB_HOST_PIPE1: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE1CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE2: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE2CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE3: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE3CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE4: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE4CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE5: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE5CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE6: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE6CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE7: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE7CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE8: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE8CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE9: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE9CTR, + USB_PIPEnCTR_9_PBUSY_SHIFT, + USB_PIPEnCTR_9_PBUSY); + break; + + default: + pbusy = 1; + break; + } + + if (pbusy == 0) + { + break; + } + + Userdef_USB_usb1_host_delay_500ns(); + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_set_pid_stall +* Description : Disables communication (STALL) in the pipe specified by the +* : argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_pid_stall (uint16_t pipe) +{ + uint16_t pid; + + pid = usb1_host_get_pid(pipe); + + if (pid == USB_HOST_PID_BUF) + { + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + USB_HOST_PID_STALL2, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + } + else + { + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + USB_HOST_PID_STALL, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_clear_pid_stall +* Description : Disables communication (NAK) in the pipe specified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_clear_pid_stall (uint16_t pipe) +{ + usb1_host_set_pid_nak(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_get_pid +* Description : Returns the pipe state specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : PID +*******************************************************************************/ +uint16_t usb1_host_get_pid (uint16_t pipe) +{ + uint16_t pid; + + switch (pipe) + { + case USB_HOST_PIPE0: + pid = RZA_IO_RegRead_16(&USB201.DCPCTR, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + pid = RZA_IO_RegRead_16(&USB201.PIPE1CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + pid = RZA_IO_RegRead_16(&USB201.PIPE2CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + pid = RZA_IO_RegRead_16(&USB201.PIPE3CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + pid = RZA_IO_RegRead_16(&USB201.PIPE4CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + pid = RZA_IO_RegRead_16(&USB201.PIPE5CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + pid = RZA_IO_RegRead_16(&USB201.PIPE6CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + pid = RZA_IO_RegRead_16(&USB201.PIPE7CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + pid = RZA_IO_RegRead_16(&USB201.PIPE8CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + pid = RZA_IO_RegRead_16(&USB201.PIPE9CTR, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + pid = 0; + break; + } + + return pid; +} + +/******************************************************************************* +* Function Name: usb1_host_set_csclr +* Description : CSPLIT status clear setting of sprit transaction in specified +* : pipe is performed. +* : When SQSET bit or SQCLR bit, and SQSET bit or SQCLR bit +* : in DCPCTR register are continuously changed (when the sequence +* : toggle bit of data PID is continuously changed over two or more pipes), +* : the access cycle with 120 ns and more than 5 cycle bus clock is necessary. +* : Do not set both SQCLR bit and SQSET bit to 1 at the same time. +* : In addition, both bits should be operated after PID is set to NAK. +* : However, when it is set to the isochronous transfer as the transfer type +* : (TYPE=11), writing in SQSET bit is disabled. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_csclr (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + 1, + USB_DCPCTR_CSCLR_SHIFT, + USB_DCPCTR_CSCLR); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + 1, + USB_PIPEnCTR_9_CSCLR_SHIFT, + USB_PIPEnCTR_9_CSCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_set_sqclr +* Description : Sets the sequence bit of the pipe specified by the argument to +* : DATA0. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_sqclr (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + 1, + USB_DCPCTR_SQCLR_SHIFT, + USB_DCPCTR_SQCLR); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + 1, + USB_PIPEnCTR_9_SQCLR_SHIFT, + USB_PIPEnCTR_9_SQCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_set_sqset +* Description : Sets the sequence bit of the pipe specified by the argument to +* : DATA1. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_sqset (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + 1, + USB_DCPCTR_SQSET_SHIFT, + USB_DCPCTR_SQSET); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + 1, + USB_PIPEnCTR_9_SQSET_SHIFT, + USB_PIPEnCTR_9_SQSET); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_get_sqmon +* Description : Toggle bit of specified pipe is obtained +* Arguments : uint16_t pipe ; Pipe number +* Return Value : sqmon +*******************************************************************************/ +uint16_t usb1_host_get_sqmon (uint16_t pipe) +{ + uint16_t sqmon; + + switch (pipe) + { + case USB_HOST_PIPE0: + sqmon = RZA_IO_RegRead_16(&USB201.DCPCTR, + USB_DCPCTR_SQMON_SHIFT, + USB_DCPCTR_SQMON); + break; + + case USB_HOST_PIPE1: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE1CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE2: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE2CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE3: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE3CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE4: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE4CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE5: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE5CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE6: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE6CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE7: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE7CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE8: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE8CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE9: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE9CTR, + USB_PIPEnCTR_9_SQMON_SHIFT, + USB_PIPEnCTR_9_SQMON); + break; + + default: + sqmon = 0; + break; + } + + return sqmon; +} + +/******************************************************************************* +* Function Name: usb1_host_aclrm +* Description : The buffer of specified pipe is initialized +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb1_host_aclrm (uint16_t pipe) +{ + usb1_host_set_aclrm(pipe); + usb1_host_clr_aclrm(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_set_aclrm +* Description : The auto buffer clear mode of specified pipe is enabled +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb1_host_set_aclrm (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + 1, + USB_PIPEnCTR_9_ACLRM_SHIFT, + USB_PIPEnCTR_9_ACLRM); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_clr_aclrm +* Description : The auto buffer clear mode of specified pipe is enabled +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb1_host_clr_aclrm (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + 0, + USB_PIPEnCTR_9_ACLRM_SHIFT, + USB_PIPEnCTR_9_ACLRM); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_get_inbuf +* Description : Returns INBUFM of the pipe specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : inbuf +*******************************************************************************/ +uint16_t usb1_host_get_inbuf (uint16_t pipe) +{ + uint16_t inbuf; + + switch (pipe) + { + case USB_HOST_PIPE0: + inbuf = 0; + break; + + case USB_HOST_PIPE1: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE1CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE2: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE2CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE3: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE3CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE4: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE4CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE5: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE5CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE6: + inbuf = 0; + break; + + case USB_HOST_PIPE7: + inbuf = 0; + break; + + case USB_HOST_PIPE8: + inbuf = 0; + break; + + case USB_HOST_PIPE9: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE9CTR, + USB_PIPEnCTR_9_INBUFM_SHIFT, + USB_PIPEnCTR_9_INBUFM); + break; + + default: + inbuf = 0; + break; + } + + return inbuf; +} + +/******************************************************************************* +* Function Name: usb1_host_setting_interrupt +* Description : Sets the USB module interrupt level. +* Arguments : uint8_t level ; interrupt level +* Return Value : none +*******************************************************************************/ +void usb1_host_setting_interrupt (uint8_t level) +{ +#if(1) /* ohci_wrapp */ + IRQn_Type d0fifo_dmaintid; + IRQn_Type d1fifo_dmaintid; + + InterruptHandlerRegister(USBI1_IRQn, usb1_host_interrupt); + GIC_SetPriority(USBI1_IRQn, level); + GIC_EnableIRQ(USBI1_IRQn); + + d0fifo_dmaintid = (IRQn_Type)Userdef_USB_usb1_host_d0fifo_dmaintid(); + + if (d0fifo_dmaintid != 0xFFFF) + { + InterruptHandlerRegister(d0fifo_dmaintid, usb1_host_dma_interrupt_d0fifo); + GIC_SetPriority(d0fifo_dmaintid, level); + GIC_EnableIRQ(d0fifo_dmaintid); + } + + d1fifo_dmaintid = (IRQn_Type)Userdef_USB_usb1_host_d1fifo_dmaintid(); + + if (d1fifo_dmaintid != 0xFFFF) + { + InterruptHandlerRegister(d1fifo_dmaintid, usb1_host_dma_interrupt_d1fifo); + GIC_SetPriority(d1fifo_dmaintid, level); + GIC_EnableIRQ(d1fifo_dmaintid); + } +#else + uint16_t d0fifo_dmaintid; + uint16_t d1fifo_dmaintid; + + R_INTC_RegistIntFunc(INTC_ID_USBI1, usb1_host_interrupt); + R_INTC_SetPriority(INTC_ID_USBI1, level); + R_INTC_Enable(INTC_ID_USBI1); + + d0fifo_dmaintid = Userdef_USB_usb1_host_d0fifo_dmaintid(); + + if (d0fifo_dmaintid != 0xFFFF) + { + R_INTC_RegistIntFunc(d0fifo_dmaintid, usb1_host_dma_interrupt_d0fifo); + R_INTC_SetPriority(d0fifo_dmaintid, level); + R_INTC_Enable(d0fifo_dmaintid); + } + + d1fifo_dmaintid = Userdef_USB_usb1_host_d1fifo_dmaintid(); + + if (d1fifo_dmaintid != 0xFFFF) + { + R_INTC_RegistIntFunc(d1fifo_dmaintid, usb1_host_dma_interrupt_d1fifo); + R_INTC_SetPriority(d1fifo_dmaintid, level); + R_INTC_Enable(d1fifo_dmaintid); + } +#endif +} + +/******************************************************************************* +* Function Name: usb1_host_reset_module +* Description : Initializes the USB module. +* : Enables providing clock to the USB module. +* : Sets USB bus wait register. +* Arguments : uint16_t clockmode ; 48MHz ; USBHCLOCK_X1_48MHZ +* : ; 12MHz ; USBHCLOCK_EXTAL_12MHZ +* Return Value : none +*******************************************************************************/ +void usb1_host_reset_module (uint16_t clockmode) +{ + if (RZA_IO_RegRead_16(&USB200.SYSCFG0, + USB_SYSCFG_UPLLE_SHIFT, + USB_SYSCFG_UPLLE) == 1) + { + if ((USB200.SYSCFG0 & USB_HOST_BITUCKSEL) != clockmode) + { + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + USB201.SYSCFG0 = 0; + USB200.SYSCFG0 = 0; + USB200.SYSCFG0 = (USB_HOST_BITUPLLE | clockmode); + Userdef_USB_usb1_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + else + { + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + Userdef_USB_usb1_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + } + else + { + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + USB201.SYSCFG0 = 0; + USB200.SYSCFG0 = 0; + USB200.SYSCFG0 = (USB_HOST_BITUPLLE | clockmode); + Userdef_USB_usb1_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + + USB201.BUSWAIT = (uint16_t)(USB_HOST_BUSWAIT_05 & USB_HOST_BITBWAIT); +} + +/******************************************************************************* +* Function Name: usb1_host_get_buf_size +* Description : Obtains pipe buffer size specified by the argument and +* : maximum packet size of the USB device in use. +* : When USB_HOST_PIPE0 is specified by the argument, obtains the maximum +* : packet size of the USB device using the corresponding pipe. +* : For the case that USB_HOST_PIPE0 is not assigned by the argument, when the +* : corresponding pipe is in continuous transfer mode, +* : obtains the buffer size allocated in the corresponcing pipe, +* : when incontinuous transfer, obtains maximum packet size. +* Arguments : uint16_t ; pipe Number +* Return Value : Maximum packet size or buffer size +*******************************************************************************/ +uint16_t usb1_host_get_buf_size (uint16_t pipe) +{ + uint16_t size; + uint16_t bufsize; + + if (pipe == USB_HOST_PIPE0) + { + size = RZA_IO_RegRead_16(&USB201.DCPMAXP, + USB_DCPMAXP_MXPS_SHIFT, + USB_DCPMAXP_MXPS); + } + else + { + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_CNTMD_SHIFT, USB_PIPECFG_CNTMD) == 1) + { + bufsize = RZA_IO_RegRead_16(&g_usb1_host_pipebuf[pipe], USB_PIPEBUF_BUFSIZE_SHIFT, USB_PIPEBUF_BUFSIZE); + size = (uint16_t)((bufsize + 1) * USB_HOST_PIPExBUF); + } + else + { + size = RZA_IO_RegRead_16(&g_usb1_host_pipemaxp[pipe], USB_PIPEMAXP_MXPS_SHIFT, USB_PIPEMAXP_MXPS); + } + } + return size; +} + +/******************************************************************************* +* Function Name: usb1_host_get_mxps +* Description : Obtains maximum packet size of the USB device using the pipe +* : specified by the argument. +* Arguments : uint16_t ; Pipe Number +* Return Value : Max Packet Size +*******************************************************************************/ +uint16_t usb1_host_get_mxps (uint16_t pipe) +{ + uint16_t size; + + if (pipe == USB_HOST_PIPE0) + { + size = RZA_IO_RegRead_16(&USB201.DCPMAXP, + USB_DCPMAXP_MXPS_SHIFT, + USB_DCPMAXP_MXPS); + } + else + { + size = RZA_IO_RegRead_16(&g_usb1_host_pipemaxp[pipe], USB_PIPEMAXP_MXPS_SHIFT, USB_PIPEMAXP_MXPS); + } + + return size; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/src/host/usb1_host_controlrw.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,434 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_controlrw.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_CtrlTransStart +* Description : Executes USB control transfer. +* Arguments : uint16_t devadr ; device address +* : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* : uint8_t *Buf ; Data buffer +* Return Value : DEVDRV_SUCCESS ; SUCCESS +* : DEVDRV_ERROR ; ERROR +*******************************************************************************/ +int32_t usb1_host_CtrlTransStart (uint16_t devadr, uint16_t Req, uint16_t Val, + uint16_t Indx, uint16_t Len, uint8_t * Buf) +{ + if (g_usb1_host_UsbDeviceSpeed == USB_HOST_LOW_SPEED) + { + RZA_IO_RegWrite_16(&USB201.SOFCFG, + 1, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + else + { + RZA_IO_RegWrite_16(&USB201.SOFCFG, + 0, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + + USB201.DCPMAXP = (uint16_t)((uint16_t)(devadr << 12) + g_usb1_host_default_max_packet[devadr]); + + if (g_usb1_host_pipe_status[USB_HOST_PIPE0] == USB_HOST_PIPE_IDLE) + { + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_WAIT; + g_usb1_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + g_usb1_host_CmdStage = (USB_HOST_STAGE_SETUP | USB_HOST_CMD_IDLE); + + if (Len == 0) + { + g_usb1_host_CmdStage |= USB_HOST_MODE_NO_DATA; /* No-data Control */ + } + else + { + if ((Req & 0x0080) != 0) + { + g_usb1_host_CmdStage |= USB_HOST_MODE_READ; /* Control Read */ + } + else + { + g_usb1_host_CmdStage |= USB_HOST_MODE_WRITE; /* Control Write */ + } + } + + g_usb1_host_SavReq = Req; /* save request */ + g_usb1_host_SavVal = Val; + g_usb1_host_SavIndx = Indx; + g_usb1_host_SavLen = Len; + } + else + { + if ((g_usb1_host_SavReq != Req) || (g_usb1_host_SavVal != Val) + || (g_usb1_host_SavIndx != Indx) || (g_usb1_host_SavLen != Len)) + { + return DEVDRV_ERROR; + } + } + + switch ((g_usb1_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + /* --------------- SETUP STAGE --------------- */ + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_IDLE): + usb1_host_SetupStage(Req, Val, Indx, Len); + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_DONE): /* goto next stage */ + g_usb1_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + switch ((g_usb1_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_WRITE: + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_DATA; + break; + + case USB_HOST_MODE_READ: + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_DATA; + break; + + case USB_HOST_MODE_NO_DATA: + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_STATUS; + break; + + default: + break; + } + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_NORES): + if (g_usb1_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb1_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_IDLE; + } + break; + + /* --------------- DATA STAGE --------------- */ + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_IDLE): + switch ((g_usb1_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_WRITE: + usb1_host_CtrlWriteStart((uint32_t)Len, Buf); + break; + + case USB_HOST_MODE_READ: + usb1_host_CtrlReadStart((uint32_t)Len, Buf); + break; + + default: + break; + } + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DONE): /* goto next stage */ + g_usb1_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_STATUS; + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_NORES): + if (g_usb1_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb1_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DOING; + usb1_host_clear_pid_stall(USB_HOST_PIPE0); + usb1_host_set_pid_buf(USB_HOST_PIPE0); + } + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_STALL): + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + break; + + /* --------------- STATUS STAGE --------------- */ + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_IDLE): + usb1_host_StatusStage(); + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DONE): /* end of Control transfer */ + usb1_host_set_pid_nak(USB_HOST_PIPE0); + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_DONE; /* exit DONE */ + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_NORES): + if (g_usb1_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb1_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DOING; + usb1_host_clear_pid_stall(USB_HOST_PIPE0); + usb1_host_set_pid_buf(USB_HOST_PIPE0); + } + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_STALL): + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + break; + + default: + break; + } + + if (g_usb1_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_WAIT) + { + RZA_IO_RegWrite_16(&USB201.SOFCFG, + 0, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb1_host_SetupStage +* Description : Executes USB control transfer/set up stage. +* Arguments : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* Return Value : none +*******************************************************************************/ +void usb1_host_SetupStage (uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len) +{ + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DOING; + + USB201.INTSTS1 = (uint16_t)~(USB_HOST_BITSACK | USB_HOST_BITSIGN); /* Status Clear */ + USB201.USBREQ = Req; + USB201.USBVAL = Val; + USB201.USBINDX = Indx; + USB201.USBLENG = Len; + USB201.DCPCTR = USB_HOST_BITSUREQ; /* PID=NAK & Send Setup */ +} + +/******************************************************************************* +* Function Name: usb1_host_StatusStage +* Description : Executes USB control transfer/status stage. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_StatusStage (void) +{ + uint8_t Buf1[16]; + + switch ((g_usb1_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_READ: + usb1_host_CtrlWriteStart((uint32_t)0, (uint8_t*)&Buf1); + break; + + case USB_HOST_MODE_WRITE: + usb1_host_CtrlReadStart((uint32_t)0, (uint8_t*)&Buf1); + break; + + case USB_HOST_MODE_NO_DATA: + usb1_host_CtrlReadStart((uint32_t)0, (uint8_t*)&Buf1); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_CtrlWriteStart +* Description : Executes USB control transfer/data stage(write). +* Arguments : uint32_t Bsize ; Data Size +* : uint8_t *Table ; Data Table Address +* Return Value : USB_HOST_WRITESHRT ; End of data write +* : USB_HOST_WRITEEND ; End of data write (not null) +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_FIFOERROR ; FIFO access error +*******************************************************************************/ +uint16_t usb1_host_CtrlWriteStart (uint32_t Bsize, uint8_t * Table) +{ + uint16_t EndFlag_K; + uint16_t mbw; + + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DOING; + + usb1_host_set_pid_nak(USB_HOST_PIPE0); /* Set NAK */ + g_usb1_host_data_count[USB_HOST_PIPE0] = Bsize; /* Transfer size set */ + g_usb1_host_data_pointer[USB_HOST_PIPE0] = Table; /* Transfer address set */ + + USB201.DCPCTR = USB_HOST_BITSQSET; /* SQSET=1, PID=NAK */ +#if(1) /* ohci_wrapp */ + Userdef_USB_usb1_host_delay_10us(3); +#endif + RZA_IO_RegWrite_16(&USB201.DCPCFG, + 1, + USB_DCPCFG_DIR_SHIFT, + USB_DCPCFG_DIR); + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[USB_HOST_PIPE0], (uint32_t)g_usb1_host_data_pointer[USB_HOST_PIPE0]); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_BITISEL, mbw); + USB201.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + + usb1_host_clear_pid_stall(USB_HOST_PIPE0); + EndFlag_K = usb1_host_write_buffer_c(USB_HOST_PIPE0); + /* Host Control sequence */ + switch (EndFlag_K) + { + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_STATUS; + usb1_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb1_host_enable_bemp_int(USB_HOST_PIPE0); /* Enable Empty Interrupt */ + break; + + case USB_HOST_WRITEEND: /* End of data write (not null) */ + case USB_HOST_WRITING: /* Continue of data write */ + usb1_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb1_host_enable_bemp_int(USB_HOST_PIPE0); /* Enable Empty Interrupt */ + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + break; + + default: + break; + } + usb1_host_set_pid_buf(USB_HOST_PIPE0); /* Set BUF */ + return (EndFlag_K); /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_CtrlReadStart +* Description : Executes USB control transfer/data stage(read). +* Arguments : uint32_t Bsize ; Data Size +* : uint8_t *Table ; Data Table Address +* Return Value : none +*******************************************************************************/ +void usb1_host_CtrlReadStart (uint32_t Bsize, uint8_t * Table) +{ + uint16_t mbw; + + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DOING; + + usb1_host_set_pid_nak(USB_HOST_PIPE0); /* Set NAK */ + g_usb1_host_data_count[USB_HOST_PIPE0] = Bsize; /* Transfer size set */ + g_usb1_host_data_pointer[USB_HOST_PIPE0] = Table; /* Transfer address set */ + + USB201.DCPCTR = USB_HOST_BITSQSET; /* SQSET=1, PID=NAK */ +#if(1) /* ohci_wrapp */ + Userdef_USB_usb1_host_delay_10us(3); +#endif + RZA_IO_RegWrite_16(&USB201.DCPCFG, + 0, + USB_DCPCFG_DIR_SHIFT, + USB_DCPCFG_DIR); + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[USB_HOST_PIPE0], (uint32_t)g_usb1_host_data_pointer[USB_HOST_PIPE0]); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_NO, mbw); + USB201.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + + usb1_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb1_host_enable_brdy_int(USB_HOST_PIPE0); /* Ok */ + usb1_host_clear_pid_stall(USB_HOST_PIPE0); + usb1_host_set_pid_buf(USB_HOST_PIPE0); /* Set BUF */ +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/src/host/usb1_host_drv_api.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,889 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_drv_api.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb1_host_resetEP(USB_HOST_CFG_PIPETBL_t *tbl); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_api_host_init +* Description : Initializes USB module in the USB host mode. +* : USB connection is executed when executing this function in +* : the states that USB device isconnected to the USB port. +* Arguments : uint8_t int_level : USB Module interrupt level +* : USBU16 mode : USB_HOST_HIGH_SPEED +* : USB_HOST_FULL_SPEED +* : uint16_t clockmode : USB Clock mode +* Return Value : USB detach or attach +* : USB_HOST_ATTACH +* : USB_HOST_DETACH +*******************************************************************************/ +uint16_t usb1_api_host_init (uint8_t int_level, uint16_t mode, uint16_t clockmode) +{ + uint16_t connect; + volatile uint8_t dummy_buf; + + CPG.STBCR7 &= 0xfc; /*The clock of USB0/1 modules is permitted */ + dummy_buf = CPG.STBCR7; /* (Dummy read) */ + + g_usb1_host_SupportUsbDeviceSpeed = mode; + + usb1_host_setting_interrupt(int_level); + usb1_host_reset_module(clockmode); + + g_usb1_host_bchg_flag = USB_HOST_NO; + g_usb1_host_detach_flag = USB_HOST_NO; + g_usb1_host_attach_flag = USB_HOST_NO; + + g_usb1_host_driver_state = USB_HOST_DRV_DETACHED; + g_usb1_host_default_max_packet[USB_HOST_DEVICE_0] = 64; + + usb1_host_InitModule(); + + connect = usb1_host_CheckAttach(); + + if (connect == USB_HOST_ATTACH) + { + g_usb1_host_attach_flag = USB_HOST_YES; + } + else + { + usb1_host_UsbDetach2(); + } + + return connect; +} + +#if(1) /* ohci_wrapp */ +#else +/******************************************************************************* +* Function Name: usb1_api_host_enumeration +* Description : Initializes USB module in the USB host mode. +* : USB connection is executed when executing this function in +* : the states that USB device isconnected to the USB port. +* Arguments : uint16_t devadr : device address +* Return Value : DEVDRV_USBH_DETACH_ERR : device detach +* : DEVDRV_SUCCESS : device enumeration success +* : DEVDRV_ERROR : device enumeration error +*******************************************************************************/ +int32_t usb1_api_host_enumeration (uint16_t devadr) +{ + int32_t ret; + uint16_t driver_sts; + + g_usb1_host_setUsbAddress = devadr; + + while (1) + { + driver_sts = usb1_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + ret = DEVDRV_USBH_DETACH_ERR; + break; + } + else if (driver_sts == USB_HOST_DRV_CONFIGURED) + { + ret = DEVDRV_SUCCESS; + break; + } + else if (driver_sts == USB_HOST_DRV_STALL) + { + ret = DEVDRV_ERROR; + break; + } + else if (driver_sts == USB_HOST_DRV_NORES) + { + ret = DEVDRV_ERROR; + break; + } + else + { + /* Do Nothing */ + } + } + + if (driver_sts == USB_HOST_DRV_NORES) + { + while (1) + { + driver_sts = usb1_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + break; + } + } + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_api_host_detach +* Description : USB detach routine +* Arguments : none +* Return Value : USB_HOST_DETACH : USB detach +* : USB_HOST_ATTACH : USB attach +* : DEVDRV_ERROR : error +*******************************************************************************/ +int32_t usb1_api_host_detach (void) +{ + int32_t ret; + uint16_t driver_sts; + + while (1) + { + driver_sts = usb1_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + ret = USB_HOST_DETACH; + break; + } + else if (driver_sts == USB_HOST_DRV_CONFIGURED) + { + ret = USB_HOST_ATTACH; + break; + } + else if (driver_sts == USB_HOST_DRV_STALL) + { + ret = DEVDRV_ERROR; + break; + } + else if (driver_sts == USB_HOST_DRV_NORES) + { + ret = DEVDRV_ERROR; + break; + } + else + { + /* Do Nothing */ + } + } + + if (driver_sts == USB_HOST_DRV_NORES) + { + while (1) + { + driver_sts = usb1_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + break; + } + } + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_api_host_data_in +* Description : Executes USB transfer as data-in in the argument specified pipe. +* Arguments : uint16_t devadr ; device address +* : uint16_t Pipe ; Pipe Number +* : uint32_t Size ; Data Size +* : uint8_t *data_buf ; Data data_buf Address +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_data_in (uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t * data_buf) +{ + int32_t ret; + + if (Pipe == USB_HOST_PIPE0) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipemaxp[Pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL) != devadr) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[Pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 1) + { + return DEVDRV_ERROR; + } + + if (g_usb1_host_pipe_status[Pipe] == USB_HOST_PIPE_IDLE) + { + usb1_host_start_receive_transfer(Pipe, Size, data_buf); + } + else + { + return DEVDRV_ERROR; /* Now pipe is busy */ + } + + /* waiting for completing routine */ + do + { + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb1_host_pipe_status[Pipe] != USB_HOST_PIPE_IDLE) && (g_usb1_host_pipe_status[Pipe] != USB_HOST_PIPE_WAIT)) + { + break; + } + + } while (1); + + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb1_host_pipe_status[Pipe]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + usb1_host_stop_transfer(Pipe); + + g_usb1_host_pipe_status[Pipe] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_api_host_data_out +* Description : Executes USB transfer as data-out in the argument specified pipe. +* Arguments : uint16_t devadr ; device address +* : uint16_t Pipe ; Pipe Number +* : uint32_t Size ; Data Size +* : uint8_t *data_buf ; Data data_buf Address +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_data_out (uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t * data_buf) +{ + int32_t ret; + + if (Pipe == USB_HOST_PIPE0) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipemaxp[Pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL) != devadr) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[Pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 0) + { + return DEVDRV_ERROR; + } + + if (g_usb1_host_pipe_status[Pipe] == USB_HOST_PIPE_IDLE) + { + usb1_host_start_send_transfer(Pipe, Size, data_buf); + } + else + { + return DEVDRV_ERROR; /* Now pipe is busy */ + } + + /* waiting for completing routine */ + do + { + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb1_host_pipe_status[Pipe] != USB_HOST_PIPE_IDLE) && (g_usb1_host_pipe_status[Pipe] != USB_HOST_PIPE_WAIT)) + { + break; + } + + } while (1); + + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb1_host_pipe_status[Pipe]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + usb1_host_stop_transfer(Pipe); + + g_usb1_host_pipe_status[Pipe] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_api_host_control_transfer +* Description : Executes USB control transfer. +* Arguments : uint16_t devadr ; device address +* : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* : uint8_t *buf ; Buffer +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_USBH_DETACH_ERR ; device detach +* : DEVDRV_USBH_CTRL_COM_ERR ; device no response +* : DEVDRV_USBH_STALL ; STALL +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_control_transfer (uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, + uint16_t Len, uint8_t * Buf) +{ + int32_t ret; + + do + { + ret = usb1_host_CtrlTransStart(devadr, Req, Val, Indx, Len, Buf); + + if (ret == DEVDRV_SUCCESS) + { + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb1_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_IDLE) + && (g_usb1_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_WAIT)) + { + break; + } + } + else + { + return DEVDRV_ERROR; + } + } while (1); + + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb1_host_pipe_status[USB_HOST_PIPE0]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_CTRL_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_api_host_set_endpoint +* Description : Sets end point on the information specified in the argument. +* Arguments : uint16_t devadr ; device address +* : uint8_t *configdescriptor ; device configration descriptor +* : USB_HOST_CFG_PIPETBL_t *user_table ; pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_set_endpoint (uint16_t devadr, USB_HOST_CFG_PIPETBL_t * user_table, uint8_t * configdescriptor) +{ + uint16_t ret; + uint32_t end_point; + uint32_t offset; + uint32_t totalLength; + USB_HOST_CFG_PIPETBL_t * pipe_table; + + /* End Point Search */ + end_point = 0; + offset = configdescriptor[0]; + totalLength = (uint16_t)(configdescriptor[2] + ((uint16_t)configdescriptor[3] << 8)); + + do + { + if (configdescriptor[offset + 1] == USB_HOST_ENDPOINT_DESC) + { + pipe_table = &user_table[end_point]; + + if (pipe_table->pipe_number == 0xffff) + { + break; + } + + ret = usb1_api_host_SetEndpointTable(devadr, pipe_table, (uint8_t *)&configdescriptor[offset]); + + if ((ret != USB_HOST_PIPE_IN) && (ret != USB_HOST_PIPE_OUT)) + { + return DEVDRV_ERROR; + } + + ++end_point; + } + + /* Next End Point Search */ + offset += configdescriptor[offset]; + + } while (offset < totalLength); + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb1_api_host_clear_endpoint +* Description : Clears the pipe definition table specified in the argument. +* Arguments : uint16_t pipe_sel : Pipe Number +* : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_clear_endpoint (USB_HOST_CFG_PIPETBL_t * user_table) +{ + uint16_t pipe; + + for (pipe = USB_HOST_PIPE0; pipe <= USB_HOST_MAX_PIPE_NO; ++pipe) + { + if (user_table->pipe_number == 0xffff) + { + break; + } + user_table->pipe_cfg &= (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD); + user_table->pipe_max_pktsize = 0; + user_table->pipe_cycle = 0; + + user_table++; + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb1_api_host_clear_endpoint_pipe +* Description : Clears the pipe definition table specified in the argument. +* Arguments : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_clear_endpoint_pipe (uint16_t pipe_sel, USB_HOST_CFG_PIPETBL_t * user_table) +{ + uint16_t pipe; + + for (pipe = USB_HOST_PIPE0; pipe <= USB_HOST_MAX_PIPE_NO; ++pipe) + { + if (user_table->pipe_number == 0xffff) + { + break; + } + + if (user_table->pipe_number == pipe_sel) + { + user_table->pipe_cfg &= (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD); + user_table->pipe_max_pktsize = 0; + user_table->pipe_cycle = 0; + break; + } + + user_table++; + } + + return DEVDRV_SUCCESS; +} +#endif + +/******************************************************************************* +* Function Name: usb1_api_host_SetEndpointTable +* Description : Sets the end point on the information specified by the argument. +* Arguments : uint16_t devadr : device address +* : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* : uint8_t *Table : Endpoint descriptor +* Return Value : USB_HOST_DIR_H_IN ; IN endpoint +* : USB_HOST_DIR_H_OUT ; OUT endpoint +* : USB_END_POINT_ERROR ; error +*******************************************************************************/ +uint16_t usb1_api_host_SetEndpointTable (uint16_t devadr, USB_HOST_CFG_PIPETBL_t * user_table, uint8_t * Table) +{ + uint16_t PipeCfg; + uint16_t PipeMaxp; + uint16_t pipe_number; + uint16_t ret; + uint16_t ret_flag = 0; // avoid warning. + + pipe_number = user_table->pipe_number; + + if (Table[1] != USB_HOST_ENDPOINT_DESC) + { + return USB_END_POINT_ERROR; + } + + switch (Table[3] & USB_HOST_EP_TYPE) + { + case USB_HOST_EP_CNTRL: + ret_flag = USB_END_POINT_ERROR; + break; + + case USB_HOST_EP_ISO: + if ((pipe_number != USB_HOST_PIPE1) && (pipe_number != USB_HOST_PIPE2)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_ISO; + break; + + case USB_HOST_EP_BULK: + if ((pipe_number < USB_HOST_PIPE1) || (pipe_number > USB_HOST_PIPE5)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_BULK; + break; + + case USB_HOST_EP_INT: + if ((pipe_number < USB_HOST_PIPE6) || (pipe_number > USB_HOST_PIPE9)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_INTERRUPT; + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + + /* Set pipe configuration table */ + if ((Table[2] & USB_HOST_EP_DIR_MASK) == USB_HOST_EP_IN) /* IN(receive) */ + { + if (PipeCfg == USB_HOST_ISO) + { + /* Transfer Type is ISO*/ + PipeCfg |= USB_HOST_DIR_H_IN; + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + case USB_HOST_D0USE: + case USB_HOST_D1USE: + case USB_HOST_D0DMA: + case USB_HOST_D1DMA: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & USB_HOST_DBLBFIELD); + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + } + else + { + /* Transfer Type is BULK or INT */ + PipeCfg |= (USB_HOST_SHTNAKON | USB_HOST_DIR_H_IN); /* Compulsory SHTNAK */ + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + case USB_HOST_D0USE: + case USB_HOST_D1USE: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); + break; + + case USB_HOST_D0DMA: + case USB_HOST_D1DMA: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); +#ifdef __USB_DMA_BFRE_ENABLE__ + /* this routine cannnot be perfomred if read operation is executed in buffer size */ + PipeCfg |= USB_HOST_BFREON; +#endif + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + } + ret = USB_HOST_PIPE_IN; + } + else /* OUT(send) */ + { + if (PipeCfg == USB_HOST_ISO) + { + /* Transfer Type is ISO*/ + PipeCfg |= (uint16_t)(user_table->pipe_cfg & USB_HOST_DBLBFIELD); + } + else + { + /* Transfer Type is BULK or INT */ + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); + } + PipeCfg |= USB_HOST_DIR_H_OUT; + ret = USB_HOST_PIPE_OUT; + } + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + g_usb1_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_CFIFO_USE; + break; + + case USB_HOST_D0USE: + g_usb1_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D0FIFO_USE; + break; + + case USB_HOST_D1USE: + g_usb1_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D1FIFO_USE; + break; + + case USB_HOST_D0DMA: + g_usb1_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D0FIFO_DMA; + break; + + case USB_HOST_D1DMA: + g_usb1_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D1FIFO_DMA; + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + + /* Endpoint number set */ + PipeCfg |= (uint16_t)(Table[2] & USB_HOST_EP_NUM_MASK); + g_usb1_host_PipeTbl[pipe_number] |= (uint16_t)(Table[2] & USB_HOST_EP_NUM_MASK); + + /* Max packet size set */ + PipeMaxp = (uint16_t)((uint16_t)Table[4] | (uint16_t)((uint16_t)Table[5] << 8)); + + if (PipeMaxp == 0u) + { + return USB_END_POINT_ERROR; + } + + /* Set device address */ + PipeMaxp |= (uint16_t)(devadr << 12); + + user_table->pipe_cfg = PipeCfg; + user_table->pipe_max_pktsize = PipeMaxp; + + usb1_host_resetEP(user_table); + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_host_resetEP +* Description : Sets the end point on the information specified by the argument. +* Arguments : USB_HOST_CFG_PIPETBL_t *tbl : pipe table +* Return Value : none +*******************************************************************************/ +static void usb1_host_resetEP (USB_HOST_CFG_PIPETBL_t * tbl) +{ + + uint16_t pipe; + + /* Host pipe */ + /* The pipe number of pipe definition table is obtained */ + pipe = (uint16_t)(tbl->pipe_number & USB_HOST_BITCURPIPE); /* Pipe Number */ + + /* FIFO port access pipe is set to initial value */ + /* The connection with FIFO should be cut before setting the pipe */ + if (RZA_IO_RegRead_16(&USB201.CFIFOSEL, + USB_CFIFOSEL_CURPIPE_SHIFT, + USB_CFIFOSEL_CURPIPE) == pipe) + { + usb1_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + if (RZA_IO_RegRead_16(&USB201.D0FIFOSEL, + USB_DnFIFOSEL_CURPIPE_SHIFT, + USB_DnFIFOSEL_CURPIPE) == pipe) + { + usb1_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + if (RZA_IO_RegRead_16(&USB201.D1FIFOSEL, + USB_DnFIFOSEL_CURPIPE_SHIFT, + USB_DnFIFOSEL_CURPIPE) == pipe) + { + usb1_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + /* Interrupt of pipe set is disabled */ + usb1_host_disable_brdy_int(pipe); + usb1_host_disable_nrdy_int(pipe); + usb1_host_disable_bemp_int(pipe); + + /* Pipe to set is set to NAK */ + usb1_host_set_pid_nak(pipe); + + /* Pipe is set */ + USB201.PIPESEL = pipe; + + USB201.PIPECFG = tbl->pipe_cfg; + USB201.PIPEBUF = tbl->pipe_buf; + USB201.PIPEMAXP = tbl->pipe_max_pktsize; + USB201.PIPEPERI = tbl->pipe_cycle; + + g_usb1_host_pipecfg[pipe] = tbl->pipe_cfg; + g_usb1_host_pipebuf[pipe] = tbl->pipe_buf; + g_usb1_host_pipemaxp[pipe] = tbl->pipe_max_pktsize; + g_usb1_host_pipeperi[pipe] = tbl->pipe_cycle; + + /* Sequence bit clear */ + usb1_host_set_sqclr(pipe); + + usb1_host_aclrm(pipe); + usb1_host_set_csclr(pipe); + + /* Pipe window selection is set to unused */ + USB201.PIPESEL = USB_HOST_PIPE0; + +} + +#if(1) /* ohci_wrapp */ +#else +/******************************************************************************* +* Function Name: usb1_api_host_data_count +* Description : Get g_usb0_host_data_count[pipe] +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t *data_count ; return g_usb0_data_count[pipe] +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_data_count (uint16_t pipe, uint32_t * data_count) +{ + if (pipe > USB_HOST_MAX_PIPE_NO) + { + return DEVDRV_ERROR; + } + + *data_count = g_usb1_host_PipeDataSize[pipe]; + + return DEVDRV_SUCCESS; +} +#endif + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/src/host/usb1_host_global.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,137 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_global.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +const uint16_t g_usb1_host_bit_set[16] = +{ + 0x0001, 0x0002, 0x0004, 0x0008, + 0x0010, 0x0020, 0x0040, 0x0080, + 0x0100, 0x0200, 0x0400, 0x0800, + 0x1000, 0x2000, 0x4000, 0x8000 +}; + +uint32_t g_usb1_host_data_count[USB_HOST_MAX_PIPE_NO + 1]; +uint8_t * g_usb1_host_data_pointer[USB_HOST_MAX_PIPE_NO + 1]; + +uint16_t g_usb1_host_PipeIgnore[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb1_host_PipeTbl[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb1_host_pipe_status[USB_HOST_MAX_PIPE_NO + 1]; +uint32_t g_usb1_host_PipeDataSize[USB_HOST_MAX_PIPE_NO + 1]; + +USB_HOST_DMA_t g_usb1_host_DmaInfo[2]; + +uint16_t g_usb1_host_DmaPipe[2]; +uint16_t g_usb1_host_DmaBval[2]; +uint16_t g_usb1_host_DmaStatus[2]; + +uint16_t g_usb1_host_driver_state; +uint16_t g_usb1_host_ConfigNum; +uint16_t g_usb1_host_CmdStage; +uint16_t g_usb1_host_bchg_flag; +uint16_t g_usb1_host_detach_flag; +uint16_t g_usb1_host_attach_flag; + +uint16_t g_usb1_host_UsbAddress; +uint16_t g_usb1_host_setUsbAddress; +uint16_t g_usb1_host_default_max_packet[USB_HOST_MAX_DEVICE + 1]; +uint16_t g_usb1_host_UsbDeviceSpeed; +uint16_t g_usb1_host_SupportUsbDeviceSpeed; + +uint16_t g_usb1_host_SavReq; +uint16_t g_usb1_host_SavVal; +uint16_t g_usb1_host_SavIndx; +uint16_t g_usb1_host_SavLen; + +uint16_t g_usb1_host_pipecfg[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb1_host_pipebuf[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb1_host_pipemaxp[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb1_host_pipeperi[USB_HOST_MAX_PIPE_NO + 1]; + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_init_pipe_status +* Description : Initialize pipe status. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_init_pipe_status (void) +{ + uint16_t loop; + + g_usb1_host_ConfigNum = 0; + + for (loop = 0; loop < (USB_HOST_MAX_PIPE_NO + 1); ++loop) + { + g_usb1_host_pipe_status[loop] = USB_HOST_PIPE_IDLE; + g_usb1_host_PipeDataSize[loop] = 0; + + /* pipe configuration in usb1_host_resetEP() */ + g_usb1_host_pipecfg[loop] = 0; + g_usb1_host_pipebuf[loop] = 0; + g_usb1_host_pipemaxp[loop] = 0; + g_usb1_host_pipeperi[loop] = 0; + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/src/host/usb1_host_usbint.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,497 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_usbint.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#if(1) /* ohci_wrapp */ +#include "ohci_wrapp_RZ_A1_local.h" +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb1_host_interrupt1(void); +static void usb1_host_BRDYInterrupt(uint16_t Status, uint16_t Int_enbl); +static void usb1_host_NRDYInterrupt(uint16_t Status, uint16_t Int_enbl); +static void usb1_host_BEMPInterrupt(uint16_t Status, uint16_t Int_enbl); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_interrupt +* Description : Executes USB interrupt. +* : Register this function in the USB interrupt handler. +* : Set CFIF0 in the pipe set before the interrupt after executing +* : this function. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb1_host_interrupt (uint32_t int_sense) +{ + uint16_t savepipe1; + uint16_t savepipe2; + uint16_t buffer; + + savepipe1 = USB201.CFIFOSEL; + savepipe2 = USB201.PIPESEL; + usb1_host_interrupt1(); + + /* Control transmission changes ISEL within interruption processing. */ + /* For this reason, write return of ISEL cannot be performed. */ + buffer = USB201.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(savepipe1 & USB_HOST_BITCURPIPE); + USB201.CFIFOSEL = buffer; + USB201.PIPESEL = savepipe2; +} + +/******************************************************************************* +* Function Name: usb1_host_interrupt1 +* Description : Execue the USB interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_interrupt1 (void) +{ + uint16_t intsts0; + uint16_t intsts1; + uint16_t intenb0; + uint16_t intenb1; + uint16_t brdysts; + uint16_t nrdysts; + uint16_t bempsts; + uint16_t brdyenb; + uint16_t nrdyenb; + uint16_t bempenb; + volatile uint16_t dumy_sts; + + intsts0 = USB201.INTSTS0; + intsts1 = USB201.INTSTS1; + intenb0 = USB201.INTENB0; + intenb1 = USB201.INTENB1; + + if ((intsts1 & USB_HOST_BITBCHG) && (intenb1 & USB_HOST_BITBCHGE)) + { + USB201.INTSTS1 = (uint16_t)~USB_HOST_BITBCHG; + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); + g_usb1_host_bchg_flag = USB_HOST_YES; + } + else if ((intsts1 & USB_HOST_BITSACK) && (intenb1 & USB_HOST_BITSACKE)) + { + USB201.INTSTS1 = (uint16_t)~USB_HOST_BITSACK; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); +#else + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; +#endif + } + else if ((intsts1 & USB_HOST_BITSIGN) && (intenb1 & USB_HOST_BITSIGNE)) + { + USB201.INTSTS1 = (uint16_t)~USB_HOST_BITSIGN; +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#else + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_NORES; +#endif + } + else if (((intsts1 & USB_HOST_BITDTCH) == USB_HOST_BITDTCH) + && ((intenb1 & USB_HOST_BITDTCHE) == USB_HOST_BITDTCHE)) + { + USB201.INTSTS1 = (uint16_t)~USB_HOST_BITDTCH; + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); + g_usb1_host_detach_flag = USB_HOST_YES; + + Userdef_USB_usb1_host_detach(); + + usb1_host_UsbDetach2(); + } + else if (((intsts1 & USB_HOST_BITATTCH) == USB_HOST_BITATTCH) + && ((intenb1 & USB_HOST_BITATTCHE) == USB_HOST_BITATTCHE)) + { + USB201.INTSTS1 = (uint16_t)~USB_HOST_BITATTCH; + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); + g_usb1_host_attach_flag = USB_HOST_YES; + + Userdef_USB_usb1_host_attach(); + + usb1_host_UsbAttach(); + } + else if ((intsts0 & intenb0 & (USB_HOST_BITBEMP | USB_HOST_BITNRDY | USB_HOST_BITBRDY))) + { + brdysts = USB201.BRDYSTS; + nrdysts = USB201.NRDYSTS; + bempsts = USB201.BEMPSTS; + brdyenb = USB201.BRDYENB; + nrdyenb = USB201.NRDYENB; + bempenb = USB201.BEMPENB; + + if ((intsts0 & USB_HOST_BITBRDY) && (intenb0 & USB_HOST_BITBRDYE) && (brdysts & brdyenb)) + { + usb1_host_BRDYInterrupt(brdysts, brdyenb); + } + else if ((intsts0 & USB_HOST_BITBEMP) && (intenb0 & USB_HOST_BITBEMPE) && (bempsts & bempenb)) + { + usb1_host_BEMPInterrupt(bempsts, bempenb); + } + else if ((intsts0 & USB_HOST_BITNRDY) && (intenb0 & USB_HOST_BITNRDYE) && (nrdysts & nrdyenb)) + { + usb1_host_NRDYInterrupt(nrdysts, nrdyenb); + } + else + { + /* Do Nothing */ + } + } + else + { + /* Do Nothing */ + } + + /* Three dummy read for clearing interrupt requests */ + dumy_sts = USB201.INTSTS0; + dumy_sts = USB201.INTSTS1; + +} + +/******************************************************************************* +* Function Name: usb1_host_BRDYInterrupt +* Description : Executes USB BRDY interrupt. +* Arguments : uint16_t Status ; BRDYSTS Register Value +* : uint16_t Int_enbl ; BRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_BRDYInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t buffer; + volatile uint16_t dumy_sts; + + if ((Status & g_usb1_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb1_host_bit_set[USB_HOST_PIPE0])) + { + USB201.BRDYSTS = (uint16_t)~g_usb1_host_bit_set[USB_HOST_PIPE0]; + +#if(1) /* ohci_wrapp */ + switch ((g_usb1_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + buffer = usb1_host_read_buffer_c(USB_HOST_PIPE0); + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb1_host_read_buffer_c(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_READOVER: /* buffer over */ + USB201.CFIFOCTR = USB_HOST_BITBCLR; + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + break; + } +#else + switch ((g_usb1_host_CmdStage & (USB_HOST_MODE_FIELD | USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + case (USB_HOST_MODE_NO_DATA | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + buffer = usb1_host_read_buffer_c(USB_HOST_PIPE0); + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case (USB_HOST_MODE_READ | USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb1_host_read_buffer_c(USB_HOST_PIPE0); + + switch (buffer) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case USB_HOST_READOVER: /* buffer over */ + USB201.CFIFOCTR = USB_HOST_BITBCLR; + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + break; + } +#endif + } + else + { + usb1_host_brdy_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB201.BRDYSTS; +} + +/******************************************************************************* +* Function Name: usb1_host_NRDYInterrupt +* Description : Executes USB NRDY interrupt. +* Arguments : uint16_t Status ; NRDYSTS Register Value +* : uint16_t Int_enbl ; NRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_NRDYInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t pid; + volatile uint16_t dumy_sts; + + if ((Status & g_usb1_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb1_host_bit_set[USB_HOST_PIPE0])) + { + USB201.NRDYSTS = (uint16_t)~g_usb1_host_bit_set[USB_HOST_PIPE0]; + pid = usb1_host_get_pid(USB_HOST_PIPE0); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_STALL; +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + + } + else if (pid == USB_HOST_PID_NAK) + { + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_NORES; +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + } + else + { + /* Do Nothing */ + } + } + else + { + usb1_host_nrdy_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB201.NRDYSTS; +} + +/******************************************************************************* +* Function Name: usb1_host_BEMPInterrupt +* Description : Executes USB BEMP interrupt. +* Arguments : uint16_t Status ; BEMPSTS Register Value +* : uint16_t Int_enbl ; BEMPENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_BEMPInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t buffer; + uint16_t pid; + volatile uint16_t dumy_sts; + + if ((Status & g_usb1_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb1_host_bit_set[USB_HOST_PIPE0])) + { + USB201.BEMPSTS = (uint16_t)~g_usb1_host_bit_set[USB_HOST_PIPE0]; + pid = usb1_host_get_pid(USB_HOST_PIPE0); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_STALL; +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + } + else + { +#if(1) /* ohci_wrapp */ + switch ((g_usb1_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb1_host_write_buffer(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_WRITING: /* Continue of data write */ + case USB_HOST_WRITEEND: /* End of data write (zero-length) */ + break; + + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_STATUS; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + /* do nothing */ + break; + } +#else + switch ((g_usb1_host_CmdStage & (USB_HOST_MODE_FIELD | USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_MODE_READ | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb1_host_write_buffer(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_WRITING: /* Continue of data write */ + case USB_HOST_WRITEEND: /* End of data write (zero-length) */ + break; + + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_STATUS; + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + default: + /* do nothing */ + break; + } +#endif + } + } + else + { + usb1_host_bemp_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB201.BEMPSTS; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/src/host/usb1_host_usbsig.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,637 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_usbsig.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb1_host_EnableINT_Module(void); +static void usb1_host_Enable_AttachINT(void); +static void usb1_host_Disable_AttachINT(void); +static void usb1_host_Disable_BchgINT(void); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_InitModule +* Description : Initializes the USB module in USB host module. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_InitModule (void) +{ + uint16_t buf1; + uint16_t buf2; + uint16_t buf3; + + usb1_host_init_pipe_status(); + + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 1, + USB_SYSCFG_DCFM_SHIFT, + USB_SYSCFG_DCFM); /* HOST mode */ + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 1, + USB_SYSCFG_DRPD_SHIFT, + USB_SYSCFG_DRPD); /* PORT0 D+, D- setting */ + + do + { + buf1 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb1_host_delay_xms(50); + buf2 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb1_host_delay_xms(50); + buf3 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + + } while ((buf1 != buf2) || (buf1 != buf3)); + + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 1, + USB_SYSCFG_USBE_SHIFT, + USB_SYSCFG_USBE); + + USB201.CFIFOSEL = (uint16_t)(USB_HOST_BITRCNT | USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); + USB201.D0FIFOSEL = (uint16_t)( USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); + USB201.D1FIFOSEL = (uint16_t)( USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); +} + +/******************************************************************************* +* Function Name: usb1_host_CheckAttach +* Description : Returns the USB device connection state. +* Arguments : none +* Return Value : uint16_t ; USB_HOST_ATTACH : Attached +* : ; USB_HOST_DETACH : not Attached +*******************************************************************************/ +uint16_t usb1_host_CheckAttach (void) +{ + uint16_t buf1; + uint16_t buf2; + uint16_t buf3; + uint16_t rhst; + + do + { + buf1 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb1_host_delay_xms(50); + buf2 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb1_host_delay_xms(50); + buf3 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + + } while ((buf1 != buf2) || (buf1 != buf3)); + + rhst = RZA_IO_RegRead_16(&USB201.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (rhst == USB_HOST_UNDECID) + { + if (buf1 == USB_HOST_FS_JSTS) + { + if (g_usb1_host_SupportUsbDeviceSpeed == USB_HOST_HIGH_SPEED) + { + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 1, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + } + else + { + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + } + return USB_HOST_ATTACH; + } + else if (buf1 == USB_HOST_LS_JSTS) + { + /* Low Speed Device */ + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + return USB_HOST_ATTACH; + } + else + { + /* Do Nothing */ + } + } + else if ((rhst == USB_HOST_HSMODE) || (rhst == USB_HOST_FSMODE)) + { + return USB_HOST_ATTACH; + } + else if (rhst == USB_HOST_LSMODE) + { + return USB_HOST_ATTACH; + } + else + { + /* Do Nothing */ + } + + return USB_HOST_DETACH; +} + +/******************************************************************************* +* Function Name: usb1_host_UsbAttach +* Description : Connects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_UsbAttach (void) +{ + usb1_host_EnableINT_Module(); + usb1_host_Disable_BchgINT(); + usb1_host_Disable_AttachINT(); + usb1_host_Enable_DetachINT(); +} + +/******************************************************************************* +* Function Name: usb1_host_UsbDetach +* Description : Disconnects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_UsbDetach (void) +{ + uint16_t pipe; + uint16_t devadr; + + g_usb1_host_driver_state = USB_HOST_DRV_DETACHED; + + /* Terminate all the pipes in which communications on port */ + /* are currently carried out */ + for (pipe = 0; pipe < (USB_HOST_MAX_PIPE_NO + 1); ++pipe) + { + if (g_usb1_host_pipe_status[pipe] != USB_HOST_PIPE_IDLE) + { + if (pipe == USB_HOST_PIPE0) + { + devadr = RZA_IO_RegRead_16(&USB201.DCPMAXP, + USB_DCPMAXP_DEVSEL_SHIFT, + USB_DCPMAXP_DEVSEL); + } + else + { + devadr = RZA_IO_RegRead_16(&g_usb1_host_pipemaxp[pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL); + } + + if (devadr == g_usb1_host_UsbAddress) + { + usb1_host_stop_transfer(pipe); + } + + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_IDLE; + } + } + + g_usb1_host_ConfigNum = 0; + g_usb1_host_UsbAddress = 0; + g_usb1_host_default_max_packet[USB_HOST_DEVICE_0] = 64; + + usb1_host_UsbDetach2(); +} + +/******************************************************************************* +* Function Name: usb1_host_UsbDetach2 +* Description : Disconnects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_UsbDetach2 (void) +{ + usb1_host_Disable_DetachINT(); + usb1_host_Disable_BchgINT(); + usb1_host_Enable_AttachINT(); +} + +/******************************************************************************* +* Function Name: usb1_host_UsbBusReset +* Description : Issues the USB bus reset signal. +* Arguments : none +* Return Value : uint16_t ; RHST +*******************************************************************************/ +uint16_t usb1_host_UsbBusReset (void) +{ + uint16_t buffer; + uint16_t loop; + + RZA_IO_RegWrite_16(&USB201.DVSTCTR0, + 1, + USB_DVSTCTR0_USBRST_SHIFT, + USB_DVSTCTR0_USBRST); + RZA_IO_RegWrite_16(&USB201.DVSTCTR0, + 0, + USB_DVSTCTR0_UACT_SHIFT, + USB_DVSTCTR0_UACT); + + Userdef_USB_usb1_host_delay_xms(50); + + buffer = USB201.DVSTCTR0; + buffer &= (uint16_t)(~(USB_HOST_BITRST)); + buffer |= USB_HOST_BITUACT; + USB201.DVSTCTR0 = buffer; + + Userdef_USB_usb1_host_delay_xms(20); + + for (loop = 0, buffer = USB_HOST_HSPROC; loop < 3; ++loop) + { + buffer = RZA_IO_RegRead_16(&USB201.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (buffer == USB_HOST_HSPROC) + { + Userdef_USB_usb1_host_delay_xms(10); + } + else + { + break; + } + } + + return buffer; +} + +/******************************************************************************* +* Function Name: usb1_host_UsbResume +* Description : Issues the USB resume signal. +* Arguments : none +* Return Value : int32_t ; DEVDRV_SUCCESS +* : ; DEVDRV_ERROR +*******************************************************************************/ +int32_t usb1_host_UsbResume (void) +{ + uint16_t buf; + + if ((g_usb1_host_driver_state & USB_HOST_DRV_SUSPEND) == 0) + { + /* not SUSPEND */ + return DEVDRV_ERROR; + } + + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); + RZA_IO_RegWrite_16(&USB201.DVSTCTR0, + 1, + USB_DVSTCTR0_RESUME_SHIFT, + USB_DVSTCTR0_RESUME); + Userdef_USB_usb1_host_delay_xms(20); + + buf = USB201.DVSTCTR0; + buf &= (uint16_t)(~(USB_HOST_BITRESUME)); + buf |= USB_HOST_BITUACT; + USB201.DVSTCTR0 = buf; + + g_usb1_host_driver_state &= (uint16_t)~USB_HOST_DRV_SUSPEND; + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb1_host_UsbSuspend +* Description : Issues the USB suspend signal. +* Arguments : none +* Return Value : int32_t ; DEVDRV_SUCCESS :not SUSPEND +* : ; DEVDRV_ERROR :SUSPEND +*******************************************************************************/ +int32_t usb1_host_UsbSuspend (void) +{ + uint16_t buf; + + if ((g_usb1_host_driver_state & USB_HOST_DRV_SUSPEND) != 0) + { + /* SUSPEND */ + return DEVDRV_ERROR; + } + + RZA_IO_RegWrite_16(&USB201.DVSTCTR0, + 0, + USB_DVSTCTR0_UACT_SHIFT, + USB_DVSTCTR0_UACT); + + Userdef_USB_usb1_host_delay_xms(5); + + buf = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + if ((buf != USB_HOST_FS_JSTS) && (buf != USB_HOST_LS_JSTS)) + { + usb1_host_UsbDetach(); + } + else + { + g_usb1_host_driver_state |= USB_HOST_DRV_SUSPEND; + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb1_host_Enable_DetachINT +* Description : Enables the USB disconnection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_Enable_DetachINT (void) +{ + USB201.INTSTS1 = (uint16_t)(~(USB_HOST_BITDTCH)); + RZA_IO_RegWrite_16(&USB201.INTENB1, + 1, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); +} + +/******************************************************************************* +* Function Name: usb1_host_Disable_DetachINT +* Description : Disables the USB disconnection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_Disable_DetachINT (void) +{ + USB201.INTSTS1 = (uint16_t)(~(USB_HOST_BITDTCH)); + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); +} + +/******************************************************************************* +* Function Name: usb1_host_Enable_AttachINT +* Description : Enables the USB connection detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_Enable_AttachINT (void) +{ + USB201.INTSTS1 = (uint16_t)(~(USB_HOST_BITATTCH)); + RZA_IO_RegWrite_16(&USB201.INTENB1, + 1, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); +} + +/******************************************************************************* +* Function Name: usb1_host_Disable_AttachINT +* Description : Disables the USB connection detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_Disable_AttachINT (void) +{ + USB201.INTSTS1 = (uint16_t)(~(USB_HOST_BITATTCH)); + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); +} + +/******************************************************************************* +* Function Name: usb1_host_Disable_BchgINT +* Description : Disables the USB bus change detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_Disable_BchgINT (void) +{ + USB201.INTSTS1 = (uint16_t)(~(USB_HOST_BITBCHG)); + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); +} + +/******************************************************************************* +* Function Name: usb1_host_set_devadd +* Description : DEVADDn register is set by specified value +* Arguments : uint16_t addr : Device address +* : uint16_t *devadd : Set value +* Return Value : none +*******************************************************************************/ +void usb1_host_set_devadd (uint16_t addr, uint16_t * devadd) +{ + uint16_t * ptr; + uint16_t ret_flag = DEVDRV_FLAG_ON; // avoid warning. + + switch (addr) + { + case USB_HOST_DEVICE_0: + ptr = (uint16_t *)&USB201.DEVADD0; + break; + + case USB_HOST_DEVICE_1: + ptr = (uint16_t *)&USB201.DEVADD1; + break; + + case USB_HOST_DEVICE_2: + ptr = (uint16_t *)&USB201.DEVADD2; + break; + + case USB_HOST_DEVICE_3: + ptr = (uint16_t *)&USB201.DEVADD3; + break; + + case USB_HOST_DEVICE_4: + ptr = (uint16_t *)&USB201.DEVADD4; + break; + + case USB_HOST_DEVICE_5: + ptr = (uint16_t *)&USB201.DEVADD5; + break; + + case USB_HOST_DEVICE_6: + ptr = (uint16_t *)&USB201.DEVADD6; + break; + + case USB_HOST_DEVICE_7: + ptr = (uint16_t *)&USB201.DEVADD7; + break; + + case USB_HOST_DEVICE_8: + ptr = (uint16_t *)&USB201.DEVADD8; + break; + + case USB_HOST_DEVICE_9: + ptr = (uint16_t *)&USB201.DEVADD9; + break; + + case USB_HOST_DEVICE_10: + ptr = (uint16_t *)&USB201.DEVADDA; + break; + + default: + ret_flag = DEVDRV_FLAG_OFF; + break; + } + + if (ret_flag == DEVDRV_FLAG_ON) + { + *ptr = (uint16_t)(*devadd & USB_HOST_DEVADD_MASK); + } +} + +/******************************************************************************* +* Function Name: usb1_host_get_devadd +* Description : DEVADDn register is obtained +* Arguments : uint16_t addr : Device address +* : uint16_t *devadd : USB_HOST_DEVADD register value +* Return Value : none +*******************************************************************************/ +void usb1_host_get_devadd (uint16_t addr, uint16_t * devadd) +{ + uint16_t * ptr; + uint16_t ret_flag = DEVDRV_FLAG_ON; // avoid warning. + + switch (addr) + { + case USB_HOST_DEVICE_0: + ptr = (uint16_t *)&USB201.DEVADD0; + break; + + case USB_HOST_DEVICE_1: + ptr = (uint16_t *)&USB201.DEVADD1; + break; + + case USB_HOST_DEVICE_2: + ptr = (uint16_t *)&USB201.DEVADD2; + break; + + case USB_HOST_DEVICE_3: + ptr = (uint16_t *)&USB201.DEVADD3; + break; + + case USB_HOST_DEVICE_4: + ptr = (uint16_t *)&USB201.DEVADD4; + break; + + case USB_HOST_DEVICE_5: + ptr = (uint16_t *)&USB201.DEVADD5; + break; + + case USB_HOST_DEVICE_6: + ptr = (uint16_t *)&USB201.DEVADD6; + break; + + case USB_HOST_DEVICE_7: + ptr = (uint16_t *)&USB201.DEVADD7; + break; + + case USB_HOST_DEVICE_8: + ptr = (uint16_t *)&USB201.DEVADD8; + break; + + case USB_HOST_DEVICE_9: + ptr = (uint16_t *)&USB201.DEVADD9; + break; + + case USB_HOST_DEVICE_10: + ptr = (uint16_t *)&USB201.DEVADDA; + break; + + default: + ret_flag = DEVDRV_FLAG_OFF; + break; + } + + if (ret_flag == DEVDRV_FLAG_ON) + { + *devadd = *ptr; + } +} + +/******************************************************************************* +* Function Name: usb1_host_EnableINT_Module +* Description : Enables BEMP/NRDY/BRDY interrupt and SIGN/SACK interrupt. +* : Enables NRDY/BEMP interrupt in the pipe0. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_EnableINT_Module (void) +{ + uint16_t buf; + + buf = USB201.INTENB0; + buf |= (USB_HOST_BITBEMPE | USB_HOST_BITNRDYE | USB_HOST_BITBRDYE); + USB201.INTENB0 = buf; + + buf = USB201.INTENB1; + buf |= (USB_HOST_BITSIGNE | USB_HOST_BITSACKE); + USB201.INTENB1 = buf; + + usb1_host_enable_nrdy_int(USB_HOST_PIPE0); + usb1_host_enable_bemp_int(USB_HOST_PIPE0); +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/src/userdef/usb1_host_dmacdrv.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,698 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_dmacdrv.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "r_typedefs.h" +#include "iodefine.h" +#include "rza_io_regrw.h" +#include "usb1_host_dmacdrv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define DMAC_INDEFINE (255) /* Macro definition when REQD bit is not used */ + +/* ==== Request setting information for on-chip peripheral module ==== */ +typedef enum dmac_peri_req_reg_type +{ + DMAC_REQ_MID, + DMAC_REQ_RID, + DMAC_REQ_AM, + DMAC_REQ_LVL, + DMAC_REQ_REQD +} dmac_peri_req_reg_type_t; + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +/* ==== Prototype declaration ==== */ + +/* ==== Global variable ==== */ +/* On-chip peripheral module request setting table */ +static const uint8_t usb1_host_dmac_peri_req_init_table[8][5] = +{ + /* MID,RID, AM,LVL,REQD */ + { 32, 3, 2, 1, 1}, /* USB_0 channel 0 transmit FIFO empty */ + { 32, 3, 2, 1, 0}, /* USB_0 channel 0 receive FIFO full */ + { 33, 3, 2, 1, 1}, /* USB_0 channel 1 transmit FIFO empty */ + { 33, 3, 2, 1, 0}, /* USB_0 channel 1 receive FIFO full */ + { 34, 3, 2, 1, 1}, /* USB_1 channel 0 transmit FIFO empty */ + { 34, 3, 2, 1, 0}, /* USB_1 channel 0 receive FIFO full */ + { 35, 3, 2, 1, 1}, /* USB_1 channel 1 transmit FIFO empty */ + { 35, 3, 2, 1, 0}, /* USB_1 channel 1 receive FIFO full */ +}; + + +/******************************************************************************* +* Function Name: usb1_host_DMAC3_PeriReqInit +* Description : Sets the register mode for DMA mode and the on-chip peripheral +* : module request for transfer request for DMAC channel 3. +* : Executes DMAC initial setting using the DMA information +* : specified by the argument *trans_info and the enabled/disabled +* : continuous transfer specified by the argument continuation. +* : Registers DMAC channel 3 interrupt handler function and sets +* : the interrupt priority level. Then enables transfer completion +* : interrupt. +* Arguments : dmac_transinfo_t * trans_info : Setting information to DMAC +* : : register +* : uint32_t dmamode : DMA mode (only for DMAC_MODE_REGISTER) +* : uint32_t continuation : Set continuous transfer to be valid +* : : after DMA transfer has been completed +* : DMAC_SAMPLE_CONTINUATION : Execute continuous transfer +* : DMAC_SAMPLE_SINGLE : Do not execute continuous +* : : transfer +* : uint32_t request_factor : Factor for on-chip peripheral module +* : : request +* : DMAC_REQ_OSTM0TINT : OSTM_0 compare match +* : DMAC_REQ_OSTM1TINT : OSTM_1 compare match +* : DMAC_REQ_TGI0A : MTU2_0 input capture/compare match +* : : +* : uint32_t req_direction : Setting value of CHCFG_n register +* : : REQD bit +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC3_PeriReqInit (const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction) +{ + /* ==== Register mode ==== */ + if (DMAC_MODE_REGISTER == dmamode) + { + /* ==== Next0 register set ==== */ + DMAC3.N0SA_n = trans_info->src_addr; /* Start address of transfer source */ + DMAC3.N0DA_n = trans_info->dst_addr; /* Start address of transfer destination */ + DMAC3.N0TB_n = trans_info->count; /* Total transfer byte count */ + + /* DAD : Transfer destination address counting direction */ + /* SAD : Transfer source address counting direction */ + /* DDS : Transfer destination transfer size */ + /* SDS : Transfer source transfer size */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + trans_info->daddr_dir, + DMAC3_CHCFG_n_DAD_SHIFT, + DMAC3_CHCFG_n_DAD); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + trans_info->saddr_dir, + DMAC3_CHCFG_n_SAD_SHIFT, + DMAC3_CHCFG_n_SAD); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + trans_info->dst_size, + DMAC3_CHCFG_n_DDS_SHIFT, + DMAC3_CHCFG_n_DDS); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + trans_info->src_size, + DMAC3_CHCFG_n_SDS_SHIFT, + DMAC3_CHCFG_n_SDS); + + /* DMS : Register mode */ + /* RSEL : Select Next0 register set */ + /* SBE : No discharge of buffer data when aborted */ + /* DEM : No DMA interrupt mask */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_DMS_SHIFT, + DMAC3_CHCFG_n_DMS); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_RSEL_SHIFT, + DMAC3_CHCFG_n_RSEL); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_SBE_SHIFT, + DMAC3_CHCFG_n_SBE); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_DEM_SHIFT, + DMAC3_CHCFG_n_DEM); + + /* ---- Continuous transfer ---- */ + if (DMAC_SAMPLE_CONTINUATION == continuation) + { + /* REN : Execute continuous transfer */ + /* RSW : Change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 1, + DMAC3_CHCFG_n_REN_SHIFT, + DMAC3_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 1, + DMAC3_CHCFG_n_RSW_SHIFT, + DMAC3_CHCFG_n_RSW); + } + /* ---- Single transfer ---- */ + else + { + /* REN : Do not execute continuous transfer */ + /* RSW : Do not change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_REN_SHIFT, + DMAC3_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_RSW_SHIFT, + DMAC3_CHCFG_n_RSW); + } + + /* TM : Single transfer */ + /* SEL : Channel setting */ + /* HIEN, LOEN : On-chip peripheral module request */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_TM_SHIFT, + DMAC3_CHCFG_n_TM); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 3, + DMAC3_CHCFG_n_SEL_SHIFT, + DMAC3_CHCFG_n_SEL); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 1, + DMAC3_CHCFG_n_HIEN_SHIFT, + DMAC3_CHCFG_n_HIEN); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_LOEN_SHIFT, + DMAC3_CHCFG_n_LOEN); + + /* ---- Set factor by specified on-chip peripheral module request ---- */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_AM], + DMAC3_CHCFG_n_AM_SHIFT, + DMAC3_CHCFG_n_AM); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_LVL], + DMAC3_CHCFG_n_LVL_SHIFT, + DMAC3_CHCFG_n_LVL); + if (usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD] != DMAC_INDEFINE) + { + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD], + DMAC3_CHCFG_n_REQD_SHIFT, + DMAC3_CHCFG_n_REQD); + } + else + { + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + req_direction, + DMAC3_CHCFG_n_REQD_SHIFT, + DMAC3_CHCFG_n_REQD); + } + RZA_IO_RegWrite_32(&DMAC23.DMARS, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_RID], + DMAC23_DMARS_CH3_RID_SHIFT, + DMAC23_DMARS_CH3_RID); + RZA_IO_RegWrite_32(&DMAC23.DMARS, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_MID], + DMAC23_DMARS_CH3_MID_SHIFT, + DMAC23_DMARS_CH3_MID); + + /* PR : Round robin mode */ + RZA_IO_RegWrite_32(&DMAC07.DCTRL_0_7, + 1, + DMAC07_DCTRL_0_7_PR_SHIFT, + DMAC07_DCTRL_0_7_PR); + } +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC3_Open +* Description : Enables DMAC channel 3 transfer. +* Arguments : uint32_t req : DMAC request mode +* Return Value : 0 : Succeeded in enabling DMA transfer +* : -1 : Failed to enable DMA transfer (due to DMA operation) +*******************************************************************************/ +int32_t usb1_host_DMAC3_Open (uint32_t req) +{ + int32_t ret; + volatile uint8_t dummy; + + /* Transferable? */ + if ((0 == RZA_IO_RegRead_32(&DMAC3.CHSTAT_n, + DMAC3_CHSTAT_n_EN_SHIFT, + DMAC3_CHSTAT_n_EN)) && + (0 == RZA_IO_RegRead_32(&DMAC3.CHSTAT_n, + DMAC3_CHSTAT_n_TACT_SHIFT, + DMAC3_CHSTAT_n_TACT))) + { + /* Clear Channel Status Register */ + RZA_IO_RegWrite_32(&DMAC3.CHCTRL_n, + 1, + DMAC3_CHCTRL_n_SWRST_SHIFT, + DMAC3_CHCTRL_n_SWRST); + dummy = RZA_IO_RegRead_32(&DMAC3.CHCTRL_n, + DMAC3_CHCTRL_n_SWRST_SHIFT, + DMAC3_CHCTRL_n_SWRST); + /* Enable DMA transfer */ + RZA_IO_RegWrite_32(&DMAC3.CHCTRL_n, + 1, + DMAC3_CHCTRL_n_SETEN_SHIFT, + DMAC3_CHCTRL_n_SETEN); + + /* ---- Request by software ---- */ + if (DMAC_REQ_MODE_SOFT == req) + { + /* DMA transfer Request by software */ + RZA_IO_RegWrite_32(&DMAC3.CHCTRL_n, + 1, + DMAC3_CHCTRL_n_STG_SHIFT, + DMAC3_CHCTRL_n_STG); + } + + ret = 0; + } + else + { + ret = -1; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC3_Close +* Description : Aborts DMAC channel 3 transfer. Returns the remaining transfer +* : byte count at the time of DMA transfer abort to the argument +* : *remain. +* Arguments : uint32_t * remain : Remaining transfer byte count when +* : : DMA transfer is aborted +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC3_Close (uint32_t * remain) +{ + + /* ==== Abort transfer ==== */ + RZA_IO_RegWrite_32(&DMAC3.CHCTRL_n, + 1, + DMAC3_CHCTRL_n_CLREN_SHIFT, + DMAC3_CHCTRL_n_CLREN); + + while (1 == RZA_IO_RegRead_32(&DMAC3.CHSTAT_n, + DMAC3_CHSTAT_n_TACT_SHIFT, + DMAC3_CHSTAT_n_TACT)) + { + /* Loop until transfer is aborted */ + } + + while (1 == RZA_IO_RegRead_32(&DMAC3.CHSTAT_n, + DMAC3_CHSTAT_n_EN_SHIFT, + DMAC3_CHSTAT_n_EN)) + { + /* Loop until 0 is set in EN before checking the remaining transfer byte count */ + } + /* ==== Obtain remaining transfer byte count ==== */ + *remain = DMAC3.CRTB_n; +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC3_Load_Set +* Description : Sets the transfer source address, transfer destination +* : address, and total transfer byte count respectively +* : specified by the argument src_addr, dst_addr, and count to +* : DMAC channel 3 as DMA transfer information. +* : Sets the register set selected by the CHCFG_n register +* : RSEL bit from the Next0 or Next1 register set. +* : This function should be called when DMA transfer of DMAC +* : channel 3 is aboted. +* Arguments : uint32_t src_addr : Transfer source address +* : uint32_t dst_addr : Transfer destination address +* : uint32_t count : Total transfer byte count +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC3_Load_Set (uint32_t src_addr, uint32_t dst_addr, uint32_t count) +{ + uint8_t reg_set; + + /* Obtain register set in use */ + reg_set = RZA_IO_RegRead_32(&DMAC3.CHSTAT_n, + DMAC3_CHSTAT_n_SR_SHIFT, + DMAC3_CHSTAT_n_SR); + + /* ==== Load ==== */ + if (0 == reg_set) + { + /* ---- Next0 Register Set ---- */ + DMAC3.N0SA_n = src_addr; /* Start address of transfer source */ + DMAC3.N0DA_n = dst_addr; /* Start address of transfer destination */ + DMAC3.N0TB_n = count; /* Total transfer byte count */ + } + else + { + /* ---- Next1 Register Set ---- */ + DMAC3.N1SA_n = src_addr; /* Start address of transfer source */ + DMAC3.N1DA_n = dst_addr; /* Start address of transfer destination */ + DMAC3.N1TB_n = count; /* Total transfer byte count */ + } +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC4_PeriReqInit +* Description : Sets the register mode for DMA mode and the on-chip peripheral +* : module request for transfer request for DMAC channel 4. +* : Executes DMAC initial setting using the DMA information +* : specified by the argument *trans_info and the enabled/disabled +* : continuous transfer specified by the argument continuation. +* : Registers DMAC channel 4 interrupt handler function and sets +* : the interrupt priority level. Then enables transfer completion +* : interrupt. +* Arguments : dmac_transinfo_t * trans_info : Setting information to DMAC +* : : register +* : uint32_t dmamode : DMA mode (only for DMAC_MODE_REGISTER) +* : uint32_t continuation : Set continuous transfer to be valid +* : : after DMA transfer has been completed +* : DMAC_SAMPLE_CONTINUATION : Execute continuous transfer +* : DMAC_SAMPLE_SINGLE : Do not execute continuous +* : : transfer +* : uint32_t request_factor : Factor for on-chip peripheral module +* : : request +* : DMAC_REQ_OSTM0TINT : OSTM_0 compare match +* : DMAC_REQ_OSTM1TINT : OSTM_1 compare match +* : DMAC_REQ_TGI0A : MTU2_0 input capture/compare match +* : : +* : uint32_t req_direction : Setting value of CHCFG_n register +* : : REQD bit +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC4_PeriReqInit (const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction) +{ + /* ==== Register mode ==== */ + if (DMAC_MODE_REGISTER == dmamode) + { + /* ==== Next0 register set ==== */ + DMAC4.N0SA_n = trans_info->src_addr; /* Start address of transfer source */ + DMAC4.N0DA_n = trans_info->dst_addr; /* Start address of transfer destination */ + DMAC4.N0TB_n = trans_info->count; /* Total transfer byte count */ + + /* DAD : Transfer destination address counting direction */ + /* SAD : Transfer source address counting direction */ + /* DDS : Transfer destination transfer size */ + /* SDS : Transfer source transfer size */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + trans_info->daddr_dir, + DMAC4_CHCFG_n_DAD_SHIFT, + DMAC4_CHCFG_n_DAD); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + trans_info->saddr_dir, + DMAC4_CHCFG_n_SAD_SHIFT, + DMAC4_CHCFG_n_SAD); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + trans_info->dst_size, + DMAC4_CHCFG_n_DDS_SHIFT, + DMAC4_CHCFG_n_DDS); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + trans_info->src_size, + DMAC4_CHCFG_n_SDS_SHIFT, + DMAC4_CHCFG_n_SDS); + + /* DMS : Register mode */ + /* RSEL : Select Next0 register set */ + /* SBE : No discharge of buffer data when aborted */ + /* DEM : No DMA interrupt mask */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_DMS_SHIFT, + DMAC4_CHCFG_n_DMS); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_RSEL_SHIFT, + DMAC4_CHCFG_n_RSEL); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_SBE_SHIFT, + DMAC4_CHCFG_n_SBE); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_DEM_SHIFT, + DMAC4_CHCFG_n_DEM); + + /* ---- Continuous transfer ---- */ + if (DMAC_SAMPLE_CONTINUATION == continuation) + { + /* REN : Execute continuous transfer */ + /* RSW : Change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 1, + DMAC4_CHCFG_n_REN_SHIFT, + DMAC4_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 1, + DMAC4_CHCFG_n_RSW_SHIFT, + DMAC4_CHCFG_n_RSW); + } + /* ---- Single transfer ---- */ + else + { + /* REN : Do not execute continuous transfer */ + /* RSW : Do not change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_REN_SHIFT, + DMAC4_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_RSW_SHIFT, + DMAC4_CHCFG_n_RSW); + } + + /* TM : Single transfer */ + /* SEL : Channel setting */ + /* HIEN, LOEN : On-chip peripheral module request */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_TM_SHIFT, + DMAC4_CHCFG_n_TM); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 4, + DMAC4_CHCFG_n_SEL_SHIFT, + DMAC4_CHCFG_n_SEL); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 1, + DMAC4_CHCFG_n_HIEN_SHIFT, + DMAC4_CHCFG_n_HIEN); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_LOEN_SHIFT, + DMAC4_CHCFG_n_LOEN); + + /* ---- Set factor by specified on-chip peripheral module request ---- */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_AM], + DMAC4_CHCFG_n_AM_SHIFT, + DMAC4_CHCFG_n_AM); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_LVL], + DMAC4_CHCFG_n_LVL_SHIFT, + DMAC4_CHCFG_n_LVL); + if (usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD] != DMAC_INDEFINE) + { + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD], + DMAC4_CHCFG_n_REQD_SHIFT, + DMAC4_CHCFG_n_REQD); + } + else + { + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + req_direction, + DMAC4_CHCFG_n_REQD_SHIFT, + DMAC4_CHCFG_n_REQD); + } + RZA_IO_RegWrite_32(&DMAC45.DMARS, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_RID], + DMAC45_DMARS_CH4_RID_SHIFT, + DMAC45_DMARS_CH4_RID); + RZA_IO_RegWrite_32(&DMAC45.DMARS, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_MID], + DMAC45_DMARS_CH4_MID_SHIFT, + DMAC45_DMARS_CH4_MID); + + /* PR : Round robin mode */ + RZA_IO_RegWrite_32(&DMAC07.DCTRL_0_7, + 1, + DMAC07_DCTRL_0_7_PR_SHIFT, + DMAC07_DCTRL_0_7_PR); + } +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC4_Open +* Description : Enables DMAC channel 4 transfer. +* Arguments : uint32_t req : DMAC request mode +* Return Value : 0 : Succeeded in enabling DMA transfer +* : -1 : Failed to enable DMA transfer (due to DMA operation) +*******************************************************************************/ +int32_t usb1_host_DMAC4_Open (uint32_t req) +{ + int32_t ret; + volatile uint8_t dummy; + + /* Transferable? */ + if ((0 == RZA_IO_RegRead_32(&DMAC4.CHSTAT_n, + DMAC4_CHSTAT_n_EN_SHIFT, + DMAC4_CHSTAT_n_EN)) && + (0 == RZA_IO_RegRead_32(&DMAC4.CHSTAT_n, + DMAC4_CHSTAT_n_TACT_SHIFT, + DMAC4_CHSTAT_n_TACT))) + { + /* Clear Channel Status Register */ + RZA_IO_RegWrite_32(&DMAC4.CHCTRL_n, + 1, + DMAC4_CHCTRL_n_SWRST_SHIFT, + DMAC4_CHCTRL_n_SWRST); + dummy = RZA_IO_RegRead_32(&DMAC4.CHCTRL_n, + DMAC4_CHCTRL_n_SWRST_SHIFT, + DMAC4_CHCTRL_n_SWRST); + /* Enable DMA transfer */ + RZA_IO_RegWrite_32(&DMAC4.CHCTRL_n, + 1, + DMAC4_CHCTRL_n_SETEN_SHIFT, + DMAC4_CHCTRL_n_SETEN); + + /* ---- Request by software ---- */ + if (DMAC_REQ_MODE_SOFT == req) + { + /* DMA transfer Request by software */ + RZA_IO_RegWrite_32(&DMAC4.CHCTRL_n, + 1, + DMAC4_CHCTRL_n_STG_SHIFT, + DMAC4_CHCTRL_n_STG); + } + + ret = 0; + } + else + { + ret = -1; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC4_Close +* Description : Aborts DMAC channel 4 transfer. Returns the remaining transfer +* : byte count at the time of DMA transfer abort to the argument +* : *remain. +* Arguments : uint32_t * remain : Remaining transfer byte count when +* : : DMA transfer is aborted +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC4_Close (uint32_t * remain) +{ + + /* ==== Abort transfer ==== */ + RZA_IO_RegWrite_32(&DMAC4.CHCTRL_n, + 1, + DMAC4_CHCTRL_n_CLREN_SHIFT, + DMAC4_CHCTRL_n_CLREN); + + while (1 == RZA_IO_RegRead_32(&DMAC4.CHSTAT_n, + DMAC4_CHSTAT_n_TACT_SHIFT, + DMAC4_CHSTAT_n_TACT)) + { + /* Loop until transfer is aborted */ + } + + while (1 == RZA_IO_RegRead_32(&DMAC4.CHSTAT_n, + DMAC4_CHSTAT_n_EN_SHIFT, + DMAC4_CHSTAT_n_EN)) + { + /* Loop until 0 is set in EN before checking the remaining transfer byte count */ + } + /* ==== Obtain remaining transfer byte count ==== */ + *remain = DMAC4.CRTB_n; +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC4_Load_Set +* Description : Sets the transfer source address, transfer destination +* : address, and total transfer byte count respectively +* : specified by the argument src_addr, dst_addr, and count to +* : DMAC channel 4 as DMA transfer information. +* : Sets the register set selected by the CHCFG_n register +* : RSEL bit from the Next0 or Next1 register set. +* : This function should be called when DMA transfer of DMAC +* : channel 4 is aboted. +* Arguments : uint32_t src_addr : Transfer source address +* : uint32_t dst_addr : Transfer destination address +* : uint32_t count : Total transfer byte count +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC4_Load_Set (uint32_t src_addr, uint32_t dst_addr, uint32_t count) +{ + uint8_t reg_set; + + /* Obtain register set in use */ + reg_set = RZA_IO_RegRead_32(&DMAC4.CHSTAT_n, + DMAC4_CHSTAT_n_SR_SHIFT, + DMAC4_CHSTAT_n_SR); + + /* ==== Load ==== */ + if (0 == reg_set) + { + /* ---- Next0 Register Set ---- */ + DMAC4.N0SA_n = src_addr; /* Start address of transfer source */ + DMAC4.N0DA_n = dst_addr; /* Start address of transfer destination */ + DMAC4.N0TB_n = count; /* Total transfer byte count */ + } + else + { + /* ---- Next1 Register Set ---- */ + DMAC4.N1SA_n = src_addr; /* Start address of transfer source */ + DMAC4.N1DA_n = dst_addr; /* Start address of transfer destination */ + DMAC4.N1TB_n = count; /* Total transfer byte count */ + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb1/src/userdef/usb1_host_userdef.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,778 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_userdef.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include <stdio.h> +#include "cmsis_os.h" +#include "r_typedefs.h" +#include "iodefine.h" +#include "devdrv_usb_host_api.h" +#include "usb1_host.h" +#include "MBRZA1H.h" /* INTC Driver Header */ +#include "usb1_host_dmacdrv.h" +#include "ohci_wrapp_RZ_A1_local.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define DUMMY_ACCESS OSTM0CNT + +/* #define CACHE_WRITEBACK */ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +extern int32_t io_cwb(unsigned long start, unsigned long end); + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb1_host_enable_dmac0(uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc); +static void usb1_host_enable_dmac1(uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc); +static void Userdef_USB_usb1_host_delay_10us_2(void); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_d0fifo_dmaintid +* Description : get D0FIFO DMA Interrupt ID +* Arguments : none +* Return Value : D0FIFO DMA Interrupt ID +*******************************************************************************/ +uint16_t Userdef_USB_usb1_host_d0fifo_dmaintid (void) +{ +#if(1) /* ohci_wrapp */ + return 0xFFFF; +#else + return DMAINT1_IRQn; +#endif +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_d1fifo_dmaintid +* Description : get D1FIFO DMA Interrupt ID +* Arguments : none +* Return Value : D1FIFO DMA Interrupt ID +*******************************************************************************/ +uint16_t Userdef_USB_usb1_host_d1fifo_dmaintid (void) +{ +#if(1) /* ohci_wrapp */ + return 0xFFFF; +#else + return DMAINT2_IRQn; +#endif +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_attach +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_attach (void) +{ +// printf("\n"); +// printf("channel 1 attach device\n"); +// printf("\n"); + ohciwrapp_loc_Connect(1); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_detach +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_detach (void) +{ +// printf("\n"); +// printf("channel 1 detach device\n"); +// printf("\n"); + ohciwrapp_loc_Connect(0); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_delay_1ms +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_delay_1ms (void) +{ + osDelay(1); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_delay_xms +* Description : Wait for the software in the period of time specified by the +* : argument. +* : Alter this function according to the user's system. +* Arguments : uint32_t msec ; Wait Time (msec) +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_delay_xms (uint32_t msec) +{ + osDelay(msec); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_delay_10us +* Description : Waits for software for the period specified by the argument. +* : Alter this function according to the user's system. +* Arguments : uint32_t usec ; Wait Time(x 10usec) +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_delay_10us (uint32_t usec) +{ + volatile int i; + + /* Wait 10us (Please change for your MCU) */ + for (i = 0; i < usec; ++i) + { + Userdef_USB_usb1_host_delay_10us_2(); + } +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_delay_10us_2 +* Description : Waits for software for the period specified by the argument. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +static void Userdef_USB_usb1_host_delay_10us_2 (void) +{ + volatile int i; + volatile unsigned long tmp; + + /* Wait 1us (Please change for your MCU) */ + for (i = 0; i < 14; ++i) + { + tmp = DUMMY_ACCESS; + } +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_delay_500ns +* Description : Wait for software for 500ns. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_delay_500ns (void) +{ + volatile int i; + volatile unsigned long tmp; + + /* Wait 500ns (Please change for your MCU) */ + /* Wait 500ns I clock 266MHz */ + tmp = DUMMY_ACCESS; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_start_dma +* Description : Enables DMA transfer on the information specified by the argument. +* : Set DMAC register by this function to enable DMA transfer. +* : After executing this function, USB module is set to start DMA +* : transfer. DMA transfer should not wait for DMA transfer complete. +* Arguments : USB_HOST_DMA_t *dma : DMA parameter +* : typedef struct{ +* : uint32_t fifo; FIFO for using +* : uint32_t buffer; Start address of transfer source/destination +* : uint32_t bytes; Transfer size(Byte) +* : uint32_t dir; Transfer direction(0:Buffer->FIFO, 1:FIFO->Buffer) +* : uint32_t size; DMA transfer size +* : } USB_HOST_DMA_t; +* : uint16_t dfacc ; 0 : cycle steal mode +* : 1 : 16byte continuous mode +* : 2 : 32byte continuous mode +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_start_dma (USB_HOST_DMA_t * dma, uint16_t dfacc) +{ + uint32_t trncount; + uint32_t src; + uint32_t dst; + uint32_t size; + uint32_t dir; +#ifdef CACHE_WRITEBACK + uint32_t ptr; +#endif + + trncount = dma->bytes; + dir = dma->dir; + + if (dir == USB_HOST_FIFO2BUF) + { + /* DxFIFO determination */ + dst = dma->buffer; +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB201.D1FIFO.UINT32); + } + size = dma->size; + + if (size == 0) + { + src += 3; /* byte access */ + } + else if (size == 1) + { + src += 2; /* short access */ + } + else + { + /* Do Nothing */ + } +#else + size = dma->size; + + if (size == 2) + { + /* 32bit access */ + if (dfacc == 2) + { + /* 32byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFOB0); + } + else + { + src = (uint32_t)(&USB201.D1FIFOB0); + } + } + else if (dfacc == 1) + { + /* 16byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFOB0); + } + else + { + src = (uint32_t)(&USB201.D1FIFOB0); + } + } + else + { + /* normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB201.D1FIFO.UINT32); + } + } + } + else if (size == 1) + { + /* 16bit access */ + dfacc = 0; /* force normal access */ + + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB201.D1FIFO.UINT32); + } + src += 2; /* short access */ + } + else + { + /* 8bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB201.D1FIFO.UINT32); + } + src += 3; /* byte access */ + } +#endif + } + else + { + /* DxFIFO determination */ + src = dma->buffer; +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB201.D1FIFO.UINT32); + } + size = dma->size; + + if (size == 0) + { + dst += 3; /* byte access */ + } + else if (size == 1) + { + dst += 2; /* short access */ + } + else + { + /* Do Nothing */ + } +#else + size = dma->size; + if (size == 2) + { + /* 32bit access */ + if (dfacc == 2) + { + /* 32byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFOB0); + } + else + { + dst = (uint32_t)(&USB201.D1FIFOB0); + } + } + else if (dfacc == 1) + { + /* 16byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFOB0); + } + else + { + dst = (uint32_t)(&USB201.D1FIFOB0); + } + } + else + { + /* normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB201.D1FIFO.UINT32); + } + } + } + else if (size == 1) + { + /* 16bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB201.D1FIFO.UINT32); + } + dst += 2; /* short access */ + } + else + { + /* 8bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB201.D1FIFO.UINT32); + } + dst += 3; /* byte access */ + } +#endif + } + +#ifdef CACHE_WRITEBACK + ptr = (uint32_t)dma->buffer; + if ((ptr & 0x20000000ul) == 0) + { + io_cwb((uint32_t)ptr,(uint32_t)(ptr)+trncount); + } +#endif + + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + usb1_host_enable_dmac0(src, dst, trncount, size, dir, dma->fifo, dfacc); + } + else + { + usb1_host_enable_dmac1(src, dst, trncount, size, dir, dma->fifo, dfacc); + } +} + +/******************************************************************************* +* Function Name: usb1_host_enable_dmac0 +* Description : Enables DMA transfer on the information specified by the argument. +* Arguments : uint32_t src : src address +* : uint32_t dst : dst address +* : uint32_t count : transfer byte +* : uint32_t size : transfer size +* : uint32_t dir : direction +* : uint32_t fifo : FIFO(D0FIFO or D1FIFO) +* : uint16_t dfacc : 0 : normal access +* : : 1 : 16byte access +* : : 2 : 32byte access +* Return Value : none +*******************************************************************************/ +static void usb1_host_enable_dmac0 (uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc) +{ + dmac_transinfo_t trans_info; + uint32_t request_factor = 0; + int32_t ret; + + /* ==== Variable setting for DMAC initialization ==== */ + trans_info.src_addr = (uint32_t)src; /* Start address of transfer source */ + trans_info.dst_addr = (uint32_t)dst; /* Start address of transfer destination */ + trans_info.count = (uint32_t)count; /* Total byte count to be transferred */ +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } +#else + if (dfacc == 2) + { + /* 32byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_256; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_256; /* Transfer destination transfer size */ + } + else if (dfacc == 1) + { + /* 16byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_128; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_128; /* Transfer destination transfer size */ + } + else + { + /* normal access */ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } + } +#endif + + if (dir == USB_HOST_FIFO2BUF) + { + request_factor = DMAC_REQ_USB1_DMA0_RX; /* USB_0 channel 0 receive FIFO full */ + trans_info.saddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer destination address */ + } + else if (dir == USB_HOST_BUF2FIFO) + { + request_factor = DMAC_REQ_USB1_DMA0_TX; /* USB_0 channel 0 receive FIFO empty */ + trans_info.saddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer destination address */ + } + else + { + /* Do Nothing */ + } + + /* ==== DMAC initialization ==== */ + usb1_host_DMAC3_PeriReqInit((const dmac_transinfo_t *)&trans_info, + DMAC_MODE_REGISTER, + DMAC_SAMPLE_SINGLE, + request_factor, + 0); /* Don't care DMAC_REQ_REQD is setting in usb1_host_DMAC3_PeriReqInit() */ + + /* ==== DMAC startup ==== */ + ret = usb1_host_DMAC3_Open(DMAC_REQ_MODE_PERI); + + if (ret != 0) + { +// printf("DMAC3 Open error!!\n"); + } + + return; +} + +/******************************************************************************* +* Function Name: usb1_host_enable_dmac1 +* Description : Enables DMA transfer on the information specified by the argument. +* Arguments : uint32_t src : src address +* : uint32_t dst : dst address +* : uint32_t count : transfer byte +* : uint32_t size : transfer size +* : uint32_t dir : direction +* : uint32_t fifo : FIFO(D0FIFO or D1FIFO) +* : uint16_t dfacc : 0 : normal access +* : : 1 : 16byte access +* : : 2 : 32byte access +* Return Value : none +*******************************************************************************/ +static void usb1_host_enable_dmac1 (uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc) +{ + dmac_transinfo_t trans_info; + uint32_t request_factor = 0; + int32_t ret; + + /* ==== Variable setting for DMAC initialization ==== */ + trans_info.src_addr = (uint32_t)src; /* Start address of transfer source */ + trans_info.dst_addr = (uint32_t)dst; /* Start address of transfer destination */ + trans_info.count = (uint32_t)count; /* Total byte count to be transferred */ +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } +#else + if (dfacc == 2) + { + /* 32byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_256; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_256; /* Transfer destination transfer size */ + } + else if (dfacc == 1) + { + /* 16byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_128; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_128; /* Transfer destination transfer size */ + } + else + { + /* normal access */ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } + } +#endif + + if (dir == USB_HOST_FIFO2BUF) + { + request_factor =DMAC_REQ_USB1_DMA1_RX; /* USB_0 channel 0 receive FIFO full */ + trans_info.saddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer destination address */ + } + else if (dir == USB_HOST_BUF2FIFO) + { + request_factor =DMAC_REQ_USB1_DMA1_TX; /* USB_0 channel 0 receive FIFO empty */ + trans_info.saddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer destination address */ + } + else + { + /* Do Nothing */ + } + + /* ==== DMAC initialization ==== */ + usb1_host_DMAC4_PeriReqInit((const dmac_transinfo_t *)&trans_info, + DMAC_MODE_REGISTER, + DMAC_SAMPLE_SINGLE, + request_factor, + 0); /* Don't care DMAC_REQ_REQD is setting in usb1_host_DMAC4_PeriReqInit() */ + + /* ==== DMAC startup ==== */ + ret = usb1_host_DMAC4_Open(DMAC_REQ_MODE_PERI); + + if (ret != 0) + { +// printf("DMAC4 Open error!!\n"); + } + + return; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_stop_dma0 +* Description : Disables DMA transfer. +* Arguments : none +* Return Value : uint32_t return Transfer Counter register(DMATCRn) value +* : regarding to the bus width. +* Notice : This function should be executed to DMAC executed at the time +* : of specification of D0_FIF0_DMA in dma->fifo. +*******************************************************************************/ +uint32_t Userdef_USB_usb1_host_stop_dma0 (void) +{ + uint32_t remain; + + /* ==== DMAC release ==== */ + usb1_host_DMAC3_Close(&remain); + + return remain; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_stop_dma1 +* Description : Disables DMA transfer. +* : This function should be executed to DMAC executed at the time +* : of specification of D1_FIF0_DMA in dma->fifo. +* Arguments : none +* Return Value : uint32_t return Transfer Counter register(DMATCRn) value +* : regarding to the bus width. +*******************************************************************************/ +uint32_t Userdef_USB_usb1_host_stop_dma1 (void) +{ + uint32_t remain; + + /* ==== DMAC release ==== */ + usb1_host_DMAC4_Close(&remain); + + return remain; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_notice +* Description : Notice of USER +* Arguments : const char *format +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_notice (const char * format) +{ +// printf(format); + + return; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_user_rdy +* Description : This function notify a user and wait for trigger +* Arguments : const char *format +* : uint16_t data +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_user_rdy (const char * format, uint16_t data) +{ +// printf(format, data); + getchar(); + + return; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_RZ_A1H/usb_host_setting.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,100 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2014 - 2015 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ + +#ifndef USB_HOST_SETTING_H +#define USB_HOST_SETTING_H + +#ifdef __cplusplus +extern "C" { +#endif + +#define USB_HOST_CH 0 +#define USB_HOST_HISPEED 1 + +#define INT_TRANS_MAX_NUM 4 /* min:1 max:4 */ +#define ISO_TRANS_MAX_NUM 0 /* min:0 max:2 */ + +#if (USB_HOST_CH == 0) +#include "usb0_host.h" +#define USB20X USB200 +#define USBIXUSBIX USBI0_IRQn +#define g_usbx_host_SupportUsbDeviceSpeed g_usb0_host_SupportUsbDeviceSpeed +#define g_usbx_host_UsbDeviceSpeed g_usb0_host_UsbDeviceSpeed +#define g_usbx_host_CmdStage g_usb0_host_CmdStage +#define g_usbx_host_pipe_status g_usb0_host_pipe_status +#define g_usbx_host_data_pointer g_usb0_host_data_pointer +#define g_usbx_host_data_count g_usb0_host_data_count +#define usbx_api_host_init usb0_api_host_init +#define usbx_host_UsbBusReset usb0_host_UsbBusReset +#define usbx_host_get_devadd usb0_host_get_devadd +#define usbx_host_set_devadd usb0_host_set_devadd +#define usbx_host_SetupStage usb0_host_SetupStage +#define usbx_host_CtrlWriteStart usb0_host_CtrlWriteStart +#define usbx_host_CtrlReadStart usb0_host_CtrlReadStart +#define usbx_api_host_SetEndpointTable usb0_api_host_SetEndpointTable +#define usbx_host_start_send_transfer usb0_host_start_send_transfer +#define usbx_host_start_receive_transfer usb0_host_start_receive_transfer +#define usbx_host_stop_transfer usb0_host_stop_transfer +#define usbx_host_set_sqclr usb0_host_set_sqclr +#define usbx_host_set_sqset usb0_host_set_sqset +#define usbx_host_CheckAttach usb0_host_CheckAttach +#define usbx_host_UsbDetach usb0_host_UsbDetach +#define usbx_host_UsbAttach usb0_host_UsbAttach +#define usbx_host_init_pipe_status usb0_host_init_pipe_status +#define usbx_host_get_sqmon usb0_host_get_sqmon +#else +#include "usb1_host.h" +#define USB20X USB201 +#define USBIXUSBIX USBI1_IRQn +#define g_usbx_host_SupportUsbDeviceSpeed g_usb1_host_SupportUsbDeviceSpeed +#define g_usbx_host_UsbDeviceSpeed g_usb1_host_UsbDeviceSpeed +#define g_usbx_host_CmdStage g_usb1_host_CmdStage +#define g_usbx_host_pipe_status g_usb1_host_pipe_status +#define g_usbx_host_data_pointer g_usb1_host_data_pointer +#define g_usbx_host_data_count g_usb1_host_data_count +#define usbx_api_host_init usb1_api_host_init +#define usbx_host_UsbBusReset usb1_host_UsbBusReset +#define usbx_host_get_devadd usb1_host_get_devadd +#define usbx_host_set_devadd usb1_host_set_devadd +#define usbx_host_SetupStage usb1_host_SetupStage +#define usbx_host_CtrlWriteStart usb1_host_CtrlWriteStart +#define usbx_host_CtrlReadStart usb1_host_CtrlReadStart +#define usbx_api_host_SetEndpointTable usb1_api_host_SetEndpointTable +#define usbx_host_start_send_transfer usb1_host_start_send_transfer +#define usbx_host_start_receive_transfer usb1_host_start_receive_transfer +#define usbx_host_stop_transfer usb1_host_stop_transfer +#define usbx_host_set_sqclr usb1_host_set_sqclr +#define usbx_host_set_sqset usb1_host_set_sqset +#define usbx_host_CheckAttach usb1_host_CheckAttach +#define usbx_host_UsbDetach usb1_host_UsbDetach +#define usbx_host_UsbAttach usb1_host_UsbAttach +#define usbx_host_init_pipe_status usb1_host_init_pipe_status +#define usbx_host_get_sqmon usb1_host_get_sqmon +#endif + + +#ifdef __cplusplus +} +#endif + +#endif /* USB_HOST_SETTING_H */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/inc/devdrv_usb_host_api.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,329 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : devdrv_usb_host_api.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB_HOST_API_H +#define USB_HOST_API_H + +#include "r_typedefs.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define USB_HOST_PORTNUM (2) + +#define USB_HOST_ELT_INTERRUPT_LEVEL (9) + +#define USBHCLOCK_X1_48MHZ (0x0000u) /* USB_X1_48MHz */ +#define USBHCLOCK_EXTAL_12MHZ (0x0004u) /* EXTAL_12MHz */ + +#define USB_HOST_MAX_DEVICE (10) + +#define USB_HOST_ON (1) +#define USB_HOST_OFF (0) +#define USB_HOST_YES (1) +#define USB_HOST_NO (0) + +#define USB_HOST_NON_SPEED (0) +#define USB_HOST_LOW_SPEED (1) +#define USB_HOST_FULL_SPEED (2) +#define USB_HOST_HIGH_SPEED (3) + +/* DEVDRV_SUCCESS(0) & DEVDRV_ERROR(-1) is dev_drv.h */ +#define DEVDRV_USBH_STALL (-2) +#define DEVDRV_USBH_TIMEOUT (-3) +#define DEVDRV_USBH_NAK_TIMEOUT (-4) +#define DEVDRV_USBH_DETACH_ERR (-5) +#define DEVDRV_USBH_SETUP_ERR (-6) +#define DEVDRV_USBH_CTRL_COM_ERR (-7) +#define DEVDRV_USBH_COM_ERR (-8) +#define DEVDRV_USBH_DEV_ADDR_ERR (-9) + +#define USB_HOST_ATTACH (1) +#define USB_HOST_DETACH (0) + +#define USB_HOST_MAX_PIPE_NO (9u) +#define USB_HOST_PIPE0 (0) +#define USB_HOST_PIPE1 (1) +#define USB_HOST_PIPE2 (2) +#define USB_HOST_PIPE3 (3) +#define USB_HOST_PIPE4 (4) +#define USB_HOST_PIPE5 (5) +#define USB_HOST_PIPE6 (6) +#define USB_HOST_PIPE7 (7) +#define USB_HOST_PIPE8 (8) +#define USB_HOST_PIPE9 (9) + +#define USB_HOST_ISO (0xc000u) +#define USB_HOST_INTERRUPT (0x8000u) +#define USB_HOST_BULK (0x4000u) + +#define USB_HOST_PIPE_IDLE (0x00) +#define USB_HOST_PIPE_WAIT (0x01) +#define USB_HOST_PIPE_DONE (0x02) +#define USB_HOST_PIPE_NORES (0x03) +#define USB_HOST_PIPE_STALL (0x04) +#define USB_HOST_PIPE_ERROR (0x05) + +#define USB_HOST_NONE (0x0000u) +#define USB_HOST_BFREFIELD (0x0400u) +#define USB_HOST_BFREON (0x0400u) +#define USB_HOST_BFREOFF (0x0000u) +#define USB_HOST_DBLBFIELD (0x0200u) +#define USB_HOST_DBLBON (0x0200u) +#define USB_HOST_DBLBOFF (0x0000u) +#define USB_HOST_CNTMDFIELD (0x0100u) +#define USB_HOST_CNTMDON (0x0100u) +#define USB_HOST_CNTMDOFF (0x0000u) +#define USB_HOST_SHTNAKON (0x0080u) +#define USB_HOST_SHTNAKOFF (0x0000u) +#define USB_HOST_DIRFIELD (0x0010u) +#define USB_HOST_DIR_H_OUT (0x0010u) +#define USB_HOST_DIR_H_IN (0x0000u) +#define USB_HOST_EPNUMFIELD (0x000fu) + +#define USB_HOST_CUSE (0) +#define USB_HOST_D0USE (1) +#define USB_HOST_D0DMA (2) +#define USB_HOST_D1USE (3) +#define USB_HOST_D1DMA (4) + +#define USB_HOST_CFIFO_USE (0x0000) +#define USB_HOST_D0FIFO_USE (0x1000) +#define USB_HOST_D1FIFO_USE (0x2000) +#define USB_HOST_D0FIFO_DMA (0x5000) +#define USB_HOST_D1FIFO_DMA (0x6000) + +#define USB_HOST_BUF2FIFO (0) +#define USB_HOST_FIFO2BUF (1) + +#define USB_HOST_DRV_DETACHED (0x0000) +#define USB_HOST_DRV_ATTACHED (0x0001) +#define USB_HOST_DRV_GET_DEVICE_DESC_64 (0x0002) +#define USB_HOST_DRV_POWERED (0x0003) +#define USB_HOST_DRV_DEFAULT (0x0004) +#define USB_HOST_DRV_SET_ADDRESS (0x0005) +#define USB_HOST_DRV_ADDRESSED (0x0006) +#define USB_HOST_DRV_GET_DEVICE_DESC_18 (0x0007) +#define USB_HOST_DRV_GET_CONGIG_DESC_9 (0x0008) +#define USB_HOST_DRV_GET_CONGIG_DESC (0x0009) +#define USB_HOST_DRV_SET_CONFIG (0x000a) +#define USB_HOST_DRV_CONFIGURED (0x000b) +#define USB_HOST_DRV_SUSPEND (0x1000) +#define USB_HOST_DRV_NORES (0x0100) +#define USB_HOST_DRV_STALL (0x0200) + +#define USB_HOST_TESTMODE_FORCE (0x000du) +#define USB_HOST_TESTMODE_TESTPACKET (0x000cu) +#define USB_HOST_TESTMODE_SE0_NAK (0x000bu) +#define USB_HOST_TESTMODE_K (0x000au) +#define USB_HOST_TESTMODE_J (0x0009u) +#define USB_HOST_TESTMODE_NORMAL (0x0000u) + +#define USB_HOST_DT_DEVICE (0x01) +#define USB_HOST_DT_CONFIGURATION (0x02) +#define USB_HOST_DT_STRING (0x03) +#define USB_HOST_DT_INTERFACE (0x04) +#define USB_HOST_DT_ENDPOINT (0x05) +#define USB_HOST_DT_DEVICE_QUALIFIER (0x06) +#define USB_HOST_DT_OTHER_SPEED_CONFIGURATION (0x07) +#define USB_HOST_DT_INTERFACE_POWER (0x08) + +#define USB_HOST_IF_CLS_NOT (0x00) +#define USB_HOST_IF_CLS_AUDIO (0x01) +#define USB_HOST_IF_CLS_CDC_CTRL (0x02) +#define USB_HOST_IF_CLS_HID (0x03) +#define USB_HOST_IF_CLS_PHYSICAL (0x05) +#define USB_HOST_IF_CLS_IMAGE (0x06) +#define USB_HOST_IF_CLS_PRINTER (0x07) +#define USB_HOST_IF_CLS_MASS (0x08) +#define USB_HOST_IF_CLS_HUB (0x09) +#define USB_HOST_IF_CLS_CDC_DATA (0x0a) +#define USB_HOST_IF_CLS_CRAD (0x0b) +#define USB_HOST_IF_CLS_CONTENT (0x0d) +#define USB_HOST_IF_CLS_VIDEO (0x0e) +#define USB_HOST_IF_CLS_DIAG (0xdc) +#define USB_HOST_IF_CLS_WIRELESS (0xe0) +#define USB_HOST_IF_CLS_APL (0xfe) +#define USB_HOST_IF_CLS_VENDOR (0xff) +#define USB_HOST_IF_CLS_HELE (0xaa) + +#define USB_HOST_EP_DIR_MASK (0x80) +#define USB_HOST_EP_OUT (0x00) +#define USB_HOST_EP_IN (0x80) +#define USB_HOST_EP_TYPE (0x03) +#define USB_HOST_EP_CNTRL (0x00) +#define USB_HOST_EP_ISO (0x01) +#define USB_HOST_EP_BULK (0x02) +#define USB_HOST_EP_INT (0x03) +#define USB_HOST_EP_NUM_MASK (0x0f) + +#define USB_HOST_PIPE_IN (0) +#define USB_HOST_PIPE_OUT (1) + +#define USB_END_POINT_ERROR (0xffff) + +#define USB_HOST_REQ_GET_STATUS (0x0000) +#define USB_HOST_REQ_CLEAR_FEATURE (0x0100) +#define USB_HOST_REQ_RESERVED2 (0x0200) +#define USB_HOST_REQ_SET_FEATURE (0x0300) +#define USB_HOST_REQ_RESERVED4 (0x0400) +#define USB_HOST_REQ_SET_ADDRESS (0x0500) +#define USB_HOST_REQ_GET_DESCRIPTOR (0x0600) +#define USB_HOST_REQ_SET_DESCRIPTOR (0x0700) +#define USB_HOST_REQ_GET_CONFIGURATION (0x0800) +#define USB_HOST_REQ_SET_CONFIGURATION (0x0900) +#define USB_HOST_REQ_GET_INTERFACE (0x0a00) +#define USB_HOST_REQ_SET_INTERFACE (0x0b00) +#define USB_HOST_REQ_SYNCH_FRAME (0x0c00) + +#define USB_HOST_REQTYPE_HOST_TO_DEVICE (0x0000) +#define USB_HOST_REQTYPE_DEVICE_TO_HOST (0x0080) +#define USB_HOST_REQTYPE_STANDARD (0x0020) +#define USB_HOST_REQTYPE_CLASS (0x0040) +#define USB_HOST_REQTYPE_VENDOR (0x0060) +#define USB_HOST_REQTYPE_DEVICE (0x0000) +#define USB_HOST_REQTYPE_INTERFACE (0x0001) +#define USB_HOST_REQTYPE_ENDPOINT (0x0002) +#define USB_HOST_REQTYPE_OTHER (0x0003) + +#define USB_HOST_DESCTYPE_DEVICE (0x0100) +#define USB_HOST_DESCTYPE_CONFIGURATION (0x0200) +#define USB_HOST_DESCTYPE_STRING (0x0300) +#define USB_HOST_DESCTYPE_INTERFACE (0x0400) +#define USB_HOST_DESCTYPE_ENDPOINT (0x0500) +#define USB_HOST_DESCTYPE_DEVICE_QUALIFIER (0x0600) +#define USB_HOST_DESCTYPE_OTHER_SPEED_CONFIGURATION (0x0700) +#define USB_HOST_DESCTYPE_INTERFACE_POWER (0x0800) + + +/******************************************************************************* +Variable Externs +*******************************************************************************/ +typedef struct +{ + uint16_t pipe_number; + uint16_t pipe_cfg; + uint16_t pipe_buf; + uint16_t pipe_max_pktsize; + uint16_t pipe_cycle; + uint16_t fifo_port; +} USB_HOST_CFG_PIPETBL_t; + +typedef struct +{ + uint32_t fifo; + uint32_t buffer; + uint32_t bytes; + uint32_t dir; + uint32_t size; +} USB_HOST_DMA_t; + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +uint16_t R_USB_api_host_init(uint16_t root, uint8_t int_level, uint16_t mode, uint16_t clockmode); +int32_t R_USB_api_host_enumeration(uint16_t root, uint16_t devadr); +int32_t R_USB_api_host_detach(uint16_t root); +int32_t R_USB_api_host_data_in(uint16_t root, uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t R_USB_api_host_data_in2(uint16_t root, uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf, uint32_t *bytes); +int32_t R_USB_api_host_data_out(uint16_t root, uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t R_USB_api_host_control_transfer(uint16_t root, uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len, uint8_t *Buf); +int32_t R_USB_api_host_set_endpoint(uint16_t root, uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t *configdescriptor); +int32_t R_USB_api_host_clear_endpoint(uint16_t root, USB_HOST_CFG_PIPETBL_t *user_table); +int32_t R_USB_api_host_clear_endpoint_pipe(uint16_t root, uint16_t pipe_sel, USB_HOST_CFG_PIPETBL_t *user_table); +uint16_t R_USB_api_host_SetEndpointTable(uint16_t root, uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t* Table); + +int32_t R_USB_api_host_GetDeviceDescriptor(uint16_t root, uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t R_USB_api_host_GetConfigDescriptor(uint16_t root, uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t R_USB_api_host_SetConfig(uint16_t root, uint16_t devadr, uint16_t confignum); +int32_t R_USB_api_host_SetInterface(uint16_t root, uint16_t devadr, uint16_t interface_alt, uint16_t interface_index); +int32_t R_USB_api_host_ClearStall(uint16_t root, uint16_t devadr, uint16_t ep_dir); +uint16_t R_USB_api_host_GetUsbDeviceState(uint16_t root); + +void R_USB_api_host_elt_clocksel(uint16_t clockmode); +void R_USB_api_host_elt_4_4(uint16_t root); +void R_USB_api_host_elt_4_5(uint16_t root); +void R_USB_api_host_elt_4_6(uint16_t root); +void R_USB_api_host_elt_4_7(uint16_t root); +void R_USB_api_host_elt_4_8(uint16_t root); +void R_USB_api_host_elt_4_9(uint16_t root); +void R_USB_api_host_elt_get_desc(uint16_t root); + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host_api.h" +#include "usb1_host_api.h" + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +#ifdef USB0_HOST_API_H +uint16_t Userdef_USB_usb0_host_d0fifo_dmaintid(void); +uint16_t Userdef_USB_usb0_host_d1fifo_dmaintid(void); +void Userdef_USB_usb0_host_attach(void); +void Userdef_USB_usb0_host_detach(void); +void Userdef_USB_usb0_host_delay_1ms(void); +void Userdef_USB_usb0_host_delay_xms(uint32_t msec); +void Userdef_USB_usb0_host_delay_10us(uint32_t usec); +void Userdef_USB_usb0_host_delay_500ns(void); +void Userdef_USB_usb0_host_start_dma(USB_HOST_DMA_t * dma, uint16_t dfacc); +uint32_t Userdef_USB_usb0_host_stop_dma0(void); +uint32_t Userdef_USB_usb0_host_stop_dma1(void); +void Userdef_USB_usb0_host_notice(const char * format); +void Userdef_USB_usb0_host_user_rdy(const char * format, uint16_t data); +#endif + +#ifdef USB1_HOST_API_H +uint16_t Userdef_USB_usb1_host_d0fifo_dmaintid(void); +uint16_t Userdef_USB_usb1_host_d1fifo_dmaintid(void); +void Userdef_USB_usb1_host_attach(void); +void Userdef_USB_usb1_host_detach(void); +void Userdef_USB_usb1_host_delay_1ms(void); +void Userdef_USB_usb1_host_delay_xms(uint32_t msec); +void Userdef_USB_usb1_host_delay_10us(uint32_t usec); +void Userdef_USB_usb1_host_delay_500ns(void); +void Userdef_USB_usb1_host_start_dma(USB_HOST_DMA_t * dma, uint16_t dfacc); +uint32_t Userdef_USB_usb1_host_stop_dma0(void); +uint32_t Userdef_USB_usb1_host_stop_dma1(void); +void Userdef_USB_usb1_host_notice(const char * format); +void Userdef_USB_usb1_host_user_rdy(const char * format, uint16_t data); +#endif + +#endif /* USB_HOST_API_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/inc/usb_host.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,201 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb_host.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB_HOST_H +#define USB_HOST_H + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "r_typedefs.h" +#include "iodefine.h" +#include "rza_io_regrw.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define USB_HOST_DEVICE_0 (0u) +#define USB_HOST_DEVICE_1 (1u) +#define USB_HOST_DEVICE_2 (2u) +#define USB_HOST_DEVICE_3 (3u) +#define USB_HOST_DEVICE_4 (4u) +#define USB_HOST_DEVICE_5 (5u) +#define USB_HOST_DEVICE_6 (6u) +#define USB_HOST_DEVICE_7 (7u) +#define USB_HOST_DEVICE_8 (8u) +#define USB_HOST_DEVICE_9 (9u) +#define USB_HOST_DEVICE_10 (10u) + +#define USB_HOST_ENDPOINT_DESC (0x05) + +#define USB_HOST_BITUPLLE (0x0002u) +#define USB_HOST_BITUCKSEL (0x0004u) +#define USB_HOST_BITBWAIT (0x003fu) + +#define USB_HOST_BUSWAIT_02 (0x0000u) +#define USB_HOST_BUSWAIT_03 (0x0001u) +#define USB_HOST_BUSWAIT_04 (0x0002u) +#define USB_HOST_BUSWAIT_05 (0x0003u) +#define USB_HOST_BUSWAIT_06 (0x0004u) +#define USB_HOST_BUSWAIT_07 (0x0005u) +#define USB_HOST_BUSWAIT_08 (0x0006u) +#define USB_HOST_BUSWAIT_09 (0x0007u) +#define USB_HOST_BUSWAIT_10 (0x0008u) +#define USB_HOST_BUSWAIT_11 (0x0009u) +#define USB_HOST_BUSWAIT_12 (0x000au) +#define USB_HOST_BUSWAIT_13 (0x000bu) +#define USB_HOST_BUSWAIT_14 (0x000cu) +#define USB_HOST_BUSWAIT_15 (0x000du) +#define USB_HOST_BUSWAIT_16 (0x000eu) +#define USB_HOST_BUSWAIT_17 (0x000fu) + +#define USB_HOST_FS_JSTS (0x0001u) +#define USB_HOST_LS_JSTS (0x0002u) + +#define USB_HOST_BITRST (0x0040u) +#define USB_HOST_BITRESUME (0x0020u) +#define USB_HOST_BITUACT (0x0010u) +#define USB_HOST_HSPROC (0x0004u) +#define USB_HOST_HSMODE (0x0003u) +#define USB_HOST_FSMODE (0x0002u) +#define USB_HOST_LSMODE (0x0001u) +#define USB_HOST_UNDECID (0x0000u) + +#define USB_HOST_BITRCNT (0x8000u) +#define USB_HOST_BITDREQE (0x1000u) +#define USB_HOST_BITMBW (0x0c00u) +#define USB_HOST_BITMBW_8 (0x0000u) +#define USB_HOST_BITMBW_16 (0x0400u) +#define USB_HOST_BITMBW_32 (0x0800u) +#define USB_HOST_BITBYTE_LITTLE (0x0000u) +#define USB_HOST_BITBYTE_BIG (0x0100u) +#define USB_HOST_BITISEL (0x0020u) +#define USB_HOST_BITCURPIPE (0x000fu) + +#define USB_HOST_CFIFO_READ (0x0000u) +#define USB_HOST_CFIFO_WRITE (0x0020u) + +#define USB_HOST_BITBVAL (0x8000u) +#define USB_HOST_BITBCLR (0x4000u) +#define USB_HOST_BITFRDY (0x2000u) +#define USB_HOST_BITDTLN (0x0fffu) + +#define USB_HOST_BITBEMPE (0x0400u) +#define USB_HOST_BITNRDYE (0x0200u) +#define USB_HOST_BITBRDYE (0x0100u) +#define USB_HOST_BITBEMP (0x0400u) +#define USB_HOST_BITNRDY (0x0200u) +#define USB_HOST_BITBRDY (0x0100u) + +#define USB_HOST_BITBCHGE (0x4000u) +#define USB_HOST_BITDTCHE (0x1000u) +#define USB_HOST_BITATTCHE (0x0800u) +#define USB_HOST_BITEOFERRE (0x0040u) +#define USB_HOST_BITBCHG (0x4000u) +#define USB_HOST_BITDTCH (0x1000u) +#define USB_HOST_BITATTCH (0x0800u) +#define USB_HOST_BITEOFERR (0x0040u) + +#define USB_HOST_BITSIGNE (0x0020u) +#define USB_HOST_BITSACKE (0x0010u) +#define USB_HOST_BITSIGN (0x0020u) +#define USB_HOST_BITSACK (0x0010u) + +#define USB_HOST_BITSUREQ (0x4000u) +#define USB_HOST_BITSQSET (0x0080u) +#define USB_HOST_PID_STALL2 (0x0003u) +#define USB_HOST_PID_STALL (0x0002u) +#define USB_HOST_PID_BUF (0x0001u) +#define USB_HOST_PID_NAK (0x0000u) + +#define USB_HOST_PIPExBUF (64u) + +#define USB_HOST_D0FIFO (0) +#define USB_HOST_D1FIFO (1) +#define USB_HOST_DMA_READY (0) +#define USB_HOST_DMA_BUSY (1) +#define USB_HOST_DMA_BUSYEND (2) + +#define USB_HOST_FIFO_USE (0x7000) + +#define USB_HOST_FIFOERROR (0xffff) +#define USB_HOST_WRITEEND (0) +#define USB_HOST_WRITESHRT (1) +#define USB_HOST_WRITING (2) +#define USB_HOST_WRITEDMA (3) +#define USB_HOST_READEND (0) +#define USB_HOST_READSHRT (1) +#define USB_HOST_READING (2) +#define USB_HOST_READOVER (3) +#define USB_HOST_READZERO (4) + +#define USB_HOST_CMD_IDLE (0x0000) +#define USB_HOST_CMD_DOING (0x0001) +#define USB_HOST_CMD_DONE (0x0002) +#define USB_HOST_CMD_NORES (0x0003) +#define USB_HOST_CMD_STALL (0x0004) +#define USB_HOST_CMD_FIELD (0x000f) + +#if 0 +#define USB_HOST_CHG_CMDFIELD( r, v ) do { r &= ( ~USB_HOST_CMD_FIELD ); \ + r |= v; } while(0) +#endif + +#define USB_HOST_MODE_WRITE (0x0100) +#define USB_HOST_MODE_READ (0x0200) +#define USB_HOST_MODE_NO_DATA (0x0300) +#define USB_HOST_MODE_FIELD (0x0f00) + +#define USB_HOST_STAGE_SETUP (0x0010) +#define USB_HOST_STAGE_DATA (0x0020) +#define USB_HOST_STAGE_STATUS (0x0030) +#define USB_HOST_STAGE_FIELD (0x00f0) + +#if 0 +#define USB_HOST_CHG_STAGEFIELD( r, v ) do { r &= ( ~USB_HOST_STAGE_FIELD ); \ + r |= v; } while(0) +#endif + +#define USB_HOST_DEVADD_MASK (0x7fc0) + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +extern uint16_t g_usb_host_elt_clockmode; + +#endif /* USB_HOST_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/inc/usb_host_version.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,32 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb_host_version.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ + +#define USB_HOST_LOCAL_Rev "VER080_140709" + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/ohci_wrapp_RZ_A1.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,1492 @@ +/* Copyright (c) 2010-2011 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#include <string.h> +#include "cmsis.h" +#include "cmsis_os.h" +#include "ohci_wrapp_RZ_A1.h" +#include "ohci_wrapp_RZ_A1_local.h" +#include "rza_io_regrw.h" +#include "usb_host_setting.h" + +/* ------------------ HcControl Register --------------------- */ +#define OR_CONTROL_PLE (0x00000004) +#define OR_CONTROL_IE (0x00000008) +#define OR_CONTROL_CLE (0x00000010) +#define OR_CONTROL_BLE (0x00000020) +/* ----------------- HcCommandStatus Register ----------------- */ +#define OR_CMD_STATUS_HCR (0x00000001) +#define OR_CMD_STATUS_CLF (0x00000002) +#define OR_CMD_STATUS_BLF (0x00000004) +#define OR_CMD_STATUS_OCR (0x00000008) +/* --------------- HcInterruptStatus Register ----------------- */ +#define OR_INTR_STATUS_WDH (0x00000002) +#define OR_INTR_STATUS_RHSC (0x00000040) +/* --------------- HcInterruptEnable Register ----------------- */ +#define OR_INTR_ENABLE_WDH (0x00000002) +#define OR_INTR_ENABLE_RHSC (0x00000040) +/* -------------- HcRhPortStatus[1:NDP] Register -------------- */ +#define OR_RH_PORT_CSC (0x00010000) +#define OR_RH_PORT_LSDA (0x00000200) +#define OR_RH_PORT_PRS (0x00000010) +#define OR_RH_PORT_POCI (0x00000008) +#define OR_RH_PORT_CCS (0x00000001) + +#define ED_FORMAT (0x00008000) /* Format */ +#define ED_SKIP (0x00004000) /* Skip this ep in queue */ +#define ED_TOGLE_CARRY (0x00000002) +#define ED_HALTED (0x00000001) + +#define TD_SETUP (0x00000000) /* Direction of Setup Packet */ +#define TD_OUT (0x00080000) /* Direction Out */ +#define TD_TOGGLE_0 (0x02000000) /* Toggle 0 */ +#define TD_TOGGLE_1 (0x03000000) /* Toggle 1 */ + +/* -------------- USB Standard Requests -------------- */ +#define GET_STATUS (0x00) +#define SET_FEATURE (0x03) +#define SET_ADDRESS (0x05) + +#define TD_CTL_MSK_DP (0x00180000) +#define TD_CTL_MSK_T (0x03000000) +#define TD_CTL_MSK_CC (0xF0000000) +#define TD_CTL_MSK_EC (0x0C000000) +#define TD_CTL_SHFT_CC (28) +#define TD_CTL_SHFT_EC (26) +#define TD_CTL_SHFT_T (24) +#define ED_SHFT_TOGLE_CARRY (1) +#define SIG_GEN_LIST_REQ (1) +#if (ISO_TRANS_MAX_NUM > 0) +#define TD_PSW_MSK_CC (0xF000) +#define TD_PSW_SHFT_CC (12) +#define TD_CTL_MSK_FC (0x07000000) +#define TD_CTL_SHFT_FC (24) +#endif + +#define CTL_TRANS_TIMEOUT (1000) +#define BLK_TRANS_TIMEOUT (5) +#define TOTAL_SEM_NUM (5 + (2 * INT_TRANS_MAX_NUM) + (2 * ISO_TRANS_MAX_NUM)) + +#define PORT_LOW_SPEED (0x00000200) +#define PORT_HIGH_SPEED (0x00000400) +#define PORT_NUM (16 + 1) /* num + root(1) */ + +typedef struct tag_hctd { + uint32_t control; /* Transfer descriptor control */ + uint8_t *currBufPtr; /* Physical address of current buffer pointer */ + struct tag_hctd *nextTD; /* Physical pointer to next Transfer Descriptor */ + uint8_t *bufEnd; /* Physical address of end of buffer */ +} hctd_t; + +#if (ISO_TRANS_MAX_NUM > 0) +#define PSW_NUM (8) +typedef struct tag_hcisotd { + uint32_t control; /* Transfer descriptor control */ + uint8_t *bufferPage0; /* Buffer Page 0 */ + struct tag_hcisotd *nextTD; /* Physical pointer to next Transfer Descriptor */ + uint8_t *bufEnd; /* Physical address of end of buffer */ + uint16_t offsetPSW[PSW_NUM]; /* Offset/PSW */ +} hcisotd_t; +#endif + +typedef struct tag_hced { + uint32_t control; /* Endpoint descriptor control */ + uint32_t tailTD; /* Physical address of tail in Transfer descriptor list */ + uint32_t headTD; /* Physcial address of head in Transfer descriptor list */ + struct tag_hced *nextED; /* Physical address of next Endpoint descriptor */ +} hced_t; + +typedef struct tag_hcca { + uint32_t IntTable[32]; /* Interrupt Table */ + uint32_t FrameNumber; /* Frame Number */ + uint32_t DoneHead; /* Done Head */ + volatile uint8_t Reserved[116]; /* Reserved for future use */ + volatile uint8_t Unknown[4]; /* Unused */ +} hcca_t; + +typedef struct tag_usb_ohci_reg { + volatile uint32_t HcRevision; + volatile uint32_t HcControl; + volatile uint32_t HcCommandStatus; + volatile uint32_t HcInterruptStatus; + volatile uint32_t HcInterruptEnable; + volatile uint32_t HcInterruptDisable; + volatile uint32_t HcHCCA; + volatile uint32_t HcPeriodCurrentED; + volatile uint32_t HcControlHeadED; + volatile uint32_t HcControlCurrentED; + volatile uint32_t HcBulkHeadED; + volatile uint32_t HcBulkCurrentED; + volatile uint32_t HcDoneHead; + volatile uint32_t HcFmInterval; + volatile uint32_t HcFmRemaining; + volatile uint32_t HcFmNumber; + volatile uint32_t HcPeriodicStart; + volatile uint32_t HcLSThreshold; + volatile uint32_t HcRhDescriptorA; + volatile uint32_t HcRhDescriptorB; + volatile uint32_t HcRhStatus; + volatile uint32_t HcRhPortStatus1; +} usb_ohci_reg_t; + +typedef struct tag_genelal_ed { + osThreadId tskid; + osSemaphoreId semid_wait; + osSemaphoreId semid_list; + void *p_curr_td; /* pointer of hctd_t or hcisotd_t */ + hced_t *p_curr_ed; + uint32_t pipe_no; + uint32_t trans_wait; + uint32_t cycle_time; + uint8_t *p_start_buf; +#if (ISO_TRANS_MAX_NUM > 0) + uint32_t psw_idx; +#endif +} genelal_ed_t; + +typedef struct tag_tdinfo { + uint32_t count; + uint32_t direction; + uint32_t msp; + uint16_t devadr; + uint16_t speed; /* 1:Speed = Low */ + uint8_t endpoint_no; +} tdinfo_t; + +typedef struct tag_split_trans { + uint16_t root_devadr; + uint16_t get_port; + uint16_t port_speed; + uint16_t reset_port; + uint32_t seq_cnt; + uint32_t port_sts_bits[PORT_NUM]; +} split_trans_t; + +static void callback_task(void const * argument); +static void control_ed_task(void const * argument); +static void bulk_ed_task(void const * argument); +static void int_ed_task(void const * argument); +static int32_t int_trans_doing(hced_t *p_ed, uint32_t index); +static int32_t chk_genelal_ed(genelal_ed_t *p_g_ed); +static void chk_genelal_td_done(genelal_ed_t *p_g_ed); +static void chk_split_trans_setting(genelal_ed_t *p_g_ed); +static void set_split_trans_setting(void); +static void control_trans(genelal_ed_t *p_g_ed); +static void bulk_trans(genelal_ed_t *p_g_ed); +static void int_trans_setting(genelal_ed_t *p_g_ed, uint32_t index); +static uint32_t chk_cycle(hced_t *p_ed); +static void int_trans(genelal_ed_t *p_g_ed); +static void get_td_info(genelal_ed_t *p_g_ed, tdinfo_t *p_td_info); +static void set_togle(uint32_t pipe, hctd_t *p_td, hced_t *p_ed); +#if (ISO_TRANS_MAX_NUM > 0) +static void iso_ed_task(void const * argument); +static int32_t iso_trans_doing(hced_t *p_ed, uint32_t index); +static void chk_iso_td_done(genelal_ed_t *p_g_ed); +static int32_t chk_iso_ed(genelal_ed_t *p_g_ed); +static void iso_trans_setting(genelal_ed_t *p_g_ed, uint32_t index); +static void iso_trans(genelal_ed_t *p_g_ed); +#endif +static void connect_check(void); + +extern USB_HOST_CFG_PIPETBL_t usb_host_blk_ep_tbl1[]; +extern USB_HOST_CFG_PIPETBL_t usb_host_int_ep_tbl1[]; +#if (ISO_TRANS_MAX_NUM > 0) +extern USB_HOST_CFG_PIPETBL_t usb_host_iso_ep_tbl1[]; +#endif + +static usb_ohci_reg_t usb_reg; +static usb_ohci_reg_t *p_usb_reg = &usb_reg; +static usbisr_fnc_t *p_usbisr_cb = NULL; +static osSemaphoreId semid_cb = NULL; +static uint32_t connect_change = 0xFFFFFFFF; +static uint32_t connect_status = 0; +static uint32_t init_end = 0; +static genelal_ed_t ctl_ed; +static genelal_ed_t blk_ed; +static genelal_ed_t int_ed[INT_TRANS_MAX_NUM]; +static split_trans_t split_ctl; + +#if (ISO_TRANS_MAX_NUM > 0) +static genelal_ed_t iso_ed[ISO_TRANS_MAX_NUM]; +#endif + +osSemaphoreDef(ohciwrapp_sem_01); +osSemaphoreDef(ohciwrapp_sem_02); +osSemaphoreDef(ohciwrapp_sem_03); +osSemaphoreDef(ohciwrapp_sem_04); +osSemaphoreDef(ohciwrapp_sem_05); +osSemaphoreDef(ohciwrapp_sem_06); +osSemaphoreDef(ohciwrapp_sem_07); +#if (INT_TRANS_MAX_NUM >= 2) +osSemaphoreDef(ohciwrapp_sem_08); +osSemaphoreDef(ohciwrapp_sem_09); +#endif +#if (INT_TRANS_MAX_NUM >= 3) +osSemaphoreDef(ohciwrapp_sem_10); +osSemaphoreDef(ohciwrapp_sem_11); +#endif +#if (INT_TRANS_MAX_NUM >= 4) +osSemaphoreDef(ohciwrapp_sem_12); +osSemaphoreDef(ohciwrapp_sem_13); +#endif +#if (ISO_TRANS_MAX_NUM >= 1) +osSemaphoreDef(ohciwrapp_sem_14); +osSemaphoreDef(ohciwrapp_sem_15); +#endif +#if (ISO_TRANS_MAX_NUM >= 2) +osSemaphoreDef(ohciwrapp_sem_16); +osSemaphoreDef(ohciwrapp_sem_17); +#endif + +osThreadDef(callback_task, osPriorityHigh, 512); +osThreadDef(control_ed_task, osPriorityNormal, 512); +osThreadDef(bulk_ed_task, osPriorityNormal, 512); +static void int_ed_task_1(void const * argument) { + int_ed_task(argument); +} +osThreadDef(int_ed_task_1, osPriorityNormal, 512); +#if (INT_TRANS_MAX_NUM >= 2) +static void int_ed_task_2(void const * argument) { + int_ed_task(argument); +} +osThreadDef(int_ed_task_2, osPriorityNormal, 512); +#endif +#if (INT_TRANS_MAX_NUM >= 3) +static void int_ed_task_3(void const * argument) { + int_ed_task(argument); +} +osThreadDef(int_ed_task_3, osPriorityNormal, 512); +#endif +#if (INT_TRANS_MAX_NUM >= 4) +static void int_ed_task_4(void const * argument) { + int_ed_task(argument); +} +osThreadDef(int_ed_task_4, osPriorityNormal, 512); +#endif + +#if (ISO_TRANS_MAX_NUM >= 1) +static void iso_ed_task_1(void const * argument) { + iso_ed_task(argument); +} +osThreadDef(iso_ed_task_1, osPriorityAboveNormal, 512); +#endif +#if (ISO_TRANS_MAX_NUM >= 2) +static void iso_ed_task_2(void const * argument) { + iso_ed_task(argument); +} +osThreadDef(iso_ed_task_2, osPriorityAboveNormal, 512); +#endif + +void ohciwrapp_init(usbisr_fnc_t *p_usbisr_fnc) { + static const osSemaphoreDef_t * const sem_def_tbl[TOTAL_SEM_NUM] = { + osSemaphore(ohciwrapp_sem_01), osSemaphore(ohciwrapp_sem_02), osSemaphore(ohciwrapp_sem_03) + , osSemaphore(ohciwrapp_sem_04), osSemaphore(ohciwrapp_sem_05), osSemaphore(ohciwrapp_sem_06) + , osSemaphore(ohciwrapp_sem_07) +#if (INT_TRANS_MAX_NUM >= 2) + , osSemaphore(ohciwrapp_sem_08), osSemaphore(ohciwrapp_sem_09) +#endif +#if (INT_TRANS_MAX_NUM >= 3) + , osSemaphore(ohciwrapp_sem_10), osSemaphore(ohciwrapp_sem_11) +#endif +#if (INT_TRANS_MAX_NUM >= 4) + , osSemaphore(ohciwrapp_sem_12), osSemaphore(ohciwrapp_sem_13) +#endif +#if (ISO_TRANS_MAX_NUM >= 1) + , osSemaphore(ohciwrapp_sem_14), osSemaphore(ohciwrapp_sem_15) +#endif +#if (ISO_TRANS_MAX_NUM >= 2) + , osSemaphore(ohciwrapp_sem_16), osSemaphore(ohciwrapp_sem_17) +#endif + }; + static const osThreadDef_t * const int_tsk_def_tbl[INT_TRANS_MAX_NUM] = { + osThread(int_ed_task_1) +#if (INT_TRANS_MAX_NUM >= 2) + , osThread(int_ed_task_2) +#endif +#if (INT_TRANS_MAX_NUM >= 3) + , osThread(int_ed_task_3) +#endif +#if (INT_TRANS_MAX_NUM >= 4) + , osThread(int_ed_task_4) +#endif + }; +#if (ISO_TRANS_MAX_NUM > 0) + static const osThreadDef_t * const iso_tsk_def_tbl[ISO_TRANS_MAX_NUM] = { + osThread(iso_ed_task_1) +#if (ISO_TRANS_MAX_NUM >= 2) + , osThread(iso_ed_task_2) +#endif + }; +#endif + + uint32_t cnt; + uint32_t index = 0; + + /* Disables interrupt for usb */ + GIC_DisableIRQ(USBIXUSBIX); + +#if (USB_HOST_CH == 0) + /* P4_1(USB0_EN) */ + GPIOP4 &= ~0x0002; /* Outputs low level */ + GPIOPMC4 &= ~0x0002; /* Port mode */ + GPIOPM4 &= ~0x0002; /* Output mode */ +#endif + + p_usbisr_cb = p_usbisr_fnc; +#if (USB_HOST_HISPEED == 0) + g_usbx_host_SupportUsbDeviceSpeed = USB_HOST_FULL_SPEED; +#else + g_usbx_host_SupportUsbDeviceSpeed = USB_HOST_HIGH_SPEED; +#endif + p_usb_reg->HcRevision = 0x00000010; + p_usb_reg->HcControl = 0x00000000; + p_usb_reg->HcCommandStatus = 0x00000000; + p_usb_reg->HcInterruptStatus = 0x00000000; + p_usb_reg->HcInterruptEnable = 0x00000000; + p_usb_reg->HcInterruptDisable = 0x00000000; + p_usb_reg->HcHCCA = 0x00000000; + p_usb_reg->HcPeriodCurrentED = 0x00000000; + p_usb_reg->HcControlHeadED = 0x00000000; + p_usb_reg->HcControlCurrentED = 0x00000000; + p_usb_reg->HcBulkHeadED = 0x00000000; + p_usb_reg->HcBulkCurrentED = 0x00000000; + p_usb_reg->HcDoneHead = 0x00000000; + p_usb_reg->HcFmInterval = 0x00002EDF; + p_usb_reg->HcFmRemaining = 0x00002EDF; + p_usb_reg->HcFmNumber = 0x00000000; + p_usb_reg->HcPeriodicStart = 0x00000000; + p_usb_reg->HcLSThreshold = 0x00000628; + p_usb_reg->HcRhDescriptorA = 0xFF000901; + p_usb_reg->HcRhDescriptorB = 0x00020000; + p_usb_reg->HcRhStatus = 0x00000000; + p_usb_reg->HcRhPortStatus1 = 0x00000000; + +#if (USB_HOST_CH == 0) + GPIOP4 |= 0x0002; /* P4_1 Outputs high level */ + osDelay(5); + GPIOP4 &= ~0x0002; /* P4_1 Outputs low level */ + osDelay(10); +#else + osDelay(15); +#endif + + if (init_end == 0) { + (void)memset(&ctl_ed, 0, sizeof(ctl_ed)); + (void)memset(&blk_ed, 0, sizeof(blk_ed)); + (void)memset(&int_ed[0], 0, sizeof(int_ed)); +#if (ISO_TRANS_MAX_NUM > 0) + (void)memset(&iso_ed[0], 0, sizeof(iso_ed)); +#endif + + /* callback */ + semid_cb = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + (void)osThreadCreate(osThread(callback_task), 0); + + /* control transfer */ + ctl_ed.semid_wait = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + ctl_ed.semid_list = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + ctl_ed.tskid = osThreadCreate(osThread(control_ed_task), 0); + + /* bulk transfer */ + blk_ed.semid_wait = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + blk_ed.semid_list = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + blk_ed.tskid = osThreadCreate(osThread(bulk_ed_task), 0); + + /* interrupt transfer */ + for (cnt = 0; cnt < INT_TRANS_MAX_NUM; cnt++) { + int_ed[cnt].semid_wait = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + int_ed[cnt].semid_list = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + int_ed[cnt].tskid = osThreadCreate(int_tsk_def_tbl[cnt], (void *)cnt); + } + +#if (ISO_TRANS_MAX_NUM > 0) + /* isochronous transfer */ + for (cnt = 0; cnt < ISO_TRANS_MAX_NUM; cnt++) { + iso_ed[cnt].semid_wait = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + iso_ed[cnt].semid_list = osSemaphoreCreate(sem_def_tbl[index], 0); + index++; + iso_ed[cnt].tskid = osThreadCreate(iso_tsk_def_tbl[cnt], (void *)cnt); + } +#endif + init_end = 1; + } +} + +uint32_t ohciwrapp_reg_r(uint32_t reg_ofs) { + if (init_end == 0) { + return 0; + } + + return *(uint32_t *)((uint8_t *)p_usb_reg + reg_ofs); +} + +void ohciwrapp_reg_w(uint32_t reg_ofs, uint32_t set_data) { + uint32_t cnt; + uint32_t last_data; + hcca_t *p_hcca; + + if (init_end == 0) { + return; + } + + switch (reg_ofs) { + case OHCI_REG_CONTROL: + last_data = p_usb_reg->HcControl; + p_usb_reg->HcControl = (set_data & 0x000007FF); + if ((last_data & OR_CONTROL_CLE) != (set_data & OR_CONTROL_CLE)) { + /* change CLE */ + if ((set_data & OR_CONTROL_CLE) != 0) { + (void)osSemaphoreRelease(ctl_ed.semid_list); + } else { + if (ctl_ed.trans_wait == 1) { + ctl_ed.trans_wait = 0; + (void)osSemaphoreRelease(ctl_ed.semid_wait); + } + (void)osSemaphoreWait(ctl_ed.semid_list, osWaitForever); + } + } + if ((last_data & OR_CONTROL_BLE) != (set_data & OR_CONTROL_BLE)) { + /* change BLE */ + if ((set_data & OR_CONTROL_BLE) != 0) { + (void)osSemaphoreRelease(blk_ed.semid_list); + } else { + if (blk_ed.trans_wait == 1) { + blk_ed.trans_wait = 0; + (void)osSemaphoreRelease(blk_ed.semid_wait); + } + (void)osSemaphoreWait(blk_ed.semid_list, osWaitForever); + } + } +#if (ISO_TRANS_MAX_NUM > 0) + if ((last_data & OR_CONTROL_IE) != (set_data & OR_CONTROL_IE)) { + /* change IE */ + for (cnt = 0; cnt < ISO_TRANS_MAX_NUM; cnt++) { + if ((set_data & OR_CONTROL_IE) != 0) { + (void)osSemaphoreRelease(iso_ed[cnt].semid_list); + } else { + if (iso_ed[cnt].trans_wait == 1) { + iso_ed[cnt].trans_wait = 0; + (void)osSemaphoreRelease(iso_ed[cnt].semid_wait); + } + (void)osSemaphoreWait(iso_ed[cnt].semid_list, osWaitForever); + } + } + } +#endif + if ((last_data & OR_CONTROL_PLE) != (set_data & OR_CONTROL_PLE)) { + /* change PLE */ + for (cnt = 0; cnt < INT_TRANS_MAX_NUM; cnt++) { + if ((set_data & OR_CONTROL_PLE) != 0) { + (void)osSemaphoreRelease(int_ed[cnt].semid_list); + } else { + if (int_ed[cnt].trans_wait == 1) { + int_ed[cnt].trans_wait = 0; + (void)osSemaphoreRelease(int_ed[cnt].semid_wait); + } + (void)osSemaphoreWait(int_ed[cnt].semid_list, osWaitForever); + } + } + } + break; + case OHCI_REG_COMMANDSTATUS: + if ((set_data & OR_CMD_STATUS_HCR) != 0) { /* HostController Reset */ + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_HCR; + if (usbx_api_host_init(16, g_usbx_host_SupportUsbDeviceSpeed, USBHCLOCK_X1_48MHZ) == USB_HOST_ATTACH) { + ohciwrapp_loc_Connect(1); + } + p_usb_reg->HcCommandStatus &= ~OR_CMD_STATUS_HCR; + } + if ((set_data & OR_CMD_STATUS_CLF) != 0) { + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_CLF; + osSignalSet(ctl_ed.tskid, SIG_GEN_LIST_REQ); + } + if ((set_data & OR_CMD_STATUS_BLF) != 0) { + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_BLF; + osSignalSet(blk_ed.tskid, SIG_GEN_LIST_REQ); + } + if ((set_data & OR_CMD_STATUS_OCR) != 0) { + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_OCR; + } else { + p_usb_reg->HcCommandStatus &= ~OR_CMD_STATUS_OCR; + } + break; + case OHCI_REG_INTERRUPTSTATUS: + if (((p_usb_reg->HcInterruptStatus & OR_INTR_STATUS_WDH) != 0) + && ((set_data & OR_INTR_STATUS_WDH) != 0)) { + if (p_usb_reg->HcDoneHead != 0x00000000) { + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + p_hcca->DoneHead = p_usb_reg->HcDoneHead; + p_usb_reg->HcDoneHead = 0x00000000; + p_usb_reg->HcInterruptStatus |= OR_INTR_STATUS_WDH; + (void)osSemaphoreRelease(semid_cb); + } else { + p_usb_reg->HcInterruptStatus &= ~OR_INTR_STATUS_WDH; + } + } + if ((set_data & OR_INTR_STATUS_RHSC) != 0) { + p_usb_reg->HcInterruptStatus &= ~OR_INTR_STATUS_RHSC; + } + break; + case OHCI_REG_INTERRUPTENABLE: + case OHCI_REG_INTERRUPTDISABLE: + case OHCI_REG_HCCA: + case OHCI_REG_CONTROLHEADED: + case OHCI_REG_CONTROLCURRENTED: + case OHCI_REG_BULKHEADED: + case OHCI_REG_BULKCURRENTED: + case OHCI_REG_FMINTERVAL: + case OHCI_REG_FMREMAINING: + case OHCI_REG_PERIODICSTART: + case OHCI_REG_LSTHRESHOLD: + case OHCI_REG_RHDESCRIPTORA: + case OHCI_REG_RHDESCRIPTORB: + case OHCI_REG_RHSTATUS: + *(uint32_t *)((uint8_t *)p_usb_reg + reg_ofs) = set_data; + break; + case OHCI_REG_RHPORTSTATUS1: + p_usb_reg->HcRhPortStatus1 &= ~(set_data & 0xFFFF0000); + if ((set_data & OR_RH_PORT_PRS) != 0) { /* Set Port Reset */ + p_usb_reg->HcRhPortStatus1 |= OR_RH_PORT_PRS; + usbx_host_UsbBusReset(); + p_usb_reg->HcRhPortStatus1 &= ~OR_RH_PORT_PRS; + } + break; + case OHCI_REG_REVISION: + case OHCI_REG_PERIODCURRENTED: + case OHCI_REG_DONEHEADED: + case OHCI_REG_FMNUMBER: + default: + /* Do Nothing */ + break; + } +} + +static void callback_task(void const * argument) { + usbisr_fnc_t *p_wk_cb = p_usbisr_cb; + + if (p_wk_cb == NULL) { + return; + } + + while (1) { + osSemaphoreWait(semid_cb, osWaitForever); + if (connect_change != 0xFFFFFFFF) { + connect_change = 0xFFFFFFFF; + connect_check(); + } + p_wk_cb(); + } +} + +static void control_ed_task(void const * argument) { + while (1) { + osSignalWait(SIG_GEN_LIST_REQ, osWaitForever); + (void)osSemaphoreWait(ctl_ed.semid_list, osWaitForever); + while ((p_usb_reg->HcControl & OR_CONTROL_CLE) != 0) { + if ((p_usb_reg->HcControlCurrentED == 0) + && ((p_usb_reg->HcCommandStatus & OR_CMD_STATUS_CLF) != 0)) { + p_usb_reg->HcControlCurrentED = p_usb_reg->HcControlHeadED; + p_usb_reg->HcCommandStatus &= ~OR_CMD_STATUS_CLF; + } + if (p_usb_reg->HcControlCurrentED != 0) { + ctl_ed.p_curr_ed = (hced_t *)p_usb_reg->HcControlCurrentED; + if (chk_genelal_ed(&ctl_ed) != 0) { + control_trans(&ctl_ed); + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_CLF; + } + p_usb_reg->HcControlCurrentED = (uint32_t)ctl_ed.p_curr_ed->nextED; + } else { + break; + } + } + if ((p_usb_reg->HcCommandStatus & OR_CMD_STATUS_CLF) != 0) { + osSignalSet(ctl_ed.tskid, SIG_GEN_LIST_REQ); + } + (void)osSemaphoreRelease(ctl_ed.semid_list); + } +} + +static void bulk_ed_task(void const * argument) { + while (1) { + osSignalWait(SIG_GEN_LIST_REQ, osWaitForever); + (void)osSemaphoreWait(blk_ed.semid_list, osWaitForever); + while ((p_usb_reg->HcControl & OR_CONTROL_BLE) != 0) { + if ((p_usb_reg->HcBulkCurrentED == 0) + && ((p_usb_reg->HcCommandStatus & OR_CMD_STATUS_BLF) != 0)) { + p_usb_reg->HcBulkCurrentED = p_usb_reg->HcBulkHeadED; + p_usb_reg->HcCommandStatus &= ~OR_CMD_STATUS_BLF; + } + if (p_usb_reg->HcBulkCurrentED != 0) { + blk_ed.p_curr_ed = (hced_t *)p_usb_reg->HcBulkCurrentED; + if (chk_genelal_ed(&blk_ed) != 0) { + bulk_trans(&blk_ed); + p_usb_reg->HcCommandStatus |= OR_CMD_STATUS_BLF; + } + p_usb_reg->HcBulkCurrentED = (uint32_t)blk_ed.p_curr_ed->nextED; + } else { + break; + } + } + if ((p_usb_reg->HcCommandStatus & OR_CMD_STATUS_BLF) != 0) { + osSignalSet(blk_ed.tskid, SIG_GEN_LIST_REQ); + } + (void)osSemaphoreRelease(blk_ed.semid_list); + } +} + +static void int_ed_task(void const * argument) { + genelal_ed_t *p_int_ed = &int_ed[(uint32_t)argument]; + uint32_t cnt; + uint32_t wait_cnt = 0; + hcca_t *p_hcca; + hced_t *p_ed; + + while (1) { + (void)osSemaphoreWait(p_int_ed->semid_list, osWaitForever); + if (p_int_ed->p_curr_ed == NULL) { + for (cnt = 0; (cnt < 32) && ((p_usb_reg->HcControl & OR_CONTROL_PLE) != 0) + && (p_int_ed->p_curr_ed == NULL); cnt++) { + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + p_ed = (hced_t *)p_hcca->IntTable[cnt]; + while ((p_ed != NULL) && ((p_usb_reg->HcControl & OR_CONTROL_PLE) != 0) + && (p_int_ed->p_curr_ed == NULL)) { + if (int_trans_doing(p_ed, (uint32_t)argument) == 0) { + p_int_ed->p_curr_ed = p_ed; + if (chk_genelal_ed(p_int_ed) != 0) { + int_trans_setting(p_int_ed, (uint32_t)argument); + } else { + p_int_ed->p_curr_ed = NULL; + } + } + p_ed = p_ed->nextED; + } + } + } + if (p_int_ed->p_curr_ed != NULL) { + while ((p_usb_reg->HcControl & OR_CONTROL_PLE) != 0) { + if (chk_genelal_ed(p_int_ed) != 0) { + int_trans(p_int_ed); + (void)osSemaphoreWait(p_int_ed->semid_wait, osWaitForever); + usbx_host_stop_transfer(p_int_ed->pipe_no); + wait_cnt = p_int_ed->cycle_time; + } else { + if (wait_cnt > 0) { + wait_cnt--; + } else { + p_int_ed->p_curr_ed = NULL; + } + break; + } + } + } + (void)osSemaphoreRelease(p_int_ed->semid_list); + if (p_int_ed->p_curr_ed == NULL) { + osDelay(10); + } else { + osDelay(1); + } + } +} + +static int32_t int_trans_doing(hced_t *p_ed, uint32_t index) { + uint32_t cnt; + int32_t ret = 0; + + for (cnt = 0; cnt < INT_TRANS_MAX_NUM; cnt++) { + if ((index != cnt) && (int_ed[cnt].p_curr_ed == p_ed)) { + ret = 1; + } + } + + return ret; +} + +static int32_t chk_genelal_ed(genelal_ed_t *p_g_ed){ + int32_t ret = 0; + hced_t *p_ed = p_g_ed->p_curr_ed; + + if (((p_ed->control & ED_SKIP) != 0) + || ((p_ed->control & ED_FORMAT) != 0) + || ((p_ed->headTD & ED_HALTED) != 0) + || ((p_ed->tailTD & 0xFFFFFFF0) == (p_ed->headTD & 0xFFFFFFF0))) { + /* Do Nothing */ + } else if ((p_ed->control & 0x0000007F) > 10) { + p_ed->headTD |= ED_HALTED; + } else { + p_g_ed->p_curr_td = (void *)(p_ed->headTD & 0xFFFFFFF0); + if (p_g_ed->p_curr_td == NULL) { + p_ed->headTD |= ED_HALTED; + } else { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + + p_g_ed->p_start_buf = p_td->currBufPtr; + ret = 1; + } + } + + return ret; +} + +static void chk_genelal_td_done(genelal_ed_t *p_g_ed) { + hcca_t *p_hcca; + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + uint32_t ConditionCode = RZA_IO_RegRead_32(&p_td->control, TD_CTL_SHFT_CC, TD_CTL_MSK_CC); + + if ((ConditionCode != TD_CC_NOT_ACCESSED_1) && (ConditionCode != TD_CC_NOT_ACCESSED_2)) { + p_g_ed->p_curr_ed->headTD = ((uint32_t)p_td->nextTD & 0xFFFFFFF0) + | (p_g_ed->p_curr_ed->headTD & 0x0000000F); + p_td->nextTD = (hctd_t *)p_usb_reg->HcDoneHead; + p_usb_reg->HcDoneHead = (uint32_t)p_g_ed->p_curr_td; + if ((p_usb_reg->HcInterruptStatus & OR_INTR_STATUS_WDH) == 0) { + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + p_hcca->DoneHead = p_usb_reg->HcDoneHead; + p_usb_reg->HcDoneHead = 0x00000000; + p_usb_reg->HcInterruptStatus |= OR_INTR_STATUS_WDH; + (void)osSemaphoreRelease(semid_cb); + } + } +} + +static void chk_split_trans_setting(genelal_ed_t *p_g_ed) { + uint8_t *p_buf; + tdinfo_t td_info; + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + + /* Hi-Speed mode only */ + if (g_usbx_host_UsbDeviceSpeed != USB_HOST_HIGH_SPEED) { + return; + } + + if (RZA_IO_RegRead_32(&p_td->control, TD_CTL_SHFT_CC, TD_CTL_MSK_CC) != TD_CC_NOERROR) { + return; + } + + get_td_info(p_g_ed, &td_info); + p_buf = p_g_ed->p_start_buf; + + if (td_info.direction == 0) { + uint8_t bRequest = p_buf[1]; + uint16_t wValue = (p_buf[3] << 8) + p_buf[2]; + uint16_t wIndx = (p_buf[5] << 8) + p_buf[4]; + uint16_t devadd; + + if ((td_info.devadr == 0) && (bRequest == SET_ADDRESS)) { + /* SET_ADDRESS */ + usbx_host_get_devadd(USB_HOST_DEVICE_0, &devadd); + usbx_host_set_devadd(wValue, &devadd); + if (split_ctl.root_devadr == 0) { + split_ctl.root_devadr = wValue; /* New Address */ + } + } else if ((td_info.devadr == split_ctl.root_devadr) && (bRequest == SET_FEATURE) + && (wValue == 0x0004) && (split_ctl.root_devadr != 0)) { + /* SET_FEATURE PORT_RESET */ + split_ctl.reset_port = (wIndx & 0x00FF); + } else if ((td_info.devadr == split_ctl.root_devadr) && (bRequest == GET_STATUS)) { + /* GET_STATUS */ + split_ctl.get_port = wIndx; + split_ctl.seq_cnt = 1; + } else { + /* Do Nothing */ + } + } else if (td_info.direction == 2) { + if ((td_info.devadr == split_ctl.root_devadr) && (split_ctl.seq_cnt == 1)) { + if (split_ctl.get_port < PORT_NUM) { + split_ctl.port_sts_bits[split_ctl.get_port] = (p_buf[1] << 8) + p_buf[0]; + } + split_ctl.seq_cnt = 0; + } + } else { + /* Do Nothing */ + } +} + +static void set_split_trans_setting(void) { + uint16_t port_speed; + uint16_t devadd; + + if ((split_ctl.root_devadr != 0) && (split_ctl.reset_port != 0) && (split_ctl.reset_port < PORT_NUM)) { + usbx_host_get_devadd(USB_HOST_DEVICE_0, &devadd); + RZA_IO_RegWrite_16(&devadd, split_ctl.root_devadr, USB_DEVADDn_UPPHUB_SHIFT, USB_DEVADDn_UPPHUB); + RZA_IO_RegWrite_16(&devadd, split_ctl.reset_port, USB_DEVADDn_HUBPORT_SHIFT, USB_DEVADDn_HUBPORT); + if ((split_ctl.port_sts_bits[split_ctl.reset_port] & PORT_HIGH_SPEED) != 0) { + port_speed = USB_HOST_HIGH_SPEED; + } else if ((split_ctl.port_sts_bits[split_ctl.reset_port] & PORT_LOW_SPEED) != 0) { + port_speed = USB_HOST_LOW_SPEED; + } else { + port_speed = USB_HOST_FULL_SPEED; + } + RZA_IO_RegWrite_16(&devadd, port_speed, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD); + usbx_host_set_devadd(USB_HOST_DEVICE_0, &devadd); + split_ctl.reset_port = 0; + } +} + +static void control_trans(genelal_ed_t *p_g_ed) { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + tdinfo_t td_info; + uint16_t devadd; + + get_td_info(p_g_ed, &td_info); + + if (g_usbx_host_UsbDeviceSpeed == USB_HOST_HIGH_SPEED) { + if (td_info.devadr == 0) { + set_split_trans_setting(); + } + } else { + /* When a non-Hi-Speed, the communication speed is determined from the TD. */ + usbx_host_get_devadd(USB_HOST_DEVICE_0, &devadd); + if (td_info.speed == 1) { + RZA_IO_RegWrite_16(&devadd, USB_HOST_LOW_SPEED, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD); + } else { + RZA_IO_RegWrite_16(&devadd, USB_HOST_FULL_SPEED, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD); + } + usbx_host_set_devadd(td_info.devadr, &devadd); + } + + USB20X.DCPMAXP = (td_info.devadr << 12) + td_info.msp; + if (td_info.direction == 0) { + g_usbx_host_CmdStage = (USB_HOST_STAGE_SETUP | USB_HOST_CMD_IDLE); + } else if (td_info.count != 0) { + g_usbx_host_CmdStage = (USB_HOST_STAGE_DATA | USB_HOST_CMD_IDLE); + } else { + g_usbx_host_CmdStage = (USB_HOST_STAGE_STATUS | USB_HOST_CMD_IDLE); + } + g_usbx_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_WAIT; + p_g_ed->pipe_no = USB_HOST_PIPE0; + + p_g_ed->trans_wait = 1; + if (connect_status == 0) { + ohciwrapp_loc_TransEnd(p_g_ed->pipe_no, TD_CC_DEVICENOTRESPONDING); + } else { + if (td_info.direction == 0) { + uint16_t Req = (p_td->currBufPtr[1] << 8) + p_td->currBufPtr[0]; + uint16_t Val = (p_td->currBufPtr[3] << 8) + p_td->currBufPtr[2]; + uint16_t Indx = (p_td->currBufPtr[5] << 8) + p_td->currBufPtr[4]; + uint16_t Len = (p_td->currBufPtr[7] << 8) + p_td->currBufPtr[6]; + + g_usbx_host_data_pointer[USB_HOST_PIPE0] = p_td->bufEnd; + usbx_host_SetupStage(Req, Val, Indx, Len); + } else if (td_info.direction == 1) { + usbx_host_CtrlWriteStart(td_info.count, p_td->currBufPtr); + } else { + usbx_host_CtrlReadStart(td_info.count, p_td->currBufPtr); + } + + (void)osSemaphoreWait(p_g_ed->semid_wait, CTL_TRANS_TIMEOUT); + if (p_g_ed->trans_wait == 1) { + p_g_ed->trans_wait = 0; + RZA_IO_RegWrite_32(&p_td->control, TD_CC_DEVICENOTRESPONDING, TD_CTL_SHFT_CC, TD_CTL_MSK_CC); + } + } + + g_usbx_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usbx_host_CmdStage |= USB_HOST_CMD_IDLE; + g_usbx_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_IDLE; +} + +static void bulk_trans(genelal_ed_t *p_g_ed) { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + hced_t *p_ed = p_g_ed->p_curr_ed; + tdinfo_t td_info; + USB_HOST_CFG_PIPETBL_t *user_table = &usb_host_blk_ep_tbl1[0]; + uint8_t wk_table[6]; + + get_td_info(p_g_ed, &td_info); + + wk_table[0] = 0; + wk_table[1] = USB_HOST_ENDPOINT_DESC; + wk_table[2] = td_info.endpoint_no; + if (td_info.direction == 2) { + wk_table[2] |= USB_HOST_EP_IN; + } + wk_table[3] = USB_HOST_EP_BULK; + wk_table[4] = (uint8_t)td_info.msp; + wk_table[5] = (uint8_t)(td_info.msp >> 8); + p_g_ed->pipe_no = user_table->pipe_number; + usbx_api_host_SetEndpointTable(td_info.devadr, user_table, wk_table); + + set_togle(p_g_ed->pipe_no, p_td, p_ed); + + p_g_ed->trans_wait = 1; + if (connect_status == 0) { + ohciwrapp_loc_TransEnd(p_g_ed->pipe_no, TD_CC_DEVICENOTRESPONDING); + } else { + if (td_info.direction == 1) { + usbx_host_start_send_transfer(p_g_ed->pipe_no, td_info.count, p_td->currBufPtr); + } else { + usbx_host_start_receive_transfer(p_g_ed->pipe_no, td_info.count, p_td->currBufPtr); + } + + (void)osSemaphoreWait(p_g_ed->semid_wait, BLK_TRANS_TIMEOUT); + usbx_host_stop_transfer(p_g_ed->pipe_no); + } +} + +static void int_trans_setting(genelal_ed_t *p_g_ed, uint32_t index) { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + hced_t *p_ed = p_g_ed->p_curr_ed; + tdinfo_t td_info; + USB_HOST_CFG_PIPETBL_t *user_table = &usb_host_int_ep_tbl1[index]; + uint8_t wk_table[6]; + uint32_t cycle_time; + uint16_t devadd; + + get_td_info(p_g_ed, &td_info); + + wk_table[0] = 0; + wk_table[1] = USB_HOST_ENDPOINT_DESC; + wk_table[2] = td_info.endpoint_no; + if (td_info.direction == 2) { + wk_table[2] |= USB_HOST_EP_IN; + } + wk_table[3] = USB_HOST_EP_INT; + wk_table[4] = (uint8_t)td_info.msp; + wk_table[5] = (uint8_t)(td_info.msp >> 8); + cycle_time = chk_cycle(p_ed); + p_g_ed->cycle_time = cycle_time; + user_table->pipe_cycle = 0; + while (cycle_time > 1) { + cycle_time >>= 1; + user_table->pipe_cycle++; + } + if (g_usbx_host_UsbDeviceSpeed == USB_HOST_HIGH_SPEED) { + usbx_host_get_devadd(td_info.devadr, &devadd); + if (RZA_IO_RegRead_16(&devadd, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD) == USB_HOST_HIGH_SPEED) { + user_table->pipe_cycle += 3; + if (user_table->pipe_cycle > 7) { + user_table->pipe_cycle = 7; + } + } + } + + p_g_ed->pipe_no = user_table->pipe_number; + usbx_api_host_SetEndpointTable(td_info.devadr, user_table, wk_table); + + set_togle(p_g_ed->pipe_no, p_td, p_ed); +} + +static uint32_t chk_cycle(hced_t *p_ed) { + uint32_t cnt; + uint32_t hit_cnt = 0; + uint32_t cycle_time = 1; + hcca_t *p_hcca; + hced_t *p_wk_ed; + + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + + for (cnt = 0; cnt < 32; cnt++) { + p_wk_ed = (hced_t *)p_hcca->IntTable[cnt]; + while (p_wk_ed != NULL) { + if (p_wk_ed == p_ed) { + hit_cnt++; + break; + } + p_wk_ed = p_wk_ed->nextED; + } + } + if (hit_cnt < 2) { + cycle_time = 32; + } else if (hit_cnt < 4) { + cycle_time = 16; + } else if (hit_cnt < 8) { + cycle_time = 8; + } else if (hit_cnt < 16) { + cycle_time = 4; + } else if (hit_cnt < 32) { + cycle_time = 2; + } else{ + cycle_time = 1; + } + + return cycle_time; +} + +static void int_trans(genelal_ed_t *p_g_ed) { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + tdinfo_t td_info; + + get_td_info(p_g_ed, &td_info); + p_g_ed->trans_wait = 1; + if (connect_status == 0) { + ohciwrapp_loc_TransEnd(p_g_ed->pipe_no, TD_CC_DEVICENOTRESPONDING); + } else { + if (td_info.direction == 1) { + usbx_host_start_send_transfer(p_g_ed->pipe_no, td_info.count, p_td->currBufPtr); + } else { + usbx_host_start_receive_transfer(p_g_ed->pipe_no, td_info.count, p_td->currBufPtr); + } + } +} + +static void get_td_info(genelal_ed_t *p_g_ed, tdinfo_t *p_td_info) { + hced_t *p_ed = p_g_ed->p_curr_ed; + + p_td_info->endpoint_no = (uint8_t)((p_ed->control >> 7) & 0x0000000F); + p_td_info->msp = (p_ed->control >> 16) & 0x000007FF; + p_td_info->devadr = p_ed->control & 0x0000000F; + p_td_info->speed = (p_ed->control >> 13) & 0x00000001; + p_td_info->direction = (p_ed->control >> 11) & 0x00000003; + + if ((p_ed->control & ED_FORMAT) == 0) { + hctd_t *p_td = (hctd_t *)p_g_ed->p_curr_td; + + if ((p_td_info->direction == 0) || (p_td_info->direction == 3)) { + if ((p_td->control & TD_CTL_MSK_DP) == TD_SETUP) { + p_td_info->direction = 0; + } else if ((p_td->control & TD_CTL_MSK_DP) == TD_OUT) { + p_td_info->direction = 1; + } else { + p_td_info->direction = 2; + } + } + if (p_td->currBufPtr != NULL) { + p_td_info->count = (uint32_t)p_td->bufEnd - (uint32_t)p_td->currBufPtr + 1; + } else { + p_td_info->count = 0; + } + } else { +#if (ISO_TRANS_MAX_NUM > 0) + hcisotd_t *p_isotd = (hcisotd_t *)p_g_ed->p_curr_td; + + if ((p_td_info->direction == 0) || (p_td_info->direction == 3)) { + if ((p_isotd->control & TD_CTL_MSK_DP) == TD_SETUP) { + p_td_info->direction = 0; + } else if ((p_isotd->control & TD_CTL_MSK_DP) == TD_OUT) { + p_td_info->direction = 1; + } else { + p_td_info->direction = 2; + } + } +#endif + } +} + +static void set_togle(uint32_t pipe, hctd_t *p_td, hced_t *p_ed) { + if ((p_td->control & TD_CTL_MSK_T) == TD_TOGGLE_0) { + usbx_host_set_sqclr(pipe); + } else if ((p_td->control & TD_CTL_MSK_T) == TD_TOGGLE_1) { + usbx_host_set_sqset(pipe); + } else if ((p_ed->headTD & ED_TOGLE_CARRY) == 0) { + usbx_host_set_sqclr(pipe); + } else { + usbx_host_set_sqset(pipe); + } +} + +#if (ISO_TRANS_MAX_NUM > 0) +static void iso_ed_task(void const * argument) { + genelal_ed_t *p_iso_ed = &iso_ed[(uint32_t)argument]; + uint32_t wait_cnt = 0; + hcca_t *p_hcca; + hced_t *p_ed; + + while (1) { + (void)osSemaphoreWait(p_iso_ed->semid_list, osWaitForever); + if (p_iso_ed->p_curr_ed == NULL) { + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + p_ed = (hced_t *)p_hcca->IntTable[0]; + while ((p_ed != NULL) && ((p_usb_reg->HcControl & OR_CONTROL_IE) != 0) + && (p_iso_ed->p_curr_ed == NULL)) { + if (iso_trans_doing(p_ed, (uint32_t)argument) == 0) { + p_iso_ed->p_curr_ed = p_ed; + if (chk_iso_ed(p_iso_ed) != 0) { + iso_trans_setting(p_iso_ed, (uint32_t)argument); + } else { + p_iso_ed->p_curr_ed = NULL; + } + } + p_ed = p_ed->nextED; + } + p_iso_ed->psw_idx = 0; + } + if (p_iso_ed->p_curr_ed != NULL) { + while ((p_usb_reg->HcControl & OR_CONTROL_IE) != 0) { + if (chk_iso_ed(p_iso_ed) != 0) { + hcisotd_t *p_isotd = (hcisotd_t *)p_iso_ed->p_curr_td; + uint32_t starting_frame = p_isotd->control & 0x0000FFFF; + uint32_t wait_time = 0; + uint32_t wk_HcFmNumber = p_usb_reg->HcFmNumber; + + if (starting_frame > wk_HcFmNumber) { + wait_time = starting_frame - wk_HcFmNumber; + } else { + wait_time = (0xFFFF - wk_HcFmNumber) + starting_frame; + } + if ((wait_time >= 2) && (wait_time <= 1000)) { + for (int cnt = 0; cnt < (wait_time - 1); cnt++) { + osDelay(1); + p_usb_reg->HcFmNumber = (wk_HcFmNumber + cnt) & 0x0000FFFF; + } + } + p_iso_ed->psw_idx = 0; + iso_trans(p_iso_ed); + (void)osSemaphoreWait(p_iso_ed->semid_wait, osWaitForever); + wait_cnt = 8; + } else { + if (wait_cnt > 0) { + wait_cnt--; + } else { + p_iso_ed->p_curr_ed = NULL; + } + break; + } + } + } + (void)osSemaphoreRelease(p_iso_ed->semid_list); + if (p_iso_ed->p_curr_ed == NULL) { + osDelay(10); + } else { + osDelay(1); + } + } +} + +static int32_t iso_trans_doing(hced_t *p_ed, uint32_t index) { + uint32_t cnt; + int32_t ret = 0; + + for (cnt = 0; cnt < ISO_TRANS_MAX_NUM; cnt++) { + if ((index != cnt) && (iso_ed[cnt].p_curr_ed == p_ed)) { + ret = 1; + } + } + + return ret; +} + +static void chk_iso_td_done(genelal_ed_t *p_g_ed) { + hcca_t *p_hcca; + hcisotd_t *p_isotd = (hcisotd_t *)p_g_ed->p_curr_td; + uint32_t ConditionCode = RZA_IO_RegRead_32(&p_isotd->control, TD_CTL_SHFT_CC, TD_CTL_MSK_CC); + + if ((ConditionCode != TD_CC_NOT_ACCESSED_1) && (ConditionCode != TD_CC_NOT_ACCESSED_2)) { + p_g_ed->p_curr_ed->headTD = ((uint32_t)p_isotd->nextTD & 0xFFFFFFF0) + | (p_g_ed->p_curr_ed->headTD & 0x0000000F); + p_isotd->nextTD = (hcisotd_t *)p_usb_reg->HcDoneHead; + p_usb_reg->HcDoneHead = (uint32_t)p_g_ed->p_curr_td; + if ((p_usb_reg->HcInterruptStatus & OR_INTR_STATUS_WDH) == 0) { + p_hcca = (hcca_t *)p_usb_reg->HcHCCA; + p_hcca->DoneHead = p_usb_reg->HcDoneHead; + p_usb_reg->HcDoneHead = 0x00000000; + p_usb_reg->HcInterruptStatus |= OR_INTR_STATUS_WDH; + (void)osSemaphoreRelease(semid_cb); + } + } +} + +static int32_t chk_iso_ed(genelal_ed_t *p_g_ed){ + int32_t ret = 0; + hced_t *p_ed = p_g_ed->p_curr_ed; + + if (((p_ed->control & ED_SKIP) != 0) + || ((p_ed->control & ED_FORMAT) == 0) + || ((p_ed->headTD & ED_HALTED) != 0) + || ((p_ed->tailTD & 0xFFFFFFF0) == (p_ed->headTD & 0xFFFFFFF0))) { + /* Do Nothing */ + } else if ((p_ed->control & 0x0000007F) > 10) { + p_ed->headTD |= ED_HALTED; + } else { + p_g_ed->p_curr_td = (void *)(p_ed->headTD & 0xFFFFFFF0); + if (p_g_ed->p_curr_td == NULL) { + p_ed->headTD |= ED_HALTED; + } else { + hcisotd_t *p_isotd = (hcisotd_t *)p_g_ed->p_curr_td; + + p_g_ed->p_start_buf = p_isotd->bufferPage0; + ret = 1; + } + } + + return ret; +} + +static void iso_trans_setting(genelal_ed_t *p_g_ed, uint32_t index) { + tdinfo_t td_info; + USB_HOST_CFG_PIPETBL_t *user_table = &usb_host_iso_ep_tbl1[index]; + uint8_t wk_table[6]; + uint16_t devadd; + + get_td_info(p_g_ed, &td_info); + + wk_table[0] = 0; + wk_table[1] = USB_HOST_ENDPOINT_DESC; + wk_table[2] = td_info.endpoint_no; + if (td_info.direction == 2) { + wk_table[2] |= USB_HOST_EP_IN; + } + wk_table[3] = USB_HOST_EP_ISO; + wk_table[4] = (uint8_t)td_info.msp; + wk_table[5] = (uint8_t)(td_info.msp >> 8); + p_g_ed->cycle_time = 1; + user_table->pipe_cycle = 0; + if (g_usbx_host_UsbDeviceSpeed == USB_HOST_HIGH_SPEED) { + usbx_host_get_devadd(td_info.devadr, &devadd); + if (RZA_IO_RegRead_16(&devadd, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD) == USB_HOST_HIGH_SPEED) { + user_table->pipe_cycle += 3; + } + } + + p_g_ed->pipe_no = user_table->pipe_number; + usbx_api_host_SetEndpointTable(td_info.devadr, user_table, wk_table); +} + +static void iso_trans(genelal_ed_t *p_g_ed) { + hcisotd_t *p_isotd = (hcisotd_t *)p_g_ed->p_curr_td; + tdinfo_t td_info; + uint32_t buff_addr; + uint32_t data_size; + + if (((uint32_t)p_isotd->offsetPSW[p_g_ed->psw_idx] & 0x00001000) == 0) { + buff_addr = (uint32_t)p_isotd->bufferPage0 & 0xFFFFF000; + } else { + buff_addr = (uint32_t)p_isotd->bufEnd & 0xFFFFF000; + } + buff_addr |= (uint32_t)p_isotd->offsetPSW[p_g_ed->psw_idx] & 0x00000FFF; + + if (p_g_ed->psw_idx < RZA_IO_RegRead_32(&p_isotd->control, TD_CTL_SHFT_FC, TD_CTL_MSK_FC)) { + data_size = p_isotd->offsetPSW[p_g_ed->psw_idx + 1] - p_isotd->offsetPSW[p_g_ed->psw_idx]; + } else { + data_size = (uint32_t)p_isotd->bufEnd - buff_addr + 1; + } + p_isotd->offsetPSW[p_g_ed->psw_idx] = (uint16_t)data_size; + + get_td_info(p_g_ed, &td_info); + p_g_ed->trans_wait = 1; + if (connect_status == 0) { + ohciwrapp_loc_TransEnd(p_g_ed->pipe_no, TD_CC_DEVICENOTRESPONDING); + } else { + if (td_info.direction == 1) { + usbx_host_start_send_transfer(p_g_ed->pipe_no, data_size, (uint8_t *)buff_addr); + } else { + usbx_host_start_receive_transfer(p_g_ed->pipe_no, data_size, (uint8_t *)buff_addr); + } + } +} +#endif + +static void connect_check(void) { + uint32_t type = 0; + uint16_t stat; + uint16_t devadd = 0; + uint32_t wk_HcRhPortStatus1 = p_usb_reg->HcRhPortStatus1; + + if (usbx_host_CheckAttach() == USB_HOST_ATTACH) { + type = 1; + } + + if ((((wk_HcRhPortStatus1 & OR_RH_PORT_CCS) == 0) && (type == 0)) + || (((wk_HcRhPortStatus1 & OR_RH_PORT_CCS) != 0) && (type != 0))) { + return; + } + + if (type == 0) { + usbx_host_UsbDetach(); + wk_HcRhPortStatus1 &= ~OR_RH_PORT_CCS; + } else { + usbx_host_UsbAttach(); + stat = usbx_host_UsbBusReset(); + RZA_IO_RegWrite_16(&devadd, 0, USB_DEVADDn_UPPHUB_SHIFT, USB_DEVADDn_UPPHUB); + RZA_IO_RegWrite_16(&devadd, 0, USB_DEVADDn_HUBPORT_SHIFT, USB_DEVADDn_HUBPORT); + if (stat == USB_HOST_HSMODE) { + wk_HcRhPortStatus1 &= ~OR_RH_PORT_LSDA; + RZA_IO_RegWrite_16(&USB20X.SOFCFG, 0, USB_SOFCFG_TRNENSEL_SHIFT, USB_SOFCFG_TRNENSEL); + g_usbx_host_UsbDeviceSpeed = USB_HOST_HIGH_SPEED; + } else if (stat == USB_HOST_FSMODE) { + wk_HcRhPortStatus1 &= ~OR_RH_PORT_LSDA; + RZA_IO_RegWrite_16(&USB20X.SOFCFG, 0, USB_SOFCFG_TRNENSEL_SHIFT, USB_SOFCFG_TRNENSEL); + g_usbx_host_UsbDeviceSpeed = USB_HOST_FULL_SPEED; + } else { + wk_HcRhPortStatus1 |= OR_RH_PORT_LSDA; + RZA_IO_RegWrite_16(&USB20X.SOFCFG, 1, USB_SOFCFG_TRNENSEL_SHIFT, USB_SOFCFG_TRNENSEL); + g_usbx_host_UsbDeviceSpeed = USB_HOST_LOW_SPEED; + } + RZA_IO_RegWrite_16(&devadd, g_usbx_host_UsbDeviceSpeed, USB_DEVADDn_USBSPD_SHIFT, USB_DEVADDn_USBSPD); + usbx_host_init_pipe_status(); + usbx_host_set_devadd(USB_HOST_DEVICE_0, &devadd); + wk_HcRhPortStatus1 |= OR_RH_PORT_CCS; + } + wk_HcRhPortStatus1 |= OR_RH_PORT_CSC; + p_usb_reg->HcRhPortStatus1 = wk_HcRhPortStatus1; + p_usb_reg->HcInterruptStatus |= OR_INTR_STATUS_RHSC; + (void)memset(&split_ctl, 0, sizeof(split_ctl)); +} + +void ohciwrapp_loc_Connect(uint32_t type) { + uint32_t cnt; + + connect_status = type; + connect_change = type; + if (type == 0) { + if (ctl_ed.trans_wait == 1) { + ohciwrapp_loc_TransEnd(ctl_ed.pipe_no, TD_CC_DEVICENOTRESPONDING); + } + if (blk_ed.trans_wait == 1) { + ohciwrapp_loc_TransEnd(blk_ed.pipe_no, TD_CC_DEVICENOTRESPONDING); + } + for (cnt = 0; cnt< INT_TRANS_MAX_NUM; cnt++) { + if (int_ed[cnt].trans_wait == 1) { + ohciwrapp_loc_TransEnd(int_ed[cnt].pipe_no, TD_CC_DEVICENOTRESPONDING); + } + } +#if (ISO_TRANS_MAX_NUM > 0) + for (cnt = 0; cnt< ISO_TRANS_MAX_NUM; cnt++) { + if (iso_ed[cnt].trans_wait == 1) { + hced_t *p_ed = iso_ed[cnt].p_curr_ed; + + p_ed->headTD |= ED_HALTED; + ohciwrapp_loc_TransEnd(iso_ed[cnt].pipe_no, TD_CC_DEVICENOTRESPONDING); + } + } +#endif + } + (void)osSemaphoreRelease(semid_cb); +} + +void ohciwrapp_loc_TransEnd(uint32_t pipe, uint32_t ConditionCode) { + uint32_t periodic = 0; + uint32_t cnt; + uint32_t sqmon; + hced_t *p_ed; + genelal_ed_t *p_wait_ed = NULL; + + if (ctl_ed.pipe_no == pipe) { + p_wait_ed = &ctl_ed; + } else if (blk_ed.pipe_no == pipe) { + p_wait_ed = &blk_ed; + } else { +#if (ISO_TRANS_MAX_NUM > 0) + if (p_wait_ed == NULL) { + for (cnt = 0; cnt< ISO_TRANS_MAX_NUM; cnt++) { + if (iso_ed[cnt].pipe_no == pipe) { + p_wait_ed = &iso_ed[cnt]; + break; + } + } + } +#endif + if (p_wait_ed == NULL) { + for (cnt = 0; cnt< INT_TRANS_MAX_NUM; cnt++) { + if (int_ed[cnt].pipe_no == pipe) { + p_wait_ed = &int_ed[cnt]; + periodic = 1; + break; + } + } + } + } + + if (p_wait_ed == NULL) { + return; + } + p_ed = p_wait_ed->p_curr_ed; + if (p_ed == NULL) { + return; + } + + if ((p_ed->control & ED_FORMAT) == 0) { + hctd_t *p_td = (hctd_t *)p_wait_ed->p_curr_td; + + if (p_td != NULL) { + if (ConditionCode == TD_CC_NOERROR) { + /* ErrorCount */ + RZA_IO_RegWrite_32(&p_td->control, 0, TD_CTL_SHFT_EC, TD_CTL_MSK_EC); + + /* CurrentBufferPointer */ + p_td->currBufPtr += ((uint32_t)p_td->bufEnd - (uint32_t)p_td->currBufPtr + 1) - g_usbx_host_data_count[pipe]; + } else { + /* ErrorCount */ + RZA_IO_RegWrite_32(&p_td->control, 3, TD_CTL_SHFT_EC, TD_CTL_MSK_EC); + } + + /* DataToggle */ + sqmon = usbx_host_get_sqmon(pipe); + RZA_IO_RegWrite_32(&p_td->control, sqmon, TD_CTL_SHFT_T, TD_CTL_MSK_T); + if (sqmon == 0) { + p_ed->headTD &= ~ED_TOGLE_CARRY; + } else { + p_ed->headTD |= ED_TOGLE_CARRY; + } + + /* ConditionCode */ + RZA_IO_RegWrite_32(&p_td->control, ConditionCode, TD_CTL_SHFT_CC, TD_CTL_MSK_CC); + + if (p_wait_ed == &ctl_ed) { + chk_split_trans_setting(&ctl_ed); + } + chk_genelal_td_done(p_wait_ed); + + if (periodic != 0) { + if (chk_genelal_ed(p_wait_ed) != 0) { + int_trans(p_wait_ed); + } else { + p_wait_ed->trans_wait = 0; + (void)osSemaphoreRelease(p_wait_ed->semid_wait); + } + } else { + p_wait_ed->trans_wait = 0; + (void)osSemaphoreRelease(p_wait_ed->semid_wait); + } + } + } else { +#if (ISO_TRANS_MAX_NUM > 0) + hcisotd_t *p_isotd = (hcisotd_t *)p_wait_ed->p_curr_td; + uint32_t next_trans = 0; + + if (p_isotd != NULL) { + usbx_host_stop_transfer(pipe); + p_usb_reg->HcFmNumber = ((p_isotd->control & 0x0000FFFF) + p_wait_ed->psw_idx) & 0x0000FFFF; + + /* Size of packet */ + p_isotd->offsetPSW[p_wait_ed->psw_idx] -= g_usbx_host_data_count[pipe]; + + /* ConditionCode */ + RZA_IO_RegWrite_32(&p_isotd->control, ConditionCode, TD_CTL_SHFT_CC, TD_CTL_MSK_CC); + RZA_IO_RegWrite_16(&p_isotd->offsetPSW[p_wait_ed->psw_idx], + (uint16_t)ConditionCode, TD_PSW_SHFT_CC, TD_PSW_MSK_CC); + + if (usbx_host_CheckAttach() != USB_HOST_ATTACH) { + p_ed->headTD |= ED_HALTED; + } + if (p_wait_ed->psw_idx >= RZA_IO_RegRead_32(&p_isotd->control, TD_CTL_SHFT_FC, TD_CTL_MSK_FC)) { + p_wait_ed->psw_idx = 0; + chk_iso_td_done(p_wait_ed); + } else { + p_wait_ed->psw_idx++; + } + if (chk_iso_ed(p_wait_ed) != 0) { + iso_trans(p_wait_ed); + next_trans = 1; + } + if (next_trans == 0) { + p_wait_ed->trans_wait = 0; + (void)osSemaphoreRelease(p_wait_ed->semid_wait); + } + } +#endif + } + +} +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/ohci_wrapp_RZ_A1.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,60 @@ +/* Copyright (c) 2010-2011 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#ifndef OHCI_WRAPP_RZ_A1_H +#define OHCI_WRAPP_RZ_A1_H + +#ifdef __cplusplus +extern "C" { +#endif + +#define OHCI_REG_REVISION (0x00) /* HcRevision */ +#define OHCI_REG_CONTROL (0x04) /* HcControl */ +#define OHCI_REG_COMMANDSTATUS (0x08) /* HcCommandStatus */ +#define OHCI_REG_INTERRUPTSTATUS (0x0C) /* HcInterruptStatus */ +#define OHCI_REG_INTERRUPTENABLE (0x10) /* HcInterruptEnable */ +#define OHCI_REG_INTERRUPTDISABLE (0x14) /* HcInterruptDisable */ +#define OHCI_REG_HCCA (0x18) /* HcHCCA */ +#define OHCI_REG_PERIODCURRENTED (0x1C) /* HcPeriodCurrentED */ +#define OHCI_REG_CONTROLHEADED (0x20) /* HcControlHeadED */ +#define OHCI_REG_CONTROLCURRENTED (0x24) /* HcControlCurrentED */ +#define OHCI_REG_BULKHEADED (0x28) /* HcBulkHeadED */ +#define OHCI_REG_BULKCURRENTED (0x2C) /* HcBulkCurrentED */ +#define OHCI_REG_DONEHEADED (0x30) /* HcDoneHead */ +#define OHCI_REG_FMINTERVAL (0x34) /* HcFmInterval */ +#define OHCI_REG_FMREMAINING (0x38) /* HcFmRemaining */ +#define OHCI_REG_FMNUMBER (0x3C) /* HcFmNumber */ +#define OHCI_REG_PERIODICSTART (0x40) /* HcPeriodicStart */ +#define OHCI_REG_LSTHRESHOLD (0x44) /* HcLSThreshold */ +#define OHCI_REG_RHDESCRIPTORA (0x48) /* HcRhDescriptorA */ +#define OHCI_REG_RHDESCRIPTORB (0x4C) /* HcRhDescriptorB */ +#define OHCI_REG_RHSTATUS (0x50) /* HcRhStatus */ +#define OHCI_REG_RHPORTSTATUS1 (0x54) /* HcRhPortStatus1 */ + +typedef void (usbisr_fnc_t)(void); + +extern void ohciwrapp_init(usbisr_fnc_t *p_usbisr_fnc); +extern uint32_t ohciwrapp_reg_r(uint32_t reg_ofs); +extern void ohciwrapp_reg_w(uint32_t reg_ofs, uint32_t set_data); +extern void ohciwrapp_interrupt(uint32_t int_sense); + +#ifdef __cplusplus +} +#endif + +#endif /* OHCI_WRAPP_RZ_A1_H */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/ohci_wrapp_RZ_A1_local.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,49 @@ +/* Copyright (c) 2010-2011 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#ifndef OHCI_WRAPP_RZ_A1_LOCAL_H +#define OHCI_WRAPP_RZ_A1_LOCAL_H + +#ifdef __cplusplus +extern "C" { +#endif + +/* ConditionCode */ +#define TD_CC_NOERROR (0) +#define TD_CC_CRC (1) +#define TD_CC_BITSTUFFING (2) +#define TD_CC_DATATOGGLEMISMATCH (3) +#define TD_CC_STALL (4) +#define TD_CC_DEVICENOTRESPONDING (5) +#define TD_CC_PIDCHECKFAILURE (6) +#define TD_CC_UNEXPECTEDPID (7) +#define TD_CC_DATAOVERRUN (8) +#define TD_CC_DATAUNDERRUN (9) +#define TD_CC_BUFFEROVERRUN (12) +#define TD_CC_BUFFERUNDERRUN (13) +#define TD_CC_NOT_ACCESSED_1 (14) +#define TD_CC_NOT_ACCESSED_2 (15) + +extern void ohciwrapp_loc_Connect(uint32_t type); +extern void ohciwrapp_loc_TransEnd(uint32_t pipe, uint32_t ConditionCode); + +#ifdef __cplusplus +} +#endif + +#endif /* OHCI_WRAPP_RZ_A1_LOCAL_H */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/ohci_wrapp_pipe.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,189 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "devdrv_usb_host_api.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/********************************************************************************************************/ +/* Endpoint Configuration Data Format */ +/********************************************************************************************************/ +/* LINE1: Pipe Window Select Register */ +/* CPU Access PIPE : USB_HOST_PIPE1 to USB_HOST_PIPE9 [ ### SET ### ] */ +/* LINE2: Pipe Configuration Register */ +/* Transfer Type : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* Buffer Ready interrupt : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* Double Buffer Mode : USB_HOST_DBLBON / USB_HOST_DBLBOFF [ ### SET ### ] */ +/* Continuous Transmit: : USB_HOST_CNTMDON / USB_HOST_CNTMDOFF [ ### SET ### ] */ +/* Short NAK : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* Transfer Direction : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* Endpoint Number : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* LINE3: Pipe Buffer Configuration Register */ +/* Buffer Size : (uint16_t)((uint16_t)(((x) / 64) - 1) << 10) */ +/* [ ### SET ### ] */ +/* Buffer Top Number : (uint16_t)(x) [ ### SET ### ] */ +/* LINE4: Pipe Maxpacket Size Register */ +/* Max Packet Size : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* LINE5: Pipe Cycle Configuration Register (0x6C) */ +/* ISO Buffer Flush Mode : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* ISO Interval Value : USB_HOST_NONE [ USB_HOST_NONE ] */ +/* LINE6: use FIFO port */ +/* : USB_HOST_CUSE [ ### SET ### ] */ +/* : USB_HOST_D0USE / USB_HOST_D1USE */ +/* : USB_HOST_D0DMA / USB_HOST_D0DMA */ +/********************************************************************************************************/ + +/* Device Address 1 */ +USB_HOST_CFG_PIPETBL_t usb_host_blk_ep_tbl1[ ] = +{ + { + USB_HOST_PIPE3, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBON | USB_HOST_CNTMDON | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((1024) / 64) - 1) << 10) | (uint16_t)(8), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D0USE + }, + + { + /* Pipe end */ + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF + } +}; + +USB_HOST_CFG_PIPETBL_t usb_host_int_ep_tbl1[ ] = +{ + { + USB_HOST_PIPE6, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBOFF | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((64) / 64) - 1) << 10) | (uint16_t)(40), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + USB_HOST_PIPE7, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBOFF | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((64) / 64) - 1) << 10) | (uint16_t)(41), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + USB_HOST_PIPE8, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBOFF | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((64) / 64) - 1) << 10) | (uint16_t)(42), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + USB_HOST_PIPE9, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBOFF | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((64) / 64) - 1) << 10) | (uint16_t)(43), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + /* Pipe end */ + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF + } +}; + +USB_HOST_CFG_PIPETBL_t usb_host_iso_ep_tbl1[ ] = +{ + { + USB_HOST_PIPE1, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBON | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((1024) / 64) - 1) << 10) | (uint16_t)(44), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + USB_HOST_PIPE2, + /* TYPE / BFRE / DBLB / CNTMD / SHTNAK / DIR / EPNUM */ + USB_HOST_NONE | USB_HOST_NONE | USB_HOST_DBLBON | USB_HOST_CNTMDOFF | USB_HOST_NONE | USB_HOST_NONE | USB_HOST_NONE, + (uint16_t)((uint16_t)(((1024) / 64) - 1) << 10) | (uint16_t)(76), + USB_HOST_NONE, + USB_HOST_NONE, + USB_HOST_D1USE + }, + + { + /* Pipe end */ + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF, + 0xFFFF + } +}; + + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/inc/usb0_host.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,156 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB0_HOST_H +#define USB0_HOST_H + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "devdrv_usb_host_api.h" +#include "usb_host.h" + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +extern const uint16_t g_usb0_host_bit_set[]; +extern uint32_t g_usb0_host_data_count[USB_HOST_MAX_PIPE_NO + 1]; +extern uint8_t *g_usb0_host_data_pointer[USB_HOST_MAX_PIPE_NO + 1]; + +extern uint16_t g_usb0_host_PipeIgnore[]; +extern uint16_t g_usb0_host_PipeTbl[]; +extern uint16_t g_usb0_host_pipe_status[]; +extern uint32_t g_usb0_host_PipeDataSize[]; + +extern USB_HOST_DMA_t g_usb0_host_DmaInfo[]; +extern uint16_t g_usb0_host_DmaPipe[]; +extern uint16_t g_usb0_host_DmaBval[]; +extern uint16_t g_usb0_host_DmaStatus[]; + +extern uint16_t g_usb0_host_driver_state; +extern uint16_t g_usb0_host_ConfigNum; +extern uint16_t g_usb0_host_CmdStage; +extern uint16_t g_usb0_host_bchg_flag; +extern uint16_t g_usb0_host_detach_flag; +extern uint16_t g_usb0_host_attach_flag; + +extern uint16_t g_usb0_host_UsbAddress; +extern uint16_t g_usb0_host_setUsbAddress; +extern uint16_t g_usb0_host_default_max_packet[USB_HOST_MAX_DEVICE + 1]; +extern uint16_t g_usb0_host_UsbDeviceSpeed; +extern uint16_t g_usb0_host_SupportUsbDeviceSpeed; + +extern uint16_t g_usb0_host_SavReq; +extern uint16_t g_usb0_host_SavVal; +extern uint16_t g_usb0_host_SavIndx; +extern uint16_t g_usb0_host_SavLen; + +extern uint16_t g_usb0_host_pipecfg[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb0_host_pipebuf[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb0_host_pipemaxp[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb0_host_pipeperi[USB_HOST_MAX_PIPE_NO + 1]; + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +/* ==== common ==== */ +void usb0_host_dma_stop_d0(uint16_t pipe, uint32_t remain); +void usb0_host_dma_stop_d1(uint16_t pipe, uint32_t remain); +uint16_t usb0_host_is_hispeed(void); +uint16_t usb0_host_is_hispeed_enable(void); +uint16_t usb0_host_start_send_transfer(uint16_t pipe, uint32_t size, uint8_t *data); +uint16_t usb0_host_write_buffer(uint16_t pipe); +uint16_t usb0_host_write_buffer_c(uint16_t pipe); +uint16_t usb0_host_write_buffer_d0(uint16_t pipe); +uint16_t usb0_host_write_buffer_d1(uint16_t pipe); +void usb0_host_start_receive_transfer(uint16_t pipe, uint32_t size, uint8_t *data); +uint16_t usb0_host_read_buffer(uint16_t pipe); +uint16_t usb0_host_read_buffer_c(uint16_t pipe); +uint16_t usb0_host_read_buffer_d0(uint16_t pipe); +uint16_t usb0_host_read_buffer_d1(uint16_t pipe); +uint16_t usb0_host_change_fifo_port(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw); +void usb0_host_set_curpipe(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw); +void usb0_host_set_curpipe2(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw, uint16_t dfacc); +uint16_t usb0_host_get_mbw(uint32_t trncount, uint32_t dtptr); +uint16_t usb0_host_read_dma(uint16_t pipe); +void usb0_host_stop_transfer(uint16_t pipe); +void usb0_host_brdy_int(uint16_t status, uint16_t int_enb); +void usb0_host_nrdy_int(uint16_t status, uint16_t int_enb); +void usb0_host_bemp_int(uint16_t status, uint16_t int_enb); +void usb0_host_setting_interrupt(uint8_t level); +void usb0_host_reset_module(uint16_t clockmode); +uint16_t usb0_host_get_buf_size(uint16_t pipe); +uint16_t usb0_host_get_mxps(uint16_t pipe); +void usb0_host_enable_brdy_int(uint16_t pipe); +void usb0_host_disable_brdy_int(uint16_t pipe); +void usb0_host_clear_brdy_sts(uint16_t pipe); +void usb0_host_enable_bemp_int(uint16_t pipe); +void usb0_host_disable_bemp_int(uint16_t pipe); +void usb0_host_clear_bemp_sts(uint16_t pipe); +void usb0_host_enable_nrdy_int(uint16_t pipe); +void usb0_host_disable_nrdy_int(uint16_t pipe); +void usb0_host_clear_nrdy_sts(uint16_t pipe); +void usb0_host_set_pid_buf(uint16_t pipe); +void usb0_host_set_pid_nak(uint16_t pipe); +void usb0_host_set_pid_stall(uint16_t pipe); +void usb0_host_clear_pid_stall(uint16_t pipe); +uint16_t usb0_host_get_pid(uint16_t pipe); +void usb0_host_set_sqclr(uint16_t pipe); +void usb0_host_set_sqset(uint16_t pipe); +void usb0_host_set_csclr(uint16_t pipe); +void usb0_host_aclrm(uint16_t pipe); +void usb0_host_set_aclrm(uint16_t pipe); +void usb0_host_clr_aclrm(uint16_t pipe); +uint16_t usb0_host_get_sqmon(uint16_t pipe); +uint16_t usb0_host_get_inbuf(uint16_t pipe); + +/* ==== host ==== */ +void usb0_host_init_pipe_status(void); +int32_t usb0_host_CtrlTransStart(uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len, uint8_t *Buf); +void usb0_host_SetupStage(uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len); +void usb0_host_CtrlReadStart(uint32_t Bsize, uint8_t *Table); +uint16_t usb0_host_CtrlWriteStart(uint32_t Bsize, uint8_t *Table); +void usb0_host_StatusStage(void); +void usb0_host_get_devadd(uint16_t addr, uint16_t *devadd); +void usb0_host_set_devadd(uint16_t addr, uint16_t *devadd); +void usb0_host_InitModule(void); +uint16_t usb0_host_CheckAttach(void); +void usb0_host_UsbDetach(void); +void usb0_host_UsbDetach2(void); +void usb0_host_UsbAttach(void); +uint16_t usb0_host_UsbBusReset(void); +int32_t usb0_host_UsbResume(void); +int32_t usb0_host_UsbSuspend(void); +void usb0_host_Enable_DetachINT(void); +void usb0_host_Disable_DetachINT(void); +void usb0_host_UsbStateManager(void); + + +#endif /* USB0_HOST_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/inc/usb0_host_api.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,112 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_api.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB0_HOST_API_H +#define USB0_HOST_API_H + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Variable Externs +*******************************************************************************/ + + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +void usb0_host_interrupt(uint32_t int_sense); +void usb0_host_dma_interrupt_d0fifo(uint32_t int_sense); +void usb0_host_dma_interrupt_d1fifo(uint32_t int_sense); + +uint16_t usb0_api_host_init(uint8_t int_level, uint16_t mode, uint16_t clockmode); +int32_t usb0_api_host_enumeration(uint16_t devadr); +int32_t usb0_api_host_detach(void); +int32_t usb0_api_host_data_in(uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t usb0_api_host_data_out(uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t usb0_api_host_control_transfer(uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len, uint8_t *Buf); +int32_t usb0_api_host_set_endpoint(uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t *configdescriptor); +int32_t usb0_api_host_clear_endpoint(USB_HOST_CFG_PIPETBL_t *user_table); +int32_t usb0_api_host_clear_endpoint_pipe(uint16_t pipe_sel, USB_HOST_CFG_PIPETBL_t *user_table); +uint16_t usb0_api_host_SetEndpointTable(uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t* Table); +int32_t usb0_api_host_data_count(uint16_t pipe, uint32_t *data_count); + +int32_t usb0_api_host_GetDeviceDescriptor(uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t usb0_api_host_GetConfigDescriptor(uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t usb0_api_host_SetConfig(uint16_t devadr, uint16_t confignum); +int32_t usb0_api_host_SetInterface(uint16_t devadr, uint16_t interface_alt, uint16_t interface_index); +int32_t usb0_api_host_ClearStall(uint16_t devadr, uint16_t ep_dir); +uint16_t usb0_api_host_GetUsbDeviceState(void); + +void usb0_api_host_elt_4_4(void); +void usb0_api_host_elt_4_5(void); +void usb0_api_host_elt_4_6(void); +void usb0_api_host_elt_4_7(void); +void usb0_api_host_elt_4_8(void); +void usb0_api_host_elt_4_9(void); +void usb0_api_host_elt_get_desc(void); + +void usb0_host_EL_ModeInit(void); +void usb0_host_EL_SetUACT(void); +void usb0_host_EL_ClearUACT(void); +void usb0_host_EL_SetTESTMODE(uint16_t mode); +void usb0_host_EL_ClearNRDYSTS(uint16_t pipe); +uint16_t usb0_host_EL_GetINTSTS1(void); +void usb0_host_EL_UsbBusReset(void); +void usb0_host_EL_UsbAttach(void); +void usb0_host_EL_SetupStage(uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len); +void usb0_host_EL_StatusStage(void); +void usb0_host_EL_CtrlReadStart(uint32_t Bsize, uint8_t *Table); +int32_t usb0_host_EL_UsbSuspend(void); +int32_t usb0_host_EL_UsbResume(void); + +#if 0 /* prototype in devdrv_usb_host_api.h */ +uint16_t Userdef_USB_usb0_host_d0fifo_dmaintid(void); +uint16_t Userdef_USB_usb0_host_d1fifo_dmaintid(void); +void Userdef_USB_usb0_host_attach(void); +void Userdef_USB_usb0_host_detach(void); +void Userdef_USB_usb0_host_delay_1ms(void); +void Userdef_USB_usb0_host_delay_xms(uint32_t msec); +void Userdef_USB_usb0_host_delay_10us(uint32_t usec); +void Userdef_USB_usb0_host_delay_500ns(void); +void Userdef_USB_usb0_host_start_dma(USB_HOST_DMA_t *dma, uint16_t dfacc); +uint32_t Userdef_USB_usb0_host_stop_dma0(void); +uint32_t Userdef_USB_usb0_host_stop_dma1(void); +#endif + +#endif /* USB0_HOST_API_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/inc/usb0_host_dmacdrv.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,139 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_dmacdrv.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB0_HOST_DMACDRV_H +#define USB0_HOST_DMACDRV_H + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ +typedef struct dmac_transinfo +{ + uint32_t src_addr; /* Transfer source address */ + uint32_t dst_addr; /* Transfer destination address */ + uint32_t count; /* Transfer byte count */ + uint32_t src_size; /* Transfer source data size */ + uint32_t dst_size; /* Transfer destination data size */ + uint32_t saddr_dir; /* Transfer source address direction */ + uint32_t daddr_dir; /* Transfer destination address direction */ +} dmac_transinfo_t; + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +/* ==== Transfer specification of the sample program ==== */ +#define DMAC_SAMPLE_SINGLE (0) /* Single transfer */ +#define DMAC_SAMPLE_CONTINUATION (1) /* Continuous transfer (use REN bit) */ + +/* ==== DMA modes ==== */ +#define DMAC_MODE_REGISTER (0) /* Register mode */ +#define DMAC_MODE_LINK (1) /* Link mode */ + +/* ==== Transfer requests ==== */ +#define DMAC_REQ_MODE_EXT (0) /* External request */ +#define DMAC_REQ_MODE_PERI (1) /* On-chip peripheral module request */ +#define DMAC_REQ_MODE_SOFT (2) /* Auto-request (request by software) */ + +/* ==== DMAC transfer sizes ==== */ +#define DMAC_TRANS_SIZE_8 (0) /* 8 bits */ +#define DMAC_TRANS_SIZE_16 (1) /* 16 bits */ +#define DMAC_TRANS_SIZE_32 (2) /* 32 bits */ +#define DMAC_TRANS_SIZE_64 (3) /* 64 bits */ +#define DMAC_TRANS_SIZE_128 (4) /* 128 bits */ +#define DMAC_TRANS_SIZE_256 (5) /* 256 bits */ +#define DMAC_TRANS_SIZE_512 (6) /* 512 bits */ +#define DMAC_TRANS_SIZE_1024 (7) /* 1024 bits */ + +/* ==== Address increment for transferring ==== */ +#define DMAC_TRANS_ADR_NO_INC (1) /* Not increment */ +#define DMAC_TRANS_ADR_INC (0) /* Increment */ + +/* ==== Method for detecting DMA request ==== */ +#define DMAC_REQ_DET_FALL (0) /* Falling edge detection */ +#define DMAC_REQ_DET_RISE (1) /* Rising edge detection */ +#define DMAC_REQ_DET_LOW (2) /* Low level detection */ +#define DMAC_REQ_DET_HIGH (3) /* High level detection */ + +/* ==== Request Direction ==== */ +#define DMAC_REQ_DIR_SRC (0) /* DMAREQ is the source/ DMAACK is active when reading */ +#define DMAC_REQ_DIR_DST (1) /* DMAREQ is the destination/ DMAACK is active when writing */ + +/* ==== Descriptors ==== */ +#define DMAC_DESC_HEADER (0) /* Header */ +#define DMAC_DESC_SRC_ADDR (1) /* Source Address */ +#define DMAC_DESC_DST_ADDR (2) /* Destination Address */ +#define DMAC_DESC_COUNT (3) /* Transaction Byte */ +#define DMAC_DESC_CHCFG (4) /* Channel Confg */ +#define DMAC_DESC_CHITVL (5) /* Channel Interval */ +#define DMAC_DESC_CHEXT (6) /* Channel Extension */ +#define DMAC_DESC_LINK_ADDR (7) /* Link Address */ + +/* ==== On-chip peripheral module requests ===== */ +typedef enum dmac_request_factor +{ + DMAC_REQ_USB0_DMA0_TX, /* USB_0 channel 0 transmit FIFO empty */ + DMAC_REQ_USB0_DMA0_RX, /* USB_0 channel 0 receive FIFO full */ + DMAC_REQ_USB0_DMA1_TX, /* USB_0 channel 1 transmit FIFO empty */ + DMAC_REQ_USB0_DMA1_RX, /* USB_0 channel 1 receive FIFO full */ + DMAC_REQ_USB1_DMA0_TX, /* USB_1 channel 0 transmit FIFO empty */ + DMAC_REQ_USB1_DMA0_RX, /* USB_1 channel 0 receive FIFO full */ + DMAC_REQ_USB1_DMA1_TX, /* USB_1 channel 1 transmit FIFO empty */ + DMAC_REQ_USB1_DMA1_RX, /* USB_1 channel 1 receive FIFO full */ +} dmac_request_factor_t; + + +/******************************************************************************* +Variable Externs +*******************************************************************************/ + + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +void usb0_host_DMAC1_PeriReqInit(const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction); +int32_t usb0_host_DMAC1_Open(uint32_t req); +void usb0_host_DMAC1_Close(uint32_t * remain); +void usb0_host_DMAC1_Load_Set(uint32_t src_addr, uint32_t dst_addr, uint32_t count); + +void usb0_host_DMAC2_PeriReqInit(const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction); +int32_t usb0_host_DMAC2_Open(uint32_t req); +void usb0_host_DMAC2_Close(uint32_t * remain); +void usb0_host_DMAC2_Load_Set(uint32_t src_addr, uint32_t dst_addr, uint32_t count); + +#endif /* USB0_HOST_DMACDRV_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/src/common/usb0_host_dataio.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,2835 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_dataio.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +static uint16_t g_usb0_host_mbw[(USB_HOST_MAX_PIPE_NO + 1)]; + +static void usb0_host_start_receive_trns_c(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb0_host_start_receive_trns_d0(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb0_host_start_receive_trns_d1(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb0_host_start_receive_dma_d0(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb0_host_start_receive_dma_d1(uint16_t pipe, uint32_t size, uint8_t *data); +static uint16_t usb0_host_read_dma_d0(uint16_t pipe); +static uint16_t usb0_host_read_dma_d1(uint16_t pipe); +static uint16_t usb0_host_write_dma_d0(uint16_t pipe); +static uint16_t usb0_host_write_dma_d1(uint16_t pipe); + +static void usb0_host_read_c_fifo(uint16_t pipe, uint16_t count); +static void usb0_host_write_c_fifo(uint16_t Pipe, uint16_t count); +static void usb0_host_read_d0_fifo(uint16_t pipe, uint16_t count); +static void usb0_host_write_d0_fifo(uint16_t pipe, uint16_t count); +static void usb0_host_read_d1_fifo(uint16_t pipe, uint16_t count); +static void usb0_host_write_d1_fifo(uint16_t pipe, uint16_t count); + +static void usb0_host_clear_transaction_counter(uint16_t pipe); +static void usb0_host_set_transaction_counter(uint16_t pipe, uint32_t count); + +static uint32_t usb0_host_com_get_dmasize(uint32_t trncount, uint32_t dtptr); + +static uint16_t usb0_host_set_dfacc_d0(uint16_t mbw, uint32_t count); +static uint16_t usb0_host_set_dfacc_d1(uint16_t mbw, uint32_t count); + + +/******************************************************************************* +* Function Name: usb0_host_start_send_transfer +* Description : Starts the USB data communication using pipe specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data data Address +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_start_send_transfer (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t status; + uint16_t usefifo; + uint16_t mbw; + + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + usb0_host_clear_bemp_sts(pipe); + usb0_host_clear_brdy_sts(pipe); + usb0_host_clear_nrdy_sts(pipe); + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + + usefifo = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + case USB_HOST_D0FIFO_DMA: + usefifo = USB_HOST_D0USE; + break; + + case USB_HOST_D1FIFO_USE: + case USB_HOST_D1FIFO_DMA: + usefifo = USB_HOST_D1USE; + break; + + default: + usefifo = USB_HOST_CUSE; + break; + }; + + usb0_host_set_curpipe(USB_HOST_PIPE0, usefifo, USB_HOST_NO, mbw); + + usb0_host_clear_transaction_counter(pipe); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + status = usb0_host_write_buffer(pipe); + + if (status != USB_HOST_FIFOERROR) + { + usb0_host_set_pid_buf(pipe); + } + + return status; +} + +/******************************************************************************* +* Function Name: usb0_host_write_buffer +* Description : Writes data in the buffer allocated in the pipe specified by +* : the argument. The FIFO for using is set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_write_buffer (uint16_t pipe) +{ + uint16_t status; + uint16_t usefifo; + + g_usb0_host_PipeIgnore[pipe] = 0; + usefifo = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + status = usb0_host_write_buffer_d0(pipe); + break; + + case USB_HOST_D1FIFO_USE: + status = usb0_host_write_buffer_d1(pipe); + break; + + case USB_HOST_D0FIFO_DMA: + status = usb0_host_write_dma_d0(pipe); + break; + + case USB_HOST_D1FIFO_DMA: + status = usb0_host_write_dma_d1(pipe); + break; + + default: + status = usb0_host_write_buffer_c(pipe); + break; + }; + + switch (status) + { + case USB_HOST_WRITING: /* Continue of data write */ + usb0_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + usb0_host_enable_brdy_int(pipe); /* Enable Ready Interrupt */ + break; + + case USB_HOST_WRITEEND: /* End of data write */ + case USB_HOST_WRITESHRT: /* End of data write */ + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + + usb0_host_clear_nrdy_sts(pipe); + usb0_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + + /* for last transfer */ + usb0_host_enable_bemp_int(pipe); /* Enable Empty Interrupt */ + break; + + case USB_HOST_WRITEDMA: /* DMA write */ + usb0_host_clear_nrdy_sts(pipe); + usb0_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + usb0_host_disable_bemp_int(pipe); /* Disable Empty Interrupt */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_write_buffer_c +* Description : Writes data in the buffer allocated in the pipe specified in +* : the argument. Writes data by CPU transfer using CFIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_write_buffer_c (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + + if (pipe == USB_HOST_PIPE0) + { + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_CFIFO_WRITE, mbw); + } + else + { + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_NO, mbw); + } + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb0_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb0_host_write_c_fifo(pipe, (uint16_t)count); + + if (g_usb0_host_data_count[pipe] < (uint32_t)size) + { + g_usb0_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB200.CFIFOCTR, + USB_CFIFOCTR_BVAL_SHIFT, + USB_CFIFOCTR_BVAL) == 0) + { + USB200.CFIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb0_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_write_buffer_d0 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by CPU transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_write_buffer_d0 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D0USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb0_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb0_host_write_d0_fifo(pipe, (uint16_t)count); + + if (g_usb0_host_data_count[pipe] < (uint32_t)size) + { + g_usb0_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB200.D0FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + USB200.D0FIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb0_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_write_buffer_d1 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by CPU transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_write_buffer_d1 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D1USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb0_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb0_host_write_d1_fifo(pipe, (uint16_t)count); + + if (g_usb0_host_data_count[pipe] < (uint32_t)size) + { + g_usb0_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB200.D1FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + USB200.D1FIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb0_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_write_dma_d0 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by DMA transfer using D0FIFO. +* : The DMA-ch for using is specified by Userdef_USB_usb0_host_start_dma(). +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND : Write end +* : USB_HOST_WRITESHRT : short data +* : USB_HOST_WRITING : Continue of data write +* : USB_HOST_WRITEDMA : Write DMA +* : USB_HOST_FIFOERROR : FIFO status +*******************************************************************************/ +static uint16_t usb0_host_write_dma_d0 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + count = g_usb0_host_data_count[pipe]; + + if (count != 0) + { + g_usb0_host_DmaPipe[USB_HOST_D0FIFO] = pipe; + + if ((count % size) != 0) + { + g_usb0_host_DmaBval[USB_HOST_D0FIFO] = 1; + } + else + { + g_usb0_host_DmaBval[USB_HOST_D0FIFO] = 0; + } + + dfacc = usb0_host_set_dfacc_d0(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 0; /* 8bit transfer */ + } + + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].fifo = USB_HOST_D0FIFO_DMA; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].dir = USB_HOST_BUF2FIFO; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].buffer = (uint32_t)g_usb0_host_data_pointer[pipe]; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].bytes = count; + + Userdef_USB_usb0_host_start_dma(&g_usb0_host_DmaInfo[USB_HOST_D0FIFO], dfacc); + + usb0_host_set_curpipe2(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw, dfacc); + + RZA_IO_RegWrite_16(&USB200.D0FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + + g_usb0_host_data_count[pipe] = 0; + g_usb0_host_data_pointer[pipe] += count; + + status = USB_HOST_WRITEDMA; /* DMA write */ + } + else + { + if (RZA_IO_RegRead_16(&USB200.D0FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + RZA_IO_RegWrite_16(&USB200.D0FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); /* Short Packet */ + } + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_write_dma_d1 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by DMA transfer using D1FIFO. +* : The DMA-ch for using is specified by Userdef_USB_usb0_host_start_dma(). +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND : Write end +* : USB_HOST_WRITESHRT : short data +* : USB_HOST_WRITING : Continue of data write +* : USB_HOST_WRITEDMA : Write DMA +* : USB_HOST_FIFOERROR : FIFO status +*******************************************************************************/ +static uint16_t usb0_host_write_dma_d1 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + count = g_usb0_host_data_count[pipe]; + + if (count != 0) + { + g_usb0_host_DmaPipe[USB_HOST_D1FIFO] = pipe; + + if ((count % size) != 0) + { + g_usb0_host_DmaBval[USB_HOST_D1FIFO] = 1; + } + else + { + g_usb0_host_DmaBval[USB_HOST_D1FIFO] = 0; + } + + dfacc = usb0_host_set_dfacc_d1(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 0; /* 8bit transfer */ + } + + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].fifo = USB_HOST_D1FIFO_DMA; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].dir = USB_HOST_BUF2FIFO; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].buffer = (uint32_t)g_usb0_host_data_pointer[pipe]; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].bytes = count; + + Userdef_USB_usb0_host_start_dma(&g_usb0_host_DmaInfo[USB_HOST_D1FIFO], dfacc); + + usb0_host_set_curpipe2(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw, dfacc); + + RZA_IO_RegWrite_16(&USB200.D1FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + + g_usb0_host_data_count[pipe] = 0; + g_usb0_host_data_pointer[pipe] += count; + + status = USB_HOST_WRITEDMA; /* DMA write */ + } + else + { + if (RZA_IO_RegRead_16(&USB200.D1FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + RZA_IO_RegWrite_16(&USB200.D1FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); /* Short Packet */ + } + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_transfer +* Description : Starts USB data reception using the pipe specified in the argument. +* : The FIFO for using is set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +void usb0_host_start_receive_transfer (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t usefifo; + + usb0_host_clear_bemp_sts(pipe); + usb0_host_clear_brdy_sts(pipe); + usb0_host_clear_nrdy_sts(pipe); + + usefifo = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + usb0_host_start_receive_trns_d0(pipe, size, data); + break; + + case USB_HOST_D1FIFO_USE: + usb0_host_start_receive_trns_d1(pipe, size, data); + break; + + case USB_HOST_D0FIFO_DMA: + usb0_host_start_receive_dma_d0(pipe, size, data); + break; + + case USB_HOST_D1FIFO_DMA: + usb0_host_start_receive_dma_d1(pipe, size, data); + break; + + default: + usb0_host_start_receive_trns_c(pipe, size, data); + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_trns_c +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using CFIFO. +* : When storing data in the buffer allocated in the pipe specified in the +* : argument, BRDY interrupt is generated to read data +* : in the interrupt. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb0_host_start_receive_trns_c (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb0_host_set_pid_nak(pipe); + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_PipeIgnore[pipe] = 0; + + g_usb0_host_PipeDataSize[pipe] = size; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_CFIFO_READ, mbw); + USB200.CFIFOCTR = USB_HOST_BITBCLR; + + usb0_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + + usb0_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_trns_d0 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, BRDY interrupt is generated to read data in the +* : interrupt. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb0_host_start_receive_trns_d0 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb0_host_set_pid_nak(pipe); + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_PipeIgnore[pipe] = 0; + + g_usb0_host_PipeDataSize[pipe] = size; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, mbw); + + usb0_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + + usb0_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_trns_d1 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using D1FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, BRDY interrupt is generated to read data. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb0_host_start_receive_trns_d1 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb0_host_set_pid_nak(pipe); + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_PipeIgnore[pipe] = 0; + + g_usb0_host_PipeDataSize[pipe] = size; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, mbw); + + usb0_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + + usb0_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_dma_d0 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by DMA transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, delivered read request to DMAC to read data from +* : the buffer by DMAC. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb0_host_start_receive_dma_d0 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb0_host_set_pid_nak(pipe); + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_PipeIgnore[pipe] = 0; + + g_usb0_host_PipeDataSize[pipe] = 0; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, mbw); + + usb0_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + usb0_host_read_dma(pipe); + + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + } + else + { + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + } + + usb0_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_start_receive_dma_d1 +* Description : Read data from the buffer allocated in the pipe specified in the argument. +* : Reads data by DMA transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, delivered read request to DMAC to read data from +* : the buffer by DMAC. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb0_host_start_receive_dma_d1 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb0_host_set_pid_nak(pipe); + g_usb0_host_data_count[pipe] = size; + g_usb0_host_data_pointer[pipe] = (uint8_t *)data; + g_usb0_host_PipeIgnore[pipe] = 0; + + g_usb0_host_PipeDataSize[pipe] = 0; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb0_host_get_mbw(size, (uint32_t)data); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, mbw); + + usb0_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + usb0_host_read_dma(pipe); + + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + } + else + { + usb0_host_enable_nrdy_int(pipe); + usb0_host_enable_brdy_int(pipe); + } + + usb0_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_read_buffer +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Uses FIF0 set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_read_buffer (uint16_t pipe) +{ + uint16_t status; + + g_usb0_host_PipeIgnore[pipe] = 0; + + if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_USE) + { + status = usb0_host_read_buffer_d0(pipe); + } + else if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_USE) + { + status = usb0_host_read_buffer_d1(pipe); + } + else + { + status = usb0_host_read_buffer_c(pipe); + } + + switch (status) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb0_host_disable_brdy_int(pipe); + g_usb0_host_PipeDataSize[pipe] -= g_usb0_host_data_count[pipe]; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + break; + + case USB_HOST_READOVER: /* buffer over */ + if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_USE) + { + USB200.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_USE) + { + USB200.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + USB200.CFIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#else + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; +#endif + g_usb0_host_PipeDataSize[pipe] -= g_usb0_host_data_count[pipe]; + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_buffer_c +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using CFIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_read_buffer_c (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb0_host_data_count[pipe]; + } + else if (g_usb0_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + } + + if (count == 0) /* 0 length packet */ + { + USB200.CFIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb0_host_read_c_fifo(pipe, (uint16_t)count); + } + + g_usb0_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_buffer_d0 +* Description : Reads data from the buffer allocated in the pipe specified in +* : the argument. +* : Reads data by CPU transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_read_buffer_d0 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t pipebuf_size; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D0USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb0_host_data_count[pipe]; + } + else if (g_usb0_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + else + { + pipebuf_size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + } + } + + if (count == 0) /* 0 length packet */ + { + USB200.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb0_host_read_d0_fifo(pipe, (uint16_t)count); + } + + g_usb0_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_buffer_d1 +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by CPU transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_read_buffer_d1 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t pipebuf_size; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D1USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb0_host_data_count[pipe]; + } + else if (g_usb0_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb0_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) !=0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + else + { + pipebuf_size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb0_host_set_pid_nak(pipe); /* Set NAK */ + } + } + } + + if (count == 0) /* 0 length packet */ + { + USB200.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb0_host_read_d1_fifo(pipe, (uint16_t)count); + } + + g_usb0_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_dma +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by DMA transfer using D0FIFO or D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb0_host_read_dma (uint16_t pipe) +{ + uint16_t status; + + g_usb0_host_PipeIgnore[pipe] = 0; + + if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_DMA) + { + status = usb0_host_read_dma_d0(pipe); + } + else + { + status = usb0_host_read_dma_d1(pipe); + } + + switch (status) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READZERO: /* End of data read */ + usb0_host_disable_brdy_int(pipe); + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb0_host_disable_brdy_int(pipe); + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + g_usb0_host_PipeDataSize[pipe] -= g_usb0_host_data_count[pipe]; + } + break; + + case USB_HOST_READOVER: /* buffer over */ + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + g_usb0_host_PipeDataSize[pipe] -= g_usb0_host_data_count[pipe]; + } +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#else + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; +#endif + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb0_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_dma_d0 +* Description : Writes data in the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by DMA transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +static uint16_t usb0_host_read_dma_d0 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + uint16_t pipebuf_size; + + g_usb0_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_READY; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + count = g_usb0_host_data_count[pipe]; + status = USB_HOST_READING; + } + else + { + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + count = g_usb0_host_data_count[pipe]; + } + else if (g_usb0_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + else + { + pipebuf_size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + } + } + + if (count == 0) /* 0 length packet */ + { + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + USB200.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear B_CLR */ + status = USB_HOST_READZERO; /* Null Packet receive */ + } + else + { + usb0_host_set_curpipe(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + /* transaction counter No set */ + /* FRDY = 1, DTLN = 0 -> BRDY */ + } + } + else + { + dfacc = usb0_host_set_dfacc_d0(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size = 0; /* 8bit transfer */ + } + + g_usb0_host_DmaPipe[USB_HOST_D0FIFO] = pipe; /* not use in read operation */ + g_usb0_host_DmaBval[USB_HOST_D0FIFO] = 0; /* not use in read operation */ + + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].fifo = USB_HOST_D0FIFO_DMA; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].dir = USB_HOST_FIFO2BUF; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].buffer = (uint32_t)g_usb0_host_data_pointer[pipe]; + g_usb0_host_DmaInfo[USB_HOST_D0FIFO].bytes = count; + + if (status == USB_HOST_READING) + { + g_usb0_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_BUSY; + } + else + { + g_usb0_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_BUSYEND; + } + + Userdef_USB_usb0_host_start_dma(&g_usb0_host_DmaInfo[USB_HOST_D0FIFO], dfacc); + + usb0_host_set_curpipe2(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw, dfacc); + + RZA_IO_RegWrite_16(&USB200.D0FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + g_usb0_host_data_count[pipe] -= count; + g_usb0_host_data_pointer[pipe] += count; + g_usb0_host_PipeDataSize[pipe] += count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_read_dma_d1 +* Description : Reads data from the buffer allocated in the pipe specified in +* : the argument. +* : Reads data by DMA transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +static uint16_t usb0_host_read_dma_d1 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + uint16_t pipebuf_size; + + g_usb0_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_READY; + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[pipe], (uint32_t)g_usb0_host_data_pointer[pipe]); + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + count = g_usb0_host_data_count[pipe]; + status = USB_HOST_READING; + } + else + { + buffer = usb0_host_change_fifo_port(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb0_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + count = g_usb0_host_data_count[pipe]; + } + else if (g_usb0_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + else + { + pipebuf_size = usb0_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + } + } + + if (count == 0) /* 0 length packet */ + { + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + USB200.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + status = USB_HOST_READZERO; /* Null Packet receive */ + } + else + { + usb0_host_set_curpipe(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + /* transaction counter No set */ + /* FRDY = 1, DTLN = 0 -> BRDY */ + } + } + else + { + dfacc = usb0_host_set_dfacc_d1(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size = 0; /* 8bit transfer */ + } + + g_usb0_host_DmaPipe[USB_HOST_D1FIFO] = pipe; /* not use in read operation */ + g_usb0_host_DmaBval[USB_HOST_D1FIFO] = 0; /* not use in read operation */ + + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].fifo = USB_HOST_D1FIFO_DMA; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].dir = USB_HOST_FIFO2BUF; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].buffer = (uint32_t)g_usb0_host_data_pointer[pipe]; + g_usb0_host_DmaInfo[USB_HOST_D1FIFO].bytes = count; + + if (status == USB_HOST_READING) + { + g_usb0_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_BUSY; + } + else + { + g_usb0_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_BUSYEND; + } + + Userdef_USB_usb0_host_start_dma(&g_usb0_host_DmaInfo[USB_HOST_D1FIFO], dfacc); + + usb0_host_set_curpipe2(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw, dfacc); + + RZA_IO_RegWrite_16(&USB200.D1FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + g_usb0_host_data_count[pipe] -= count; + g_usb0_host_data_pointer[pipe] += count; + g_usb0_host_PipeDataSize[pipe] += count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_change_fifo_port +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument. After allocating FIF0, waits in the software +* : till the corresponding pipe becomes ready. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* Return Value : USB_HOST_FIFOERROR ; Error +* : Others ; CFIFOCTR/D0FIFOCTR/D1FIFOCTR Register Value +*******************************************************************************/ +uint16_t usb0_host_change_fifo_port (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw) +{ + uint16_t buffer; + uint32_t loop; + volatile uint32_t loop2; + + usb0_host_set_curpipe(pipe, fifosel, isel, mbw); + + for (loop = 0; loop < 4; loop++) + { + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB200.CFIFOCTR; + break; + + case USB_HOST_D0USE: + case USB_HOST_D0DMA: + buffer = USB200.D0FIFOCTR; + break; + + case USB_HOST_D1USE: + case USB_HOST_D1DMA: + buffer = USB200.D1FIFOCTR; + break; + + default: + buffer = 0; + break; + } + + if ((buffer & USB_HOST_BITFRDY) == USB_HOST_BITFRDY) + { + return buffer; + } + + loop2 = 25; + + while (loop2-- > 0) + { + /* wait */ + } + } + + return USB_HOST_FIFOERROR; +} + +/******************************************************************************* +* Function Name: usb0_host_set_curpipe +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* Return Value : none +*******************************************************************************/ +void usb0_host_set_curpipe (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw) +{ + uint16_t buffer; + uint32_t loop; + volatile uint32_t loop2; + + g_usb0_host_mbw[pipe] = mbw; + + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB200.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(~isel & USB_HOST_BITISEL); + USB200.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(isel | pipe | mbw); + USB200.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D0DMA: + case USB_HOST_D0USE: + buffer = USB200.D0FIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + USB200.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB200.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D1DMA: + case USB_HOST_D1USE: + buffer = USB200.D1FIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + USB200.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB200.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + default: + break; + } + + /* Cautions !!! + * Depending on the external bus speed of CPU, you may need to wait for 450ns here. + * For details, please look at the data sheet. */ + loop2 = 100; + + while (loop2-- > 0) + { + /* wait */ + } +} + +/******************************************************************************* +* Function Name: usb0_host_set_curpipe2 +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument.(DFACC) +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* : uint16_t dfacc ; DFACC Access mode +* Return Value : none +*******************************************************************************/ +void usb0_host_set_curpipe2 (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw, uint16_t dfacc) +{ + uint16_t buffer; + uint32_t loop; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + uint32_t dummy; +#endif + volatile uint32_t loop2; + + g_usb0_host_mbw[pipe] = mbw; + + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB200.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(~isel & USB_HOST_BITISEL); + USB200.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(isel | pipe | mbw); + USB200.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D0DMA: + case USB_HOST_D0USE: + buffer = USB200.D0FIFOSEL; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + + if (dfacc != 0) + { + buffer |= (uint16_t)(USB_HOST_BITMBW_32); + } +#else + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); +#endif + USB200.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + +#ifdef __USB_HOST_DF_ACC_ENABLE__ + if (dfacc != 0) + { + dummy = USB200.D0FIFO.UINT32; + } +#endif + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB200.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D1DMA: + case USB_HOST_D1USE: + buffer = USB200.D1FIFOSEL; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + + if (dfacc != 0) + { + buffer |= (uint16_t)(USB_HOST_BITMBW_32); + } +#else + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); +#endif + USB200.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + +#ifdef __USB_HOST_DF_ACC_ENABLE__ + if (dfacc != 0) + { + dummy = USB200.D1FIFO.UINT32; + loop = dummy; // avoid warning. + } +#endif + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB200.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB200.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + default: + break; + } + + /* Cautions !!! + * Depending on the external bus speed of CPU, you may need to wait for 450ns here. + * For details, please look at the data sheet. */ + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } +} + +/******************************************************************************* +* Function Name: usb0_host_write_c_fifo +* Description : Writes data in CFIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_write_c_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB200.CFIFO.UINT8[HH] = *g_usb0_host_data_pointer[pipe]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB200.CFIFO.UINT16[H] = *((uint16_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB200.CFIFO.UINT32 = *((uint32_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_read_c_fifo +* Description : Reads data from CFIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_read_c_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb0_host_data_pointer[pipe] = USB200.CFIFO.UINT8[HH]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb0_host_data_pointer[pipe]) = USB200.CFIFO.UINT16[H]; + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb0_host_data_pointer[pipe]) = USB200.CFIFO.UINT32; + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_write_d0_fifo +* Description : Writes data in D0FIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_write_d0_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB200.D0FIFO.UINT8[HH] = *g_usb0_host_data_pointer[pipe]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB200.D0FIFO.UINT16[H] = *((uint16_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB200.D0FIFO.UINT32 = *((uint32_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_read_d0_fifo +* Description : Reads data from D0FIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating DOFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t Pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_read_d0_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb0_host_data_pointer[pipe] = USB200.D0FIFO.UINT8[HH]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb0_host_data_pointer[pipe]) = USB200.D0FIFO.UINT16[H]; + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb0_host_data_pointer[pipe]) = USB200.D0FIFO.UINT32; + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_write_d1_fifo +* Description : Writes data in D1FIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating D1FIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_write_d1_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB200.D1FIFO.UINT8[HH] = *g_usb0_host_data_pointer[pipe]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB200.D1FIFO.UINT16[H] = *((uint16_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB200.D1FIFO.UINT32 = *((uint32_t *)g_usb0_host_data_pointer[pipe]); + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_read_d1_fifo +* Description : Reads data from D1FIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating D1FIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb0_host_read_d1_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb0_host_data_pointer[pipe] = USB200.D1FIFO.UINT8[HH]; + g_usb0_host_data_pointer[pipe] += 1; + } + } + else if (g_usb0_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb0_host_data_pointer[pipe]) = USB200.D1FIFO.UINT16[H]; + g_usb0_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb0_host_data_pointer[pipe]) = USB200.D1FIFO.UINT32; + g_usb0_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_com_get_dmasize +* Description : Calculates access width of DMA transfer by the argument to + return as the Return Value. +* Arguments : uint32_t trncount : transfer byte +* : uint32_t dtptr : transfer data pointer +* Return Value : DMA transfer size : 0 8bit +* : : 1 16bit +* : : 2 32bit +*******************************************************************************/ +static uint32_t usb0_host_com_get_dmasize (uint32_t trncount, uint32_t dtptr) +{ + uint32_t size; + + if (((trncount & 0x0001) != 0) || ((dtptr & 0x00000001) != 0)) + { + /* When transfer byte count is odd */ + /* or transfer data area is 8-bit alignment */ + size = 0; /* 8bit */ + } + else if (((trncount & 0x0003) != 0) || ((dtptr & 0x00000003) != 0)) + { + /* When the transfer byte count is multiples of 2 */ + /* or the transfer data area is 16-bit alignment */ + size = 1; /* 16bit */ + } + else + { + /* When the transfer byte count is multiples of 4 */ + /* or the transfer data area is 32-bit alignment */ + size = 2; /* 32bit */ + } + + return size; +} + +/******************************************************************************* +* Function Name: usb0_host_get_mbw +* Description : Calculates access width of DMA to return the value set in MBW. +* Arguments : uint32_t trncount : transfer byte +* : uint32_t dtptr : transfer data pointer +* Return Value : FIFO transfer size : USB_HOST_BITMBW_8 8bit +* : : USB_HOST_BITMBW_16 16bit +* : : USB_HOST_BITMBW_32 32bit +*******************************************************************************/ +uint16_t usb0_host_get_mbw (uint32_t trncount, uint32_t dtptr) +{ + uint32_t size; + uint16_t mbw; + + size = usb0_host_com_get_dmasize(trncount, dtptr); + + if (size == 0) + { + /* 8bit */ + mbw = USB_HOST_BITMBW_8; + } + else if (size == 1) + { + /* 16bit */ + mbw = USB_HOST_BITMBW_16; + } + else + { + /* 32bit */ + mbw = USB_HOST_BITMBW_32; + } + + return mbw; +} + +/******************************************************************************* +* Function Name: usb0_host_set_transaction_counter +* Description : Sets transaction counter by the argument(PIPEnTRN). +* : Clears transaction before setting to enable transaction counter setting. +* Arguments : uint16_t pipe ; Pipe number +* : uint32_t bsize : Data transfer size +* Return Value : none +*******************************************************************************/ +static void usb0_host_set_transaction_counter (uint16_t pipe, uint32_t bsize) +{ + uint16_t mxps; + uint16_t cnt; + + if (bsize == 0) + { + return; + } + + mxps = usb0_host_get_mxps(pipe); /* Max Packet Size */ + + if ((bsize % mxps) == 0) + { + cnt = (uint16_t)(bsize / mxps); + } + else + { + cnt = (uint16_t)((bsize / mxps) + 1); + } + + switch (pipe) + { + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE1TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE1TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE2TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE2TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE3TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE3TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE4TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE4TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE5TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE5TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB200.PIPE9TRN = cnt; + RZA_IO_RegWrite_16(&USB200.PIPE9TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_clear_transaction_counter +* Description : Clears the transaction counter by the argument. +* : After executing this function, the transaction counter is invalid. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb0_host_clear_transaction_counter (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE1TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE2TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE3TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE4TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE5TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB200.PIPE9TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_stop_transfer +* Description : Stops the USB transfer in the pipe specified by the argument. +* : After stopping the USB transfer, clears the buffer allocated in +* : the pipe. +* : After executing this function, allocation in FIF0 becomes USB_HOST_PIPE0; +* : invalid. After executing this function, BRDY/NRDY/BEMP interrupt +* : in the corresponding pipe becomes invalid. Sequence bit is also +* : cleared. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_stop_transfer (uint16_t pipe) +{ + uint16_t usefifo; + uint32_t remain; + + usb0_host_set_pid_nak(pipe); + + usefifo = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + usb0_host_clear_transaction_counter(pipe); + USB200.D0FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D1FIFO_USE: + usb0_host_clear_transaction_counter(pipe); + USB200.D1FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D0FIFO_DMA: + remain = Userdef_USB_usb0_host_stop_dma0(); + usb0_host_dma_stop_d0(pipe, remain); + usb0_host_clear_transaction_counter(pipe); + USB200.D0FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D1FIFO_DMA: + remain = Userdef_USB_usb0_host_stop_dma1(); + usb0_host_dma_stop_d1(pipe, remain); + usb0_host_clear_transaction_counter(pipe); + USB200.D1FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + default: + usb0_host_clear_transaction_counter(pipe); + USB200.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + } + + /* Interrupt of pipe set is disabled */ + usb0_host_disable_brdy_int(pipe); + usb0_host_disable_nrdy_int(pipe); + usb0_host_disable_bemp_int(pipe); + +#if(1) /* ohci_wrapp */ +#else + usb0_host_aclrm(pipe); +#endif + usb0_host_set_csclr(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_set_dfacc_d0 +* Description : Sets the DFACC setting value in D0FIFO using the transfer size. +* Arguments : uint16_t mbw ; MBW +* : uint16_t count ; data count +* Return Value : DFACC Access mode +*******************************************************************************/ +static uint16_t usb0_host_set_dfacc_d0 (uint16_t mbw, uint32_t count) +{ + uint16_t dfacc = 0; + +#ifndef __USB_HOST_DF_ACC_ENABLE__ + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; +#else + if (mbw == USB_HOST_BITMBW_32) + { + if ((count % 32) == 0) + { + /* 32byte transfer */ + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 2, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 2; + } + else if ((count % 16) == 0) + { + /* 16byte transfer */ + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 1, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 1; + } + else + { + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + } + else if (mbw == USB_HOST_BITMBW_16) + { + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + else + { + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } +#endif + + return dfacc; +} + +/******************************************************************************* +* Function Name: usb0_host_set_dfacc_d1 +* Description : Sets the DFACC setting value in D1FIFO using the transfer size. +* Arguments : uint16_t mbw ; MBW +* : uint16_t count ; data count +* Return Value : DFACC Access mode +*******************************************************************************/ +static uint16_t usb0_host_set_dfacc_d1 (uint16_t mbw, uint32_t count) +{ + uint16_t dfacc = 0; + +#ifndef __USB_HOST_DF_ACC_ENABLE__ + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; +#else + if (mbw == USB_HOST_BITMBW_32) + { + if ((count % 32) == 0) + { + /* 32byte transfer */ + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 2, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 2; + } + else if ((count % 16) == 0) + { + /* 16byte transfer */ + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 1, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 1; + } + else + { + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + } + else if (mbw == USB_HOST_BITMBW_16) + { + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + else + { + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB200.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } +#endif + + return dfacc; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/src/common/usb0_host_dma.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,355 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_dma.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +/* #include "usb0_host_dmacdrv.h" */ + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +static void usb0_host_dmaint(uint16_t fifo); +static void usb0_host_dmaint_buf2fifo(uint16_t pipe); +static void usb0_host_dmaint_fifo2buf(uint16_t pipe); + + +/******************************************************************************* +* Function Name: usb0_host_dma_stop_d0 +* Description : D0FIFO DMA stop +* Arguments : uint16_t pipe : pipe number +* : uint32_t remain : transfer byte +* Return Value : none +*******************************************************************************/ +void usb0_host_dma_stop_d0 (uint16_t pipe, uint32_t remain) +{ + uint16_t dtln; + uint16_t dfacc; + uint16_t buffer; + uint16_t sds_b = 1; + + dfacc = RZA_IO_RegRead_16(&USB200.D0FBCFG, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + if (dfacc == 2) + { + sds_b = 32; + } + else if (dfacc == 1) + { + sds_b = 16; + } + else + { + if (g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size == 2) + { + sds_b = 4; + } + else if (g_usb0_host_DmaInfo[USB_HOST_D0FIFO].size == 1) + { + sds_b = 2; + } + else + { + sds_b = 1; + } + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + if (g_usb0_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + buffer = USB200.D0FIFOCTR; + dtln = (buffer & USB_HOST_BITDTLN); + + if ((dtln % sds_b) != 0) + { + remain += (sds_b - (dtln % sds_b)); + } + g_usb0_host_PipeDataSize[pipe] = (g_usb0_host_data_count[pipe] - remain); + g_usb0_host_data_count[pipe] = remain; + } + } + + RZA_IO_RegWrite_16(&USB200.D0FIFOSEL, + 0, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); +} + +/******************************************************************************* +* Function Name: usb0_host_dma_stop_d1 +* Description : D1FIFO DMA stop +* Arguments : uint16_t pipe : pipe number +* : uint32_t remain : transfer byte +* Return Value : none +*******************************************************************************/ +void usb0_host_dma_stop_d1 (uint16_t pipe, uint32_t remain) +{ + uint16_t dtln; + uint16_t dfacc; + uint16_t buffer; + uint16_t sds_b = 1; + + dfacc = RZA_IO_RegRead_16(&USB200.D1FBCFG, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + if (dfacc == 2) + { + sds_b = 32; + } + else if (dfacc == 1) + { + sds_b = 16; + } + else + { + if (g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size == 2) + { + sds_b = 4; + } + else if (g_usb0_host_DmaInfo[USB_HOST_D1FIFO].size == 1) + { + sds_b = 2; + } + else + { + sds_b = 1; + } + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + if (g_usb0_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + buffer = USB200.D1FIFOCTR; + dtln = (buffer & USB_HOST_BITDTLN); + + if ((dtln % sds_b) != 0) + { + remain += (sds_b - (dtln % sds_b)); + } + g_usb0_host_PipeDataSize[pipe] = (g_usb0_host_data_count[pipe] - remain); + g_usb0_host_data_count[pipe] = remain; + } + } + + RZA_IO_RegWrite_16(&USB200.D1FIFOSEL, + 0, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); +} + +/******************************************************************************* +* Function Name: usb0_host_dma_interrupt_d0fifo +* Description : This function is DMA interrupt handler entry. +* : Execute usb1_host_dmaint() after disabling DMA interrupt in this function. +* : Disable DMA interrupt to DMAC executed when USB_HOST_D0FIFO_DMA is +* : specified by dma->fifo. +* : Register this function as DMA complete interrupt. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb0_host_dma_interrupt_d0fifo (uint32_t int_sense) +{ + usb0_host_dmaint(USB_HOST_D0FIFO); + g_usb0_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_READY; +} + +/******************************************************************************* +* Function Name: usb0_host_dma_interrupt_d1fifo +* Description : This function is DMA interrupt handler entry. +* : Execute usb0_host_dmaint() after disabling DMA interrupt in this function. +* : Disable DMA interrupt to DMAC executed when USB_HOST_D1FIFO_DMA is +* : specified by dma->fifo. +* : Register this function as DMA complete interrupt. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb0_host_dma_interrupt_d1fifo (uint32_t int_sense) +{ + usb0_host_dmaint(USB_HOST_D1FIFO); + g_usb0_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_READY; +} + +/******************************************************************************* +* Function Name: usb0_host_dmaint +* Description : This function is DMA transfer end interrupt +* Arguments : uint16_t fifo ; fifo number +* : ; USB_HOST_D0FIFO +* : ; USB_HOST_D1FIFO +* Return Value : none +*******************************************************************************/ +static void usb0_host_dmaint (uint16_t fifo) +{ + uint16_t pipe; + + pipe = g_usb0_host_DmaPipe[fifo]; + + if (g_usb0_host_DmaInfo[fifo].dir == USB_HOST_BUF2FIFO) + { + usb0_host_dmaint_buf2fifo(pipe); + } + else + { + usb0_host_dmaint_fifo2buf(pipe); + } +} + +/******************************************************************************* +* Function Name: usb0_host_dmaint_fifo2buf +* Description : Executes read completion from FIFO by DMAC. +* Arguments : uint16_t pipe : pipe number +* Return Value : none +*******************************************************************************/ +static void usb0_host_dmaint_fifo2buf (uint16_t pipe) +{ + uint32_t remain; + uint16_t useport; + + if (g_usb0_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + useport = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + if (useport == USB_HOST_D0FIFO_DMA) + { + remain = Userdef_USB_usb0_host_stop_dma0(); + usb0_host_dma_stop_d0(pipe, remain); + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + if (g_usb0_host_DmaStatus[USB_HOST_D0FIFO] == USB_HOST_DMA_BUSYEND) + { + USB200.D0FIFOCTR = USB_HOST_BITBCLR; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + else + { + usb0_host_enable_brdy_int(pipe); + } + } + } + else + { + remain = Userdef_USB_usb0_host_stop_dma1(); + usb0_host_dma_stop_d1(pipe, remain); + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + if (g_usb0_host_DmaStatus[USB_HOST_D1FIFO] == USB_HOST_DMA_BUSYEND) + { + USB200.D1FIFOCTR = USB_HOST_BITBCLR; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + else + { + usb0_host_enable_brdy_int(pipe); + } + } + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_dmaint_buf2fifo +* Description : Executes write completion in FIFO by DMAC. +* Arguments : uint16_t pipe : pipe number +* Return Value : none +*******************************************************************************/ +static void usb0_host_dmaint_buf2fifo (uint16_t pipe) +{ + uint16_t useport; + uint32_t remain; + + useport = (uint16_t)(g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + if (useport == USB_HOST_D0FIFO_DMA) + { + remain = Userdef_USB_usb0_host_stop_dma0(); + usb0_host_dma_stop_d0(pipe, remain); + + if (g_usb0_host_DmaBval[USB_HOST_D0FIFO] != 0) + { + RZA_IO_RegWrite_16(&USB200.D0FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); + } + } + else + { + remain = Userdef_USB_usb0_host_stop_dma1(); + usb0_host_dma_stop_d1(pipe, remain); + + if (g_usb0_host_DmaBval[USB_HOST_D1FIFO] != 0) + { + RZA_IO_RegWrite_16(&USB200.D1FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); + } + } + + usb0_host_enable_bemp_int(pipe); +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/src/common/usb0_host_intrn.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,285 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_intrn.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#if(1) /* ohci_wrapp */ +#include "ohci_wrapp_RZ_A1_local.h" +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_brdy_int +* Description : Executes BRDY interrupt(USB_HOST_PIPE1-9). +* : According to the pipe that interrupt is generated in, +* : reads/writes buffer allocated in the pipe. +* : This function is executed in the BRDY interrupt handler. +* : This function clears BRDY interrupt status and BEMP interrupt +* : status. +* Arguments : uint16_t status ; BRDYSTS Register Value +* : uint16_t int_enb ; BRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_brdy_int (uint16_t status, uint16_t int_enb) +{ + uint32_t int_sense = 0; + uint16_t pipe; + uint16_t pipebit; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + pipebit = g_usb0_host_bit_set[pipe]; + + if ((status & pipebit) && (int_enb & pipebit)) + { + USB200.BRDYSTS = (uint16_t)~pipebit; + USB200.BEMPSTS = (uint16_t)~pipebit; + + if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_DMA) + { + if (g_usb0_host_DmaStatus[USB_HOST_D0FIFO] != USB_HOST_DMA_READY) + { + usb0_host_dma_interrupt_d0fifo(int_sense); + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + usb0_host_read_dma(pipe); + usb0_host_disable_brdy_int(pipe); + } + else + { + USB200.D0FIFOCTR = USB_HOST_BITBCLR; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + } + else if ((g_usb0_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_DMA) + { + if (g_usb0_host_DmaStatus[USB_HOST_D1FIFO] != USB_HOST_DMA_READY) + { + usb0_host_dma_interrupt_d1fifo(int_sense); + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + usb0_host_read_dma(pipe); + usb0_host_disable_brdy_int(pipe); + } + else + { + USB200.D1FIFOCTR = USB_HOST_BITBCLR; + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + } + else + { + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 0) + { + usb0_host_read_buffer(pipe); + } + else + { + usb0_host_write_buffer(pipe); + } + } +#if(1) /* ohci_wrapp */ + switch (g_usb0_host_pipe_status[pipe]) + { + case USB_HOST_PIPE_DONE: + ohciwrapp_loc_TransEnd(pipe, TD_CC_NOERROR); + break; + case USB_HOST_PIPE_NORES: + case USB_HOST_PIPE_STALL: + case USB_HOST_PIPE_ERROR: + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); + break; + default: + /* Do Nothing */ + break; + } +#endif + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_nrdy_int +* Description : Executes NRDY interrupt(USB_HOST_PIPE1-9). +* : Checks NRDY interrupt cause by PID. When the cause if STALL, +* : regards the pipe state as STALL and ends the processing. +* : Then the cause is not STALL, increments the error count to +* : communicate again. When the error count is 3, determines +* : the pipe state as USB_HOST_PIPE_NORES and ends the processing. +* : This function is executed in the NRDY interrupt handler. +* : This function clears NRDY interrupt status. +* Arguments : uint16_t status ; NRDYSTS Register Value +* : uint16_t int_enb ; NRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_nrdy_int (uint16_t status, uint16_t int_enb) +{ + uint16_t pid; + uint16_t pipe; + uint16_t bitcheck; + + bitcheck = (uint16_t)(status & int_enb); + + USB200.NRDYSTS = (uint16_t)~status; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + if ((bitcheck&g_usb0_host_bit_set[pipe]) == g_usb0_host_bit_set[pipe]) + { + if (RZA_IO_RegRead_16(&USB200.SYSCFG0, + USB_SYSCFG_DCFM_SHIFT, + USB_SYSCFG_DCFM) == 1) + { + if (g_usb0_host_pipe_status[pipe] == USB_HOST_PIPE_WAIT) + { + pid = usb0_host_get_pid(pipe); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_STALL; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); +#endif + } + else + { +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_NORES; + ohciwrapp_loc_TransEnd(pipe, TD_CC_DEVICENOTRESPONDING); +#else + g_usb0_host_PipeIgnore[pipe]++; + + if (g_usb0_host_PipeIgnore[pipe] == 3) + { + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_NORES; + } + else + { + usb0_host_set_pid_buf(pipe); + } +#endif + } + } + } + else + { + /* USB Function */ + } + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_bemp_int +* Description : Executes BEMP interrupt(USB_HOST_PIPE1-9). +* Arguments : uint16_t status ; BEMPSTS Register Value +* : uint16_t int_enb ; BEMPENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_bemp_int (uint16_t status, uint16_t int_enb) +{ + uint16_t pid; + uint16_t pipe; + uint16_t bitcheck; + uint16_t inbuf; + + bitcheck = (uint16_t)(status & int_enb); + + USB200.BEMPSTS = (uint16_t)~status; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + if ((bitcheck&g_usb0_host_bit_set[pipe]) == g_usb0_host_bit_set[pipe]) + { + pid = usb0_host_get_pid(pipe); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_STALL; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); +#endif + } + else + { + inbuf = usb0_host_get_inbuf(pipe); + + if (inbuf == 0) + { + usb0_host_disable_bemp_int(pipe); + usb0_host_set_pid_nak(pipe); + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_NOERROR); +#endif + } + } + } + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/src/common/usb0_host_lib.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,1580 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_lib.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#if(1) /* ohci_wrapp */ +#include "VKRZA1H.h" /* INTC Driver Header */ +#else +#include "devdrv_intc.h" /* INTC Driver Header */ +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_enable_brdy_int +* Description : Enables BRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : BRDY. Enables BRDY interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_enable_brdy_int (uint16_t pipe) +{ + /* enable brdy interrupt */ + USB200.BRDYENB |= (uint16_t)g_usb0_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb0_host_disable_brdy_int +* Description : Disables BRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : BRDY. Enables BRDY interrupt in the pipe specified by the argument +* : in the disabled status. After disabling BRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_disable_brdy_int (uint16_t pipe) +{ + /* disable brdy interrupt */ + USB200.BRDYENB &= (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_clear_brdy_sts +* Description : Clear BRDY interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_clear_brdy_sts (uint16_t pipe) +{ + /* clear brdy status */ + USB200.BRDYSTS = (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_enable_bemp_int +* Description : Enables BEMP interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : BEMP. Enables BEMP interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BEMP, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_enable_bemp_int (uint16_t pipe) +{ + /* enable bemp interrupt */ + USB200.BEMPENB |= (uint16_t)g_usb0_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb0_host_disable_bemp_int +* Description : Disables BEMP interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : BEMP. Enables BEMP interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BEMP, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_disable_bemp_int (uint16_t pipe) +{ + /* disable bemp interrupt */ + USB200.BEMPENB &= (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_clear_bemp_sts +* Description : Clear BEMP interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_clear_bemp_sts (uint16_t pipe) +{ + /* clear bemp status */ + USB200.BEMPSTS = (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_enable_nrdy_int +* Description : Enables NRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : NRDY. Enables NRDY interrupt in the pipe specified by the argument +* : in the disabled status. After enabling NRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_enable_nrdy_int (uint16_t pipe) +{ + /* enable nrdy interrupt */ + USB200.NRDYENB |= (uint16_t)g_usb0_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb0_host_disable_nrdy_int +* Description : Disables NRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : NRDY. Disables NRDY interrupt in the pipe specified by the argument +* : in the disabled status. After disabling NRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_disable_nrdy_int (uint16_t pipe) +{ + /* disable nrdy interrupt */ + USB200.NRDYENB &= (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_clear_nrdy_sts +* Description : Clear NRDY interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_clear_nrdy_sts (uint16_t pipe) +{ + /* clear nrdy status */ + USB200.NRDYSTS = (uint16_t)~(g_usb0_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb0_host_is_hispeed +* Description : Returns the result of USB reset hand shake (RHST) as +* : return value. +* Arguments : none +* Return Value : USB_HOST_HIGH_SPEED ; Hi-Speed +* : USB_HOST_FULL_SPEED ; Full-Speed +* : USB_HOST_LOW_SPEED ; Low-Speed +* : USB_HOST_NON_SPEED ; error +*******************************************************************************/ +uint16_t usb0_host_is_hispeed (void) +{ + uint16_t rhst; + uint16_t speed; + + rhst = RZA_IO_RegRead_16(&USB200.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (rhst == USB_HOST_HSMODE) + { + speed = USB_HOST_HIGH_SPEED; + } + else if (rhst == USB_HOST_FSMODE) + { + speed = USB_HOST_FULL_SPEED; + } + else if (rhst == USB_HOST_LSMODE) + { + speed = USB_HOST_LOW_SPEED; + } + else + { + speed = USB_HOST_NON_SPEED; + } + + return speed; +} + +/******************************************************************************* +* Function Name: usb0_host_is_hispeed_enable +* Description : Returns the USB High-Speed connection enabled status as +* : return value. +* Arguments : none +* Return Value : USB_HOST_YES : Hi-Speed Enable +* : USB_HOST_NO : Hi-Speed Disable +*******************************************************************************/ +uint16_t usb0_host_is_hispeed_enable (void) +{ + uint16_t ret; + + ret = USB_HOST_NO; + + if (RZA_IO_RegRead_16(&USB200.SYSCFG0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE) == 1) + { + ret = USB_HOST_YES; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_host_set_pid_buf +* Description : Enables communicaqtion in the pipe specified by the argument +* : (BUF). +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_pid_buf (uint16_t pipe) +{ + uint16_t pid; + + pid = usb0_host_get_pid(pipe); + + if (pid == USB_HOST_PID_STALL2) + { + usb0_host_set_pid_nak(pipe); + } + + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + USB_HOST_PID_BUF, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_set_pid_nak +* Description : Disables communication (NAK) in the pipe specified by the argument. +* : When the pipe status was enabling communication (BUF) before +* : executing before executing this function, waits in the software +* : until the pipe becomes ready after setting disabled. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_pid_nak (uint16_t pipe) +{ + uint16_t pid; + uint16_t pbusy; + uint32_t loop; + + pid = usb0_host_get_pid(pipe); + + if (pid == USB_HOST_PID_STALL2) + { + usb0_host_set_pid_stall(pipe); + } + + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + USB_HOST_PID_NAK, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + + if (pid == USB_HOST_PID_BUF) + { + for (loop = 0; loop < 200; loop++) + { + switch (pipe) + { + case USB_HOST_PIPE0: + pbusy = RZA_IO_RegRead_16(&USB200.DCPCTR, + USB_DCPCTR_PBUSY_SHIFT, + USB_DCPCTR_PBUSY); + break; + + case USB_HOST_PIPE1: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE1CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE2: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE2CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE3: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE3CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE4: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE4CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE5: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE5CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE6: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE6CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE7: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE7CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE8: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE8CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE9: + pbusy = RZA_IO_RegRead_16(&USB200.PIPE9CTR, + USB_PIPEnCTR_9_PBUSY_SHIFT, + USB_PIPEnCTR_9_PBUSY); + break; + + default: + pbusy = 1; + break; + } + + if (pbusy == 0) + { + break; + } + + Userdef_USB_usb0_host_delay_500ns(); + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_set_pid_stall +* Description : Disables communication (STALL) in the pipe specified by the +* : argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_pid_stall (uint16_t pipe) +{ + uint16_t pid; + + pid = usb0_host_get_pid(pipe); + + if (pid == USB_HOST_PID_BUF) + { + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + USB_HOST_PID_STALL2, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + } + else + { + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + USB_HOST_PID_STALL, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + } +} + +/******************************************************************************* +* Function Name: usb0_host_clear_pid_stall +* Description : Disables communication (NAK) in the pipe specified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_clear_pid_stall (uint16_t pipe) +{ + usb0_host_set_pid_nak(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_get_pid +* Description : Returns the pipe state specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : PID +*******************************************************************************/ +uint16_t usb0_host_get_pid (uint16_t pipe) +{ + uint16_t pid; + + switch (pipe) + { + case USB_HOST_PIPE0: + pid = RZA_IO_RegRead_16(&USB200.DCPCTR, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + pid = RZA_IO_RegRead_16(&USB200.PIPE1CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + pid = RZA_IO_RegRead_16(&USB200.PIPE2CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + pid = RZA_IO_RegRead_16(&USB200.PIPE3CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + pid = RZA_IO_RegRead_16(&USB200.PIPE4CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + pid = RZA_IO_RegRead_16(&USB200.PIPE5CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + pid = RZA_IO_RegRead_16(&USB200.PIPE6CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + pid = RZA_IO_RegRead_16(&USB200.PIPE7CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + pid = RZA_IO_RegRead_16(&USB200.PIPE8CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + pid = RZA_IO_RegRead_16(&USB200.PIPE9CTR, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + pid = 0; + break; + } + + return pid; +} + +/******************************************************************************* +* Function Name: usb0_host_set_csclr +* Description : CSPLIT status clear setting of sprit transaction in specified +* : pipe is performed. +* : When SQSET bit or SQCLR bit, and SQSET bit or SQCLR bit +* : in DCPCTR register are continuously changed (when the sequence +* : toggle bit of data PID is continuously changed over two or more pipes), +* : the access cycle with 120 ns and more than 5 cycle bus clock is necessary. +* : Do not set both SQCLR bit and SQSET bit to 1 at the same time. +* : In addition, both bits should be operated after PID is set to NAK. +* : However, when it is set to the isochronous transfer as the transfer type +* : (TYPE=11), writing in SQSET bit is disabled. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_csclr (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + 1, + USB_DCPCTR_CSCLR_SHIFT, + USB_DCPCTR_CSCLR); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + 1, + USB_PIPEnCTR_9_CSCLR_SHIFT, + USB_PIPEnCTR_9_CSCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_set_sqclr +* Description : Sets the sequence bit of the pipe specified by the argument to +* : DATA0. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_sqclr (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + 1, + USB_DCPCTR_SQCLR_SHIFT, + USB_DCPCTR_SQCLR); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + 1, + USB_PIPEnCTR_9_SQCLR_SHIFT, + USB_PIPEnCTR_9_SQCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_set_sqset +* Description : Sets the sequence bit of the pipe specified by the argument to +* : DATA1. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb0_host_set_sqset (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB200.DCPCTR, + 1, + USB_DCPCTR_SQSET_SHIFT, + USB_DCPCTR_SQSET); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + 1, + USB_PIPEnCTR_9_SQSET_SHIFT, + USB_PIPEnCTR_9_SQSET); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_get_sqmon +* Description : Toggle bit of specified pipe is obtained +* Arguments : uint16_t pipe ; Pipe number +* Return Value : sqmon +*******************************************************************************/ +uint16_t usb0_host_get_sqmon (uint16_t pipe) +{ + uint16_t sqmon; + + switch (pipe) + { + case USB_HOST_PIPE0: + sqmon = RZA_IO_RegRead_16(&USB200.DCPCTR, + USB_DCPCTR_SQMON_SHIFT, + USB_DCPCTR_SQMON); + break; + + case USB_HOST_PIPE1: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE1CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE2: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE2CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE3: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE3CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE4: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE4CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE5: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE5CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE6: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE6CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE7: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE7CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE8: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE8CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE9: + sqmon = RZA_IO_RegRead_16(&USB200.PIPE9CTR, + USB_PIPEnCTR_9_SQMON_SHIFT, + USB_PIPEnCTR_9_SQMON); + break; + + default: + sqmon = 0; + break; + } + + return sqmon; +} + +/******************************************************************************* +* Function Name: usb0_host_aclrm +* Description : The buffer of specified pipe is initialized +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb0_host_aclrm (uint16_t pipe) +{ + usb0_host_set_aclrm(pipe); + usb0_host_clr_aclrm(pipe); +} + +/******************************************************************************* +* Function Name: usb0_host_set_aclrm +* Description : The auto buffer clear mode of specified pipe is enabled +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb0_host_set_aclrm (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + 1, + USB_PIPEnCTR_9_ACLRM_SHIFT, + USB_PIPEnCTR_9_ACLRM); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_clr_aclrm +* Description : The auto buffer clear mode of specified pipe is enabled +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb0_host_clr_aclrm (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB200.PIPE1CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB200.PIPE2CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB200.PIPE3CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB200.PIPE4CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB200.PIPE5CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB200.PIPE6CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB200.PIPE7CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB200.PIPE8CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB200.PIPE9CTR, + 0, + USB_PIPEnCTR_9_ACLRM_SHIFT, + USB_PIPEnCTR_9_ACLRM); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_get_inbuf +* Description : Returns INBUFM of the pipe specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : inbuf +*******************************************************************************/ +uint16_t usb0_host_get_inbuf (uint16_t pipe) +{ + uint16_t inbuf; + + switch (pipe) + { + case USB_HOST_PIPE0: + inbuf = 0; + break; + + case USB_HOST_PIPE1: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE1CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE2: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE2CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE3: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE3CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE4: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE4CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE5: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE5CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE6: + inbuf = 0; + break; + + case USB_HOST_PIPE7: + inbuf = 0; + break; + + case USB_HOST_PIPE8: + inbuf = 0; + break; + + case USB_HOST_PIPE9: + inbuf = RZA_IO_RegRead_16(&USB200.PIPE9CTR, + USB_PIPEnCTR_9_INBUFM_SHIFT, + USB_PIPEnCTR_9_INBUFM); + break; + + default: + inbuf = 0; + break; + } + + return inbuf; +} + +/******************************************************************************* +* Function Name: usb0_host_setting_interrupt +* Description : Sets the USB module interrupt level. +* Arguments : uint8_t level ; interrupt level +* Return Value : none +*******************************************************************************/ +void usb0_host_setting_interrupt (uint8_t level) +{ +#if(1) /* ohci_wrapp */ + IRQn_Type d0fifo_dmaintid; + IRQn_Type d1fifo_dmaintid; + + InterruptHandlerRegister(USBI0_IRQn, usb0_host_interrupt); + GIC_SetPriority(USBI0_IRQn, level); + GIC_EnableIRQ(USBI0_IRQn); + + d0fifo_dmaintid = (IRQn_Type)Userdef_USB_usb0_host_d0fifo_dmaintid(); + + if (d0fifo_dmaintid != 0xFFFF) + { + InterruptHandlerRegister(d0fifo_dmaintid, usb0_host_dma_interrupt_d0fifo); + GIC_SetPriority(d0fifo_dmaintid, level); + GIC_EnableIRQ(d0fifo_dmaintid); + } + + d1fifo_dmaintid = (IRQn_Type)Userdef_USB_usb0_host_d1fifo_dmaintid(); + + if (d1fifo_dmaintid != 0xFFFF) + { + InterruptHandlerRegister(d1fifo_dmaintid, usb0_host_dma_interrupt_d1fifo); + GIC_SetPriority(d1fifo_dmaintid, level); + GIC_EnableIRQ(d1fifo_dmaintid); + } +#else + uint16_t d0fifo_dmaintid; + uint16_t d1fifo_dmaintid; + + R_INTC_RegistIntFunc(INTC_ID_USBI0, usb0_host_interrupt); + R_INTC_SetPriority(INTC_ID_USBI0, level); + R_INTC_Enable(INTC_ID_USBI0); + + d0fifo_dmaintid = Userdef_USB_usb0_host_d0fifo_dmaintid(); + + if (d0fifo_dmaintid != 0xFFFF) + { + R_INTC_RegistIntFunc(d0fifo_dmaintid, usb0_host_dma_interrupt_d0fifo); + R_INTC_SetPriority(d0fifo_dmaintid, level); + R_INTC_Enable(d0fifo_dmaintid); + } + + d1fifo_dmaintid = Userdef_USB_usb0_host_d1fifo_dmaintid(); + + if (d1fifo_dmaintid != 0xFFFF) + { + R_INTC_RegistIntFunc(d1fifo_dmaintid, usb0_host_dma_interrupt_d1fifo); + R_INTC_SetPriority(d1fifo_dmaintid, level); + R_INTC_Enable(d1fifo_dmaintid); + } +#endif +} + +/******************************************************************************* +* Function Name: usb0_host_reset_module +* Description : Initializes the USB module. +* : Enables providing clock to the USB module. +* : Sets USB bus wait register. +* Arguments : uint16_t clockmode ; 48MHz ; USBHCLOCK_X1_48MHZ +* : ; 12MHz ; USBHCLOCK_EXTAL_12MHZ +* Return Value : none +*******************************************************************************/ +void usb0_host_reset_module (uint16_t clockmode) +{ + if (RZA_IO_RegRead_16(&USB200.SYSCFG0, + USB_SYSCFG_UPLLE_SHIFT, + USB_SYSCFG_UPLLE) == 1) + { + if ((USB200.SYSCFG0 & USB_HOST_BITUCKSEL) != clockmode) + { + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + USB200.SYSCFG0 = 0; + USB200.SYSCFG0 = (USB_HOST_BITUPLLE | clockmode); + Userdef_USB_usb0_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + else + { + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + Userdef_USB_usb0_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + } + else + { + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + USB200.SYSCFG0 = 0; + USB200.SYSCFG0 = (USB_HOST_BITUPLLE | clockmode); + Userdef_USB_usb0_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + + USB200.BUSWAIT = (uint16_t)(USB_HOST_BUSWAIT_05 & USB_HOST_BITBWAIT); +} + +/******************************************************************************* +* Function Name: usb0_host_get_buf_size +* Description : Obtains pipe buffer size specified by the argument and +* : maximum packet size of the USB device in use. +* : When USB_HOST_PIPE0 is specified by the argument, obtains the maximum +* : packet size of the USB device using the corresponding pipe. +* : For the case that USB_HOST_PIPE0 is not assigned by the argument, when the +* : corresponding pipe is in continuous transfer mode, +* : obtains the buffer size allocated in the corresponcing pipe, +* : when incontinuous transfer, obtains maximum packet size. +* Arguments : uint16_t ; pipe Number +* Return Value : Maximum packet size or buffer size +*******************************************************************************/ +uint16_t usb0_host_get_buf_size (uint16_t pipe) +{ + uint16_t size; + uint16_t bufsize; + + if (pipe == USB_HOST_PIPE0) + { + size = RZA_IO_RegRead_16(&USB200.DCPMAXP, + USB_DCPMAXP_MXPS_SHIFT, + USB_DCPMAXP_MXPS); + } + else + { + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[pipe], USB_PIPECFG_CNTMD_SHIFT, USB_PIPECFG_CNTMD) == 1) + { + bufsize = RZA_IO_RegRead_16(&g_usb0_host_pipebuf[pipe], USB_PIPEBUF_BUFSIZE_SHIFT, USB_PIPEBUF_BUFSIZE); + size = (uint16_t)((bufsize + 1) * USB_HOST_PIPExBUF); + } + else + { + size = RZA_IO_RegRead_16(&g_usb0_host_pipemaxp[pipe], USB_PIPEMAXP_MXPS_SHIFT, USB_PIPEMAXP_MXPS); + } + } + return size; +} + +/******************************************************************************* +* Function Name: usb0_host_get_mxps +* Description : Obtains maximum packet size of the USB device using the pipe +* : specified by the argument. +* Arguments : uint16_t ; Pipe Number +* Return Value : Max Packet Size +*******************************************************************************/ +uint16_t usb0_host_get_mxps (uint16_t pipe) +{ + uint16_t size; + + if (pipe == USB_HOST_PIPE0) + { + size = RZA_IO_RegRead_16(&USB200.DCPMAXP, + USB_DCPMAXP_MXPS_SHIFT, + USB_DCPMAXP_MXPS); + } + else + { + size = RZA_IO_RegRead_16(&g_usb0_host_pipemaxp[pipe], USB_PIPEMAXP_MXPS_SHIFT, USB_PIPEMAXP_MXPS); + } + + return size; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/src/host/usb0_host_controlrw.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,434 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_controlrw.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_CtrlTransStart +* Description : Executes USB control transfer. +* Arguments : uint16_t devadr ; device address +* : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* : uint8_t *Buf ; Data buffer +* Return Value : DEVDRV_SUCCESS ; SUCCESS +* : DEVDRV_ERROR ; ERROR +*******************************************************************************/ +int32_t usb0_host_CtrlTransStart (uint16_t devadr, uint16_t Req, uint16_t Val, + uint16_t Indx, uint16_t Len, uint8_t * Buf) +{ + if (g_usb0_host_UsbDeviceSpeed == USB_HOST_LOW_SPEED) + { + RZA_IO_RegWrite_16(&USB200.SOFCFG, + 1, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + else + { + RZA_IO_RegWrite_16(&USB200.SOFCFG, + 0, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + + USB200.DCPMAXP = (uint16_t)((uint16_t)(devadr << 12) + g_usb0_host_default_max_packet[devadr]); + + if (g_usb0_host_pipe_status[USB_HOST_PIPE0] == USB_HOST_PIPE_IDLE) + { + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_WAIT; + g_usb0_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + g_usb0_host_CmdStage = (USB_HOST_STAGE_SETUP | USB_HOST_CMD_IDLE); + + if (Len == 0) + { + g_usb0_host_CmdStage |= USB_HOST_MODE_NO_DATA; /* No-data Control */ + } + else + { + if ((Req & 0x0080) != 0) + { + g_usb0_host_CmdStage |= USB_HOST_MODE_READ; /* Control Read */ + } + else + { + g_usb0_host_CmdStage |= USB_HOST_MODE_WRITE; /* Control Write */ + } + } + + g_usb0_host_SavReq = Req; /* save request */ + g_usb0_host_SavVal = Val; + g_usb0_host_SavIndx = Indx; + g_usb0_host_SavLen = Len; + } + else + { + if ((g_usb0_host_SavReq != Req) || (g_usb0_host_SavVal != Val) + || (g_usb0_host_SavIndx != Indx) || (g_usb0_host_SavLen != Len)) + { + return DEVDRV_ERROR; + } + } + + switch ((g_usb0_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + /* --------------- SETUP STAGE --------------- */ + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_IDLE): + usb0_host_SetupStage(Req, Val, Indx, Len); + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_DONE): /* goto next stage */ + g_usb0_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + switch ((g_usb0_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_WRITE: + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_DATA; + break; + + case USB_HOST_MODE_READ: + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_DATA; + break; + + case USB_HOST_MODE_NO_DATA: + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_STATUS; + break; + + default: + break; + } + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_NORES): + if (g_usb0_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb0_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_IDLE; + } + break; + + /* --------------- DATA STAGE --------------- */ + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_IDLE): + switch ((g_usb0_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_WRITE: + usb0_host_CtrlWriteStart((uint32_t)Len, Buf); + break; + + case USB_HOST_MODE_READ: + usb0_host_CtrlReadStart((uint32_t)Len, Buf); + break; + + default: + break; + } + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DONE): /* goto next stage */ + g_usb0_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_STATUS; + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_NORES): + if (g_usb0_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb0_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DOING; + usb0_host_clear_pid_stall(USB_HOST_PIPE0); + usb0_host_set_pid_buf(USB_HOST_PIPE0); + } + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_STALL): + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + break; + + /* --------------- STATUS STAGE --------------- */ + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_IDLE): + usb0_host_StatusStage(); + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DONE): /* end of Control transfer */ + usb0_host_set_pid_nak(USB_HOST_PIPE0); + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_DONE; /* exit DONE */ + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_NORES): + if (g_usb0_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb0_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DOING; + usb0_host_clear_pid_stall(USB_HOST_PIPE0); + usb0_host_set_pid_buf(USB_HOST_PIPE0); + } + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_STALL): + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + break; + + default: + break; + } + + if (g_usb0_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_WAIT) + { + RZA_IO_RegWrite_16(&USB200.SOFCFG, + 0, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb0_host_SetupStage +* Description : Executes USB control transfer/set up stage. +* Arguments : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* Return Value : none +*******************************************************************************/ +void usb0_host_SetupStage (uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len) +{ + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DOING; + + USB200.INTSTS1 = (uint16_t)~(USB_HOST_BITSACK | USB_HOST_BITSIGN); /* Status Clear */ + USB200.USBREQ = Req; + USB200.USBVAL = Val; + USB200.USBINDX = Indx; + USB200.USBLENG = Len; + USB200.DCPCTR = USB_HOST_BITSUREQ; /* PID=NAK & Send Setup */ +} + +/******************************************************************************* +* Function Name: usb0_host_StatusStage +* Description : Executes USB control transfer/status stage. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_StatusStage (void) +{ + uint8_t Buf1[16]; + + switch ((g_usb0_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_READ: + usb0_host_CtrlWriteStart((uint32_t)0, (uint8_t *)&Buf1); + break; + + case USB_HOST_MODE_WRITE: + usb0_host_CtrlReadStart((uint32_t)0, (uint8_t *)&Buf1); + break; + + case USB_HOST_MODE_NO_DATA: + usb0_host_CtrlReadStart((uint32_t)0, (uint8_t *)&Buf1); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb0_host_CtrlWriteStart +* Description : Executes USB control transfer/data stage(write). +* Arguments : uint32_t Bsize ; Data Size +* : uint8_t *Table ; Data Table Address +* Return Value : USB_HOST_WRITESHRT ; End of data write +* : USB_HOST_WRITEEND ; End of data write (not null) +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_FIFOERROR ; FIFO access error +*******************************************************************************/ +uint16_t usb0_host_CtrlWriteStart (uint32_t Bsize, uint8_t * Table) +{ + uint16_t EndFlag_K; + uint16_t mbw; + + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DOING; + + usb0_host_set_pid_nak(USB_HOST_PIPE0); /* Set NAK */ + g_usb0_host_data_count[USB_HOST_PIPE0] = Bsize; /* Transfer size set */ + g_usb0_host_data_pointer[USB_HOST_PIPE0] = Table; /* Transfer address set */ + + USB200.DCPCTR = USB_HOST_BITSQSET; /* SQSET=1, PID=NAK */ +#if(1) /* ohci_wrapp */ + Userdef_USB_usb0_host_delay_10us(3); +#endif + RZA_IO_RegWrite_16(&USB200.DCPCFG, + 1, + USB_DCPCFG_DIR_SHIFT, + USB_DCPCFG_DIR); + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[USB_HOST_PIPE0], (uint32_t)g_usb0_host_data_pointer[USB_HOST_PIPE0]); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_BITISEL, mbw); + USB200.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + + usb0_host_clear_pid_stall(USB_HOST_PIPE0); + EndFlag_K = usb0_host_write_buffer_c(USB_HOST_PIPE0); + /* Host Control sequence */ + switch (EndFlag_K) + { + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_STATUS; + usb0_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb0_host_enable_bemp_int(USB_HOST_PIPE0); /* Enable Empty Interrupt */ + break; + + case USB_HOST_WRITEEND: /* End of data write (not null) */ + case USB_HOST_WRITING: /* Continue of data write */ + usb0_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb0_host_enable_bemp_int(USB_HOST_PIPE0); /* Enable Empty Interrupt */ + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + break; + + default: + break; + } + usb0_host_set_pid_buf(USB_HOST_PIPE0); /* Set BUF */ + return (EndFlag_K); /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb0_host_CtrlReadStart +* Description : Executes USB control transfer/data stage(read). +* Arguments : uint32_t Bsize ; Data Size +* : uint8_t *Table ; Data Table Address +* Return Value : none +*******************************************************************************/ +void usb0_host_CtrlReadStart (uint32_t Bsize, uint8_t * Table) +{ + uint16_t mbw; + + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DOING; + + usb0_host_set_pid_nak(USB_HOST_PIPE0); /* Set NAK */ + g_usb0_host_data_count[USB_HOST_PIPE0] = Bsize; /* Transfer size set */ + g_usb0_host_data_pointer[USB_HOST_PIPE0] = Table; /* Transfer address set */ + + USB200.DCPCTR = USB_HOST_BITSQSET; /* SQSET=1, PID=NAK */ +#if(1) /* ohci_wrapp */ + Userdef_USB_usb0_host_delay_10us(3); +#endif + RZA_IO_RegWrite_16(&USB200.DCPCFG, + 0, + USB_DCPCFG_DIR_SHIFT, + USB_DCPCFG_DIR); + + mbw = usb0_host_get_mbw(g_usb0_host_data_count[USB_HOST_PIPE0], (uint32_t)g_usb0_host_data_pointer[USB_HOST_PIPE0]); + usb0_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_NO, mbw); + USB200.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + + usb0_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb0_host_enable_brdy_int(USB_HOST_PIPE0); /* Ok */ + usb0_host_clear_pid_stall(USB_HOST_PIPE0); + usb0_host_set_pid_buf(USB_HOST_PIPE0); /* Set BUF */ +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/src/host/usb0_host_drv_api.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,889 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_drv_api.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb0_host_resetEP(USB_HOST_CFG_PIPETBL_t *tbl); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_api_host_init +* Description : Initializes USB module in the USB host mode. +* : USB connection is executed when executing this function in +* : the states that USB device isconnected to the USB port. +* Arguments : uint8_t int_level : USB Module interrupt level +* : USBU16 mode : USB_HOST_HIGH_SPEED +* : USB_HOST_FULL_SPEED +* : uint16_t clockmode : USB Clock mode +* Return Value : USB detach or attach +* : USB_HOST_ATTACH +* : USB_HOST_DETACH +*******************************************************************************/ +uint16_t usb0_api_host_init (uint8_t int_level, uint16_t mode, uint16_t clockmode) +{ + uint16_t connect; + volatile uint8_t dummy_buf; + + CPG.STBCR7 &= 0xfd; /*The clock of USB0 modules is permitted */ + dummy_buf = CPG.STBCR7; /* (Dummy read) */ + + g_usb0_host_SupportUsbDeviceSpeed = mode; + + usb0_host_setting_interrupt(int_level); + usb0_host_reset_module(clockmode); + + g_usb0_host_bchg_flag = USB_HOST_NO; + g_usb0_host_detach_flag = USB_HOST_NO; + g_usb0_host_attach_flag = USB_HOST_NO; + + g_usb0_host_driver_state = USB_HOST_DRV_DETACHED; + g_usb0_host_default_max_packet[USB_HOST_DEVICE_0] = 64; + + usb0_host_InitModule(); + + connect = usb0_host_CheckAttach(); + + if (connect == USB_HOST_ATTACH) + { + g_usb0_host_attach_flag = USB_HOST_YES; + } + else + { + usb0_host_UsbDetach2(); + } + + return connect; +} + +#if(1) /* ohci_wrapp */ +#else +/******************************************************************************* +* Function Name: usb0_api_host_enumeration +* Description : Initializes USB module in the USB host mode. +* : USB connection is executed when executing this function in +* : the states that USB device isconnected to the USB port. +* Arguments : uint16_t devadr : device address +* Return Value : DEVDRV_USBH_DETACH_ERR : device detach +* : DEVDRV_SUCCESS : device enumeration success +* : DEVDRV_ERROR : device enumeration error +*******************************************************************************/ +int32_t usb0_api_host_enumeration (uint16_t devadr) +{ + int32_t ret; + uint16_t driver_sts; + + g_usb0_host_setUsbAddress = devadr; + + while (1) + { + driver_sts = usb0_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + ret = DEVDRV_USBH_DETACH_ERR; + break; + } + else if (driver_sts == USB_HOST_DRV_CONFIGURED) + { + ret = DEVDRV_SUCCESS; + break; + } + else if (driver_sts == USB_HOST_DRV_STALL) + { + ret = DEVDRV_ERROR; + break; + } + else if (driver_sts == USB_HOST_DRV_NORES) + { + ret = DEVDRV_ERROR; + break; + } + else + { + /* Do Nothing */ + } + } + + if (driver_sts == USB_HOST_DRV_NORES) + { + while (1) + { + driver_sts = usb0_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + break; + } + } + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_api_host_detach +* Description : USB detach routine +* Arguments : none +* Return Value : USB_HOST_DETACH : USB detach +* : USB_HOST_ATTACH : USB attach +* : DEVDRV_ERROR : error +*******************************************************************************/ +int32_t usb0_api_host_detach (void) +{ + int32_t ret; + uint16_t driver_sts; + + while (1) + { + driver_sts = usb0_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + ret = USB_HOST_DETACH; + break; + } + else if (driver_sts == USB_HOST_DRV_CONFIGURED) + { + ret = USB_HOST_ATTACH; + break; + } + else if (driver_sts == USB_HOST_DRV_STALL) + { + ret = DEVDRV_ERROR; + break; + } + else if (driver_sts == USB_HOST_DRV_NORES) + { + ret = DEVDRV_ERROR; + break; + } + else + { + /* Do Nothing */ + } + } + + if (driver_sts == USB_HOST_DRV_NORES) + { + while (1) + { + driver_sts = usb0_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + break; + } + } + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_api_host_data_in +* Description : Executes USB transfer as data-in in the argument specified pipe. +* Arguments : uint16_t devadr ; device address +* : uint16_t Pipe ; Pipe Number +* : uint32_t Size ; Data Size +* : uint8_t *data_buf ; Data data_buf Address +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_data_in (uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t * data_buf) +{ + int32_t ret; + + if (Pipe == USB_HOST_PIPE0) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipemaxp[Pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL) != devadr) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[Pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 1) + { + return DEVDRV_ERROR; + } + + if (g_usb0_host_pipe_status[Pipe] == USB_HOST_PIPE_IDLE) + { + usb0_host_start_receive_transfer(Pipe, Size, data_buf); + } + else + { + return DEVDRV_ERROR; /* Now pipe is busy */ + } + + /* waiting for completing routine */ + do + { + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb0_host_pipe_status[Pipe] != USB_HOST_PIPE_IDLE) && (g_usb0_host_pipe_status[Pipe] != USB_HOST_PIPE_WAIT)) + { + break; + } + + } while (1); + + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb0_host_pipe_status[Pipe]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + usb0_host_stop_transfer(Pipe); + + g_usb0_host_pipe_status[Pipe] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_api_host_data_out +* Description : Executes USB transfer as data-out in the argument specified pipe. +* Arguments : uint16_t devadr ; device address +* : uint16_t Pipe ; Pipe Number +* : uint32_t Size ; Data Size +* : uint8_t *data_buf ; Data data_buf Address +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_data_out (uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t * data_buf) +{ + int32_t ret; + + if (Pipe == USB_HOST_PIPE0) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipemaxp[Pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL) != devadr) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb0_host_pipecfg[Pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 0) + { + return DEVDRV_ERROR; + } + + if (g_usb0_host_pipe_status[Pipe] == USB_HOST_PIPE_IDLE) + { + usb0_host_start_send_transfer(Pipe, Size, data_buf); + } + else + { + return DEVDRV_ERROR; /* Now pipe is busy */ + } + + /* waiting for completing routine */ + do + { + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb0_host_pipe_status[Pipe] != USB_HOST_PIPE_IDLE) && (g_usb0_host_pipe_status[Pipe] != USB_HOST_PIPE_WAIT)) + { + break; + } + + } while (1); + + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb0_host_pipe_status[Pipe]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + usb0_host_stop_transfer(Pipe); + + g_usb0_host_pipe_status[Pipe] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_api_host_control_transfer +* Description : Executes USB control transfer. +* Arguments : uint16_t devadr ; device address +* : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* : uint8_t *buf ; Buffer +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_USBH_DETACH_ERR ; device detach +* : DEVDRV_USBH_CTRL_COM_ERR ; device no response +* : DEVDRV_USBH_STALL ; STALL +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_control_transfer (uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, + uint16_t Len, uint8_t * Buf) +{ + int32_t ret; + + do + { + ret = usb0_host_CtrlTransStart(devadr, Req, Val, Indx, Len, Buf); + + if (ret == DEVDRV_SUCCESS) + { + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb0_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_IDLE) + && (g_usb0_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_WAIT)) + { + break; + } + } + else + { + return DEVDRV_ERROR; + } + } while (1); + + if (g_usb0_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb0_host_pipe_status[USB_HOST_PIPE0]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_CTRL_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_api_host_set_endpoint +* Description : Sets end point on the information specified in the argument. +* Arguments : uint16_t devadr ; device address +* : uint8_t *configdescriptor ; device configration descriptor +* : USB_HOST_CFG_PIPETBL_t *user_table ; pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_set_endpoint (uint16_t devadr, USB_HOST_CFG_PIPETBL_t * user_table, uint8_t * configdescriptor) +{ + uint16_t ret; + uint32_t end_point; + uint32_t offset; + uint32_t totalLength; + USB_HOST_CFG_PIPETBL_t * pipe_table; + + /* End Point Search */ + end_point = 0; + offset = configdescriptor[0]; + totalLength = (uint16_t)(configdescriptor[2] + ((uint16_t)configdescriptor[3] << 8)); + + do + { + if (configdescriptor[offset + 1] == USB_HOST_ENDPOINT_DESC) + { + pipe_table = &user_table[end_point]; + + if (pipe_table->pipe_number == 0xffff) + { + break; + } + + ret = usb0_api_host_SetEndpointTable(devadr, pipe_table, (uint8_t *)&configdescriptor[offset]); + + if ((ret != USB_HOST_PIPE_IN) && (ret != USB_HOST_PIPE_OUT)) + { + return DEVDRV_ERROR; + } + + ++end_point; + } + + /* Next End Point Search */ + offset += configdescriptor[offset]; + + } while (offset < totalLength); + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb0_api_host_clear_endpoint +* Description : Clears the pipe definition table specified in the argument. +* Arguments : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_clear_endpoint (USB_HOST_CFG_PIPETBL_t * user_table) +{ + uint16_t pipe; + + for (pipe = USB_HOST_PIPE0; pipe <= USB_HOST_MAX_PIPE_NO; ++pipe) + { + if (user_table->pipe_number == 0xffff) + { + break; + } + user_table->pipe_cfg &= (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD); + user_table->pipe_max_pktsize = 0; + user_table->pipe_cycle = 0; + + user_table++; + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb0_api_host_clear_endpoint_pipe +* Description : Clears the pipe definition table specified in the argument. +* Arguments : uint16_t pipe_sel : Pipe Number +* : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_clear_endpoint_pipe (uint16_t pipe_sel, USB_HOST_CFG_PIPETBL_t * user_table) +{ + uint16_t pipe; + + for (pipe = USB_HOST_PIPE0; pipe <= USB_HOST_MAX_PIPE_NO; ++pipe) + { + if (user_table->pipe_number == 0xffff) + { + break; + } + + if (user_table->pipe_number == pipe_sel) + { + user_table->pipe_cfg &= (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD); + user_table->pipe_max_pktsize = 0; + user_table->pipe_cycle = 0; + break; + } + + user_table++; + } + + return DEVDRV_SUCCESS; +} +#endif + +/******************************************************************************* +* Function Name: usb0_api_host_SetEndpointTable +* Description : Sets the end point on the information specified by the argument. +* Arguments : uint16_t devadr : device address +* : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* : uint8_t *Table : Endpoint descriptor +* Return Value : USB_HOST_DIR_H_IN ; IN endpoint +* : USB_HOST_DIR_H_OUT ; OUT endpoint +* : USB_END_POINT_ERROR ; error +*******************************************************************************/ +uint16_t usb0_api_host_SetEndpointTable (uint16_t devadr, USB_HOST_CFG_PIPETBL_t * user_table, uint8_t * Table) +{ + uint16_t PipeCfg; + uint16_t PipeMaxp; + uint16_t pipe_number; + uint16_t ret; + uint16_t ret_flag = 0; // avoid warning. + + pipe_number = user_table->pipe_number; + + if (Table[1] != USB_HOST_ENDPOINT_DESC) + { + return USB_END_POINT_ERROR; + } + + switch (Table[3] & USB_HOST_EP_TYPE) + { + case USB_HOST_EP_CNTRL: + ret_flag = USB_END_POINT_ERROR; + break; + + case USB_HOST_EP_ISO: + if ((pipe_number != USB_HOST_PIPE1) && (pipe_number != USB_HOST_PIPE2)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_ISO; + break; + + case USB_HOST_EP_BULK: + if ((pipe_number < USB_HOST_PIPE1) || (pipe_number > USB_HOST_PIPE5)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_BULK; + break; + + case USB_HOST_EP_INT: + if ((pipe_number < USB_HOST_PIPE6) || (pipe_number > USB_HOST_PIPE9)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_INTERRUPT; + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + + /* Set pipe configuration table */ + if ((Table[2] & USB_HOST_EP_DIR_MASK) == USB_HOST_EP_IN) /* IN(receive) */ + { + if (PipeCfg == USB_HOST_ISO) + { + /* Transfer Type is ISO*/ + PipeCfg |= USB_HOST_DIR_H_IN; + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + case USB_HOST_D0USE: + case USB_HOST_D1USE: + case USB_HOST_D0DMA: + case USB_HOST_D1DMA: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & USB_HOST_DBLBFIELD); + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + } + else + { + /* Transfer Type is BULK or INT */ + PipeCfg |= (USB_HOST_SHTNAKON | USB_HOST_DIR_H_IN); /* Compulsory SHTNAK */ + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + case USB_HOST_D0USE: + case USB_HOST_D1USE: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); + break; + + case USB_HOST_D0DMA: + case USB_HOST_D1DMA: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); +#ifdef __USB_DMA_BFRE_ENABLE__ + /* this routine cannnot be perfomred if read operation is executed in buffer size */ + PipeCfg |= USB_HOST_BFREON; +#endif + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + } + ret = USB_HOST_PIPE_IN; + } + else /* OUT(send) */ + { + if (PipeCfg == USB_HOST_ISO) + { + /* Transfer Type is ISO*/ + PipeCfg |= (uint16_t)(user_table->pipe_cfg & USB_HOST_DBLBFIELD); + } + else + { + /* Transfer Type is BULK or INT */ + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); + } + PipeCfg |= USB_HOST_DIR_H_OUT; + ret = USB_HOST_PIPE_OUT; + } + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + g_usb0_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_CFIFO_USE; + break; + + case USB_HOST_D0USE: + g_usb0_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D0FIFO_USE; + break; + + case USB_HOST_D1USE: + g_usb0_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D1FIFO_USE; + break; + + case USB_HOST_D0DMA: + g_usb0_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D0FIFO_DMA; + break; + + case USB_HOST_D1DMA: + g_usb0_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D1FIFO_DMA; + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + + /* Endpoint number set */ + PipeCfg |= (uint16_t)(Table[2] & USB_HOST_EP_NUM_MASK); + g_usb0_host_PipeTbl[pipe_number] |= (uint16_t)(Table[2] & USB_HOST_EP_NUM_MASK); + + /* Max packet size set */ + PipeMaxp = (uint16_t)((uint16_t)Table[4] | (uint16_t)((uint16_t)Table[5] << 8)); + + if (PipeMaxp == 0u) + { + return USB_END_POINT_ERROR; + } + + /* Set device address */ + PipeMaxp |= (uint16_t)(devadr << 12); + + user_table->pipe_cfg = PipeCfg; + user_table->pipe_max_pktsize = PipeMaxp; + + usb0_host_resetEP(user_table); + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_host_resetEP +* Description : Sets the end point on the information specified by the argument. +* Arguments : USB_HOST_CFG_PIPETBL_t *tbl : pipe table +* Return Value : none +*******************************************************************************/ +static void usb0_host_resetEP (USB_HOST_CFG_PIPETBL_t * tbl) +{ + + uint16_t pipe; + + /* Host pipe */ + /* The pipe number of pipe definition table is obtained */ + pipe = (uint16_t)(tbl->pipe_number & USB_HOST_BITCURPIPE); /* Pipe Number */ + + /* FIFO port access pipe is set to initial value */ + /* The connection with FIFO should be cut before setting the pipe */ + if (RZA_IO_RegRead_16(&USB200.CFIFOSEL, + USB_CFIFOSEL_CURPIPE_SHIFT, + USB_CFIFOSEL_CURPIPE) == pipe) + { + usb0_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + if (RZA_IO_RegRead_16(&USB200.D0FIFOSEL, + USB_DnFIFOSEL_CURPIPE_SHIFT, + USB_DnFIFOSEL_CURPIPE) == pipe) + { + usb0_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + if (RZA_IO_RegRead_16(&USB200.D1FIFOSEL, + USB_DnFIFOSEL_CURPIPE_SHIFT, + USB_DnFIFOSEL_CURPIPE) == pipe) + { + usb0_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + /* Interrupt of pipe set is disabled */ + usb0_host_disable_brdy_int(pipe); + usb0_host_disable_nrdy_int(pipe); + usb0_host_disable_bemp_int(pipe); + + /* Pipe to set is set to NAK */ + usb0_host_set_pid_nak(pipe); + + /* Pipe is set */ + USB200.PIPESEL = pipe; + + USB200.PIPECFG = tbl->pipe_cfg; + USB200.PIPEBUF = tbl->pipe_buf; + USB200.PIPEMAXP = tbl->pipe_max_pktsize; + USB200.PIPEPERI = tbl->pipe_cycle; + + g_usb0_host_pipecfg[pipe] = tbl->pipe_cfg; + g_usb0_host_pipebuf[pipe] = tbl->pipe_buf; + g_usb0_host_pipemaxp[pipe] = tbl->pipe_max_pktsize; + g_usb0_host_pipeperi[pipe] = tbl->pipe_cycle; + + /* Sequence bit clear */ + usb0_host_set_sqclr(pipe); + + usb0_host_aclrm(pipe); + usb0_host_set_csclr(pipe); + + /* Pipe window selection is set to unused */ + USB200.PIPESEL = USB_HOST_PIPE0; + +} + +#if(1) /* ohci_wrapp */ +#else +/******************************************************************************* +* Function Name: usb0_api_host_data_count +* Description : Get g_usb0_host_data_count[pipe] +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t *data_count ; return g_usb0_data_count[pipe] +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb0_api_host_data_count (uint16_t pipe, uint32_t * data_count) +{ + if (pipe > USB_HOST_MAX_PIPE_NO) + { + return DEVDRV_ERROR; + } + + *data_count = g_usb0_host_PipeDataSize[pipe]; + + return DEVDRV_SUCCESS; +} +#endif + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/src/host/usb0_host_global.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,137 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_global.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +const uint16_t g_usb0_host_bit_set[16] = +{ + 0x0001, 0x0002, 0x0004, 0x0008, + 0x0010, 0x0020, 0x0040, 0x0080, + 0x0100, 0x0200, 0x0400, 0x0800, + 0x1000, 0x2000, 0x4000, 0x8000 +}; + +uint32_t g_usb0_host_data_count[USB_HOST_MAX_PIPE_NO + 1]; +uint8_t * g_usb0_host_data_pointer[USB_HOST_MAX_PIPE_NO + 1]; + +uint16_t g_usb0_host_PipeIgnore[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb0_host_PipeTbl[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb0_host_pipe_status[USB_HOST_MAX_PIPE_NO + 1]; +uint32_t g_usb0_host_PipeDataSize[USB_HOST_MAX_PIPE_NO + 1]; + +USB_HOST_DMA_t g_usb0_host_DmaInfo[2]; + +uint16_t g_usb0_host_DmaPipe[2]; +uint16_t g_usb0_host_DmaBval[2]; +uint16_t g_usb0_host_DmaStatus[2]; + +uint16_t g_usb0_host_driver_state; +uint16_t g_usb0_host_ConfigNum; +uint16_t g_usb0_host_CmdStage; +uint16_t g_usb0_host_bchg_flag; +uint16_t g_usb0_host_detach_flag; +uint16_t g_usb0_host_attach_flag; + +uint16_t g_usb0_host_UsbAddress; +uint16_t g_usb0_host_setUsbAddress; +uint16_t g_usb0_host_default_max_packet[USB_HOST_MAX_DEVICE + 1]; +uint16_t g_usb0_host_UsbDeviceSpeed; +uint16_t g_usb0_host_SupportUsbDeviceSpeed; + +uint16_t g_usb0_host_SavReq; +uint16_t g_usb0_host_SavVal; +uint16_t g_usb0_host_SavIndx; +uint16_t g_usb0_host_SavLen; + +uint16_t g_usb0_host_pipecfg[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb0_host_pipebuf[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb0_host_pipemaxp[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb0_host_pipeperi[USB_HOST_MAX_PIPE_NO + 1]; + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_init_pipe_status +* Description : Initialize pipe status. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_init_pipe_status (void) +{ + uint16_t loop; + + g_usb0_host_ConfigNum = 0; + + for (loop = 0; loop < (USB_HOST_MAX_PIPE_NO + 1); ++loop) + { + g_usb0_host_pipe_status[loop] = USB_HOST_PIPE_IDLE; + g_usb0_host_PipeDataSize[loop] = 0; + + /* pipe configuration in usb0_host_resetEP() */ + g_usb0_host_pipecfg[loop] = 0; + g_usb0_host_pipebuf[loop] = 0; + g_usb0_host_pipemaxp[loop] = 0; + g_usb0_host_pipeperi[loop] = 0; + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/src/host/usb0_host_usbint.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,496 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_usbint.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#if(1) /* ohci_wrapp */ +#include "ohci_wrapp_RZ_A1_local.h" +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb0_host_interrupt1(void); +static void usb0_host_BRDYInterrupt(uint16_t Status, uint16_t Int_enbl); +static void usb0_host_NRDYInterrupt(uint16_t Status, uint16_t Int_enbl); +static void usb0_host_BEMPInterrupt(uint16_t Status, uint16_t Int_enbl); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_interrupt +* Description : Executes USB interrupt. +* : Register this function in the USB interrupt handler. +* : Set CFIF0 in the pipe set before the interrupt after executing +* : this function. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb0_host_interrupt (uint32_t int_sense) +{ + uint16_t savepipe1; + uint16_t savepipe2; + uint16_t buffer; + + savepipe1 = USB200.CFIFOSEL; + savepipe2 = USB200.PIPESEL; + usb0_host_interrupt1(); + + /* Control transmission changes ISEL within interruption processing. */ + /* For this reason, write return of ISEL cannot be performed. */ + buffer = USB200.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(savepipe1 & USB_HOST_BITCURPIPE); + USB200.CFIFOSEL = buffer; + USB200.PIPESEL = savepipe2; +} + +/******************************************************************************* +* Function Name: usb0_host_interrupt1 +* Description : Execue the USB interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_interrupt1 (void) +{ + uint16_t intsts0; + uint16_t intsts1; + uint16_t intenb0; + uint16_t intenb1; + uint16_t brdysts; + uint16_t nrdysts; + uint16_t bempsts; + uint16_t brdyenb; + uint16_t nrdyenb; + uint16_t bempenb; + volatile uint16_t dumy_sts; + + intsts0 = USB200.INTSTS0; + intsts1 = USB200.INTSTS1; + intenb0 = USB200.INTENB0; + intenb1 = USB200.INTENB1; + + if ((intsts1 & USB_HOST_BITBCHG) && (intenb1 & USB_HOST_BITBCHGE)) + { + USB200.INTSTS1 = (uint16_t)~USB_HOST_BITBCHG; + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); + g_usb0_host_bchg_flag = USB_HOST_YES; + } + else if ((intsts1 & USB_HOST_BITSACK) && (intenb1 & USB_HOST_BITSACKE)) + { + USB200.INTSTS1 = (uint16_t)~USB_HOST_BITSACK; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); +#else + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; +#endif + } + else if ((intsts1 & USB_HOST_BITSIGN) && (intenb1 & USB_HOST_BITSIGNE)) + { + USB200.INTSTS1 = (uint16_t)~USB_HOST_BITSIGN; +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#else + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_NORES; +#endif + } + else if (((intsts1 & USB_HOST_BITDTCH) == USB_HOST_BITDTCH) + && ((intenb1 & USB_HOST_BITDTCHE) == USB_HOST_BITDTCHE)) + { + USB200.INTSTS1 = (uint16_t)~USB_HOST_BITDTCH; + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); + g_usb0_host_detach_flag = USB_HOST_YES; + + Userdef_USB_usb0_host_detach(); + + usb0_host_UsbDetach2(); + } + else if (((intsts1 & USB_HOST_BITATTCH) == USB_HOST_BITATTCH) + && ((intenb1 & USB_HOST_BITATTCHE) == USB_HOST_BITATTCHE)) + { + USB200.INTSTS1 = (uint16_t)~USB_HOST_BITATTCH; + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); + g_usb0_host_attach_flag = USB_HOST_YES; + + Userdef_USB_usb0_host_attach(); + + usb0_host_UsbAttach(); + } + else if ((intsts0 & intenb0 & (USB_HOST_BITBEMP | USB_HOST_BITNRDY | USB_HOST_BITBRDY))) + { + brdysts = USB200.BRDYSTS; + nrdysts = USB200.NRDYSTS; + bempsts = USB200.BEMPSTS; + brdyenb = USB200.BRDYENB; + nrdyenb = USB200.NRDYENB; + bempenb = USB200.BEMPENB; + + if ((intsts0 & USB_HOST_BITBRDY) && (intenb0 & USB_HOST_BITBRDYE) && (brdysts & brdyenb)) + { + usb0_host_BRDYInterrupt(brdysts, brdyenb); + } + else if ((intsts0 & USB_HOST_BITBEMP) && (intenb0 & USB_HOST_BITBEMPE) && (bempsts & bempenb)) + { + usb0_host_BEMPInterrupt(bempsts, bempenb); + } + else if ((intsts0 & USB_HOST_BITNRDY) && (intenb0 & USB_HOST_BITNRDYE) && (nrdysts & nrdyenb)) + { + usb0_host_NRDYInterrupt(nrdysts, nrdyenb); + } + else + { + /* Do Nothing */ + } + } + else + { + /* Do Nothing */ + } + + /* Three dummy read for clearing interrupt requests */ + dumy_sts = USB200.INTSTS0; + dumy_sts = USB200.INTSTS1; + +} + +/******************************************************************************* +* Function Name: usb0_host_BRDYInterrupt +* Description : Executes USB BRDY interrupt. +* Arguments : uint16_t Status ; BRDYSTS Register Value +* : uint16_t Int_enbl ; BRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_BRDYInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t buffer; + volatile uint16_t dumy_sts; + + if ((Status & g_usb0_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb0_host_bit_set[USB_HOST_PIPE0])) + { + USB200.BRDYSTS = (uint16_t)~g_usb0_host_bit_set[USB_HOST_PIPE0]; + +#if(1) /* ohci_wrapp */ + switch ((g_usb0_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + buffer = usb0_host_read_buffer_c(USB_HOST_PIPE0); + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb0_host_read_buffer_c(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_READOVER: /* buffer over */ + USB200.CFIFOCTR = USB_HOST_BITBCLR; + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + break; + } +#else + switch ((g_usb0_host_CmdStage & (USB_HOST_MODE_FIELD | USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + case (USB_HOST_MODE_NO_DATA | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + buffer = usb0_host_read_buffer_c(USB_HOST_PIPE0); + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case (USB_HOST_MODE_READ | USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb0_host_read_buffer_c(USB_HOST_PIPE0); + + switch (buffer) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case USB_HOST_READOVER: /* buffer over */ + USB200.CFIFOCTR = USB_HOST_BITBCLR; + usb0_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + break; + } +#endif + } + else + { + usb0_host_brdy_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB200.BRDYSTS; +} + +/******************************************************************************* +* Function Name: usb0_host_NRDYInterrupt +* Description : Executes USB NRDY interrupt. +* Arguments : uint16_t Status ; NRDYSTS Register Value +* : uint16_t Int_enbl ; NRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_NRDYInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t pid; + volatile uint16_t dumy_sts; + + if ((Status & g_usb0_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb0_host_bit_set[USB_HOST_PIPE0])) + { + USB200.NRDYSTS = (uint16_t)~g_usb0_host_bit_set[USB_HOST_PIPE0]; + pid = usb0_host_get_pid(USB_HOST_PIPE0); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_STALL; +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + } + else if (pid == USB_HOST_PID_NAK) + { + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_NORES; +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + } + else + { + /* Do Nothing */ + } + } + else + { + usb0_host_nrdy_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB200.NRDYSTS; +} + +/******************************************************************************* +* Function Name: usb0_host_BEMPInterrupt +* Description : Executes USB BEMP interrupt. +* Arguments : uint16_t Status ; BEMPSTS Register Value +* : uint16_t Int_enbl ; BEMPENB Register Value +* Return Value : none +*******************************************************************************/ +void usb0_host_BEMPInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t buffer; + uint16_t pid; + volatile uint16_t dumy_sts; + + if ((Status & g_usb0_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb0_host_bit_set[USB_HOST_PIPE0])) + { + USB200.BEMPSTS = (uint16_t)~g_usb0_host_bit_set[USB_HOST_PIPE0]; + pid = usb0_host_get_pid(USB_HOST_PIPE0); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_STALL; +#if(1) /* ohci_wrapp */ + g_usb0_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + } + else + { +#if(1) /* ohci_wrapp */ + switch ((g_usb0_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb0_host_write_buffer(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_WRITING: /* Continue of data write */ + case USB_HOST_WRITEEND: /* End of data write (zero-length) */ + break; + + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_STATUS; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + /* do nothing */ + break; + } +#else + switch ((g_usb0_host_CmdStage & (USB_HOST_MODE_FIELD | USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_MODE_READ | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb0_host_write_buffer(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_WRITING: /* Continue of data write */ + case USB_HOST_WRITEEND: /* End of data write (zero-length) */ + break; + + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb0_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb0_host_CmdStage |= USB_HOST_STAGE_STATUS; + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb0_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb0_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + default: + /* do nothing */ + break; + } +#endif + } + } + else + { + usb0_host_bemp_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB200.BEMPSTS; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/src/host/usb0_host_usbsig.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,637 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_usbsig.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb0_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb0_host_EnableINT_Module(void); +static void usb0_host_Enable_AttachINT(void); +static void usb0_host_Disable_AttachINT(void); +static void usb0_host_Disable_BchgINT(void); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb0_host_InitModule +* Description : Initializes the USB module in USB host module. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_InitModule (void) +{ + uint16_t buf1; + uint16_t buf2; + uint16_t buf3; + + usb0_host_init_pipe_status(); + + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 1, + USB_SYSCFG_DCFM_SHIFT, + USB_SYSCFG_DCFM); /* HOST mode */ + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 1, + USB_SYSCFG_DRPD_SHIFT, + USB_SYSCFG_DRPD); /* PORT0 D+, D- setting */ + + do + { + buf1 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb0_host_delay_xms(50); + buf2 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb0_host_delay_xms(50); + buf3 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + + } while ((buf1 != buf2) || (buf1 != buf3)); + + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 1, + USB_SYSCFG_USBE_SHIFT, + USB_SYSCFG_USBE); + + USB200.CFIFOSEL = (uint16_t)(USB_HOST_BITRCNT | USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); + USB200.D0FIFOSEL = (uint16_t)( USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); + USB200.D1FIFOSEL = (uint16_t)( USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); +} + +/******************************************************************************* +* Function Name: usb0_host_CheckAttach +* Description : Returns the USB device connection state. +* Arguments : none +* Return Value : uint16_t ; USB_HOST_ATTACH : Attached +* : ; USB_HOST_DETACH : not Attached +*******************************************************************************/ +uint16_t usb0_host_CheckAttach (void) +{ + uint16_t buf1; + uint16_t buf2; + uint16_t buf3; + uint16_t rhst; + + do + { + buf1 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb0_host_delay_xms(50); + buf2 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb0_host_delay_xms(50); + buf3 = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + + } while ((buf1 != buf2) || (buf1 != buf3)); + + rhst = RZA_IO_RegRead_16(&USB200.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (rhst == USB_HOST_UNDECID) + { + if (buf1 == USB_HOST_FS_JSTS) + { + if (g_usb0_host_SupportUsbDeviceSpeed == USB_HOST_HIGH_SPEED) + { + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 1, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + } + else + { + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + } + return USB_HOST_ATTACH; + } + else if (buf1 == USB_HOST_LS_JSTS) + { + /* Low Speed Device */ + RZA_IO_RegWrite_16(&USB200.SYSCFG0, + 0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + return USB_HOST_ATTACH; + } + else + { + /* Do Nothing */ + } + } + else if ((rhst == USB_HOST_HSMODE) || (rhst == USB_HOST_FSMODE)) + { + return USB_HOST_ATTACH; + } + else if (rhst == USB_HOST_LSMODE) + { + return USB_HOST_ATTACH; + } + else + { + /* Do Nothing */ + } + + return USB_HOST_DETACH; +} + +/******************************************************************************* +* Function Name: usb0_host_UsbAttach +* Description : Connects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_UsbAttach (void) +{ + usb0_host_EnableINT_Module(); + usb0_host_Disable_BchgINT(); + usb0_host_Disable_AttachINT(); + usb0_host_Enable_DetachINT(); +} + +/******************************************************************************* +* Function Name: usb0_host_UsbDetach +* Description : Disconnects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_UsbDetach (void) +{ + uint16_t pipe; + uint16_t devadr; + + g_usb0_host_driver_state = USB_HOST_DRV_DETACHED; + + /* Terminate all the pipes in which communications on port */ + /* are currently carried out */ + for (pipe = 0; pipe < (USB_HOST_MAX_PIPE_NO + 1); ++pipe) + { + if (g_usb0_host_pipe_status[pipe] != USB_HOST_PIPE_IDLE) + { + if (pipe == USB_HOST_PIPE0) + { + devadr = RZA_IO_RegRead_16(&USB200.DCPMAXP, + USB_DCPMAXP_DEVSEL_SHIFT, + USB_DCPMAXP_DEVSEL); + } + else + { + devadr = RZA_IO_RegRead_16(&g_usb0_host_pipemaxp[pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL); + } + + if (devadr == g_usb0_host_UsbAddress) + { + usb0_host_stop_transfer(pipe); + } + + g_usb0_host_pipe_status[pipe] = USB_HOST_PIPE_IDLE; + } + } + + g_usb0_host_ConfigNum = 0; + g_usb0_host_UsbAddress = 0; + g_usb0_host_default_max_packet[USB_HOST_DEVICE_0] = 64; + + usb0_host_UsbDetach2(); +} + +/******************************************************************************* +* Function Name: usb0_host_UsbDetach2 +* Description : Disconnects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_UsbDetach2 (void) +{ + usb0_host_Disable_DetachINT(); + usb0_host_Disable_BchgINT(); + usb0_host_Enable_AttachINT(); +} + +/******************************************************************************* +* Function Name: usb0_host_UsbBusReset +* Description : Issues the USB bus reset signal. +* Arguments : none +* Return Value : uint16_t ; RHST +*******************************************************************************/ +uint16_t usb0_host_UsbBusReset (void) +{ + uint16_t buffer; + uint16_t loop; + + RZA_IO_RegWrite_16(&USB200.DVSTCTR0, + 1, + USB_DVSTCTR0_USBRST_SHIFT, + USB_DVSTCTR0_USBRST); + RZA_IO_RegWrite_16(&USB200.DVSTCTR0, + 0, + USB_DVSTCTR0_UACT_SHIFT, + USB_DVSTCTR0_UACT); + + Userdef_USB_usb0_host_delay_xms(50); + + buffer = USB200.DVSTCTR0; + buffer &= (uint16_t)(~(USB_HOST_BITRST)); + buffer |= USB_HOST_BITUACT; + USB200.DVSTCTR0 = buffer; + + Userdef_USB_usb0_host_delay_xms(20); + + for (loop = 0, buffer = USB_HOST_HSPROC; loop < 3; ++loop) + { + buffer = RZA_IO_RegRead_16(&USB200.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (buffer == USB_HOST_HSPROC) + { + Userdef_USB_usb0_host_delay_xms(10); + } + else + { + break; + } + } + + return buffer; +} + +/******************************************************************************* +* Function Name: usb0_host_UsbResume +* Description : Issues the USB resume signal. +* Arguments : none +* Return Value : int32_t ; DEVDRV_SUCCESS +* : ; DEVDRV_ERROR +*******************************************************************************/ +int32_t usb0_host_UsbResume (void) +{ + uint16_t buf; + + if ((g_usb0_host_driver_state & USB_HOST_DRV_SUSPEND) == 0) + { + /* not SUSPEND */ + return DEVDRV_ERROR; + } + + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); + RZA_IO_RegWrite_16(&USB200.DVSTCTR0, + 1, + USB_DVSTCTR0_RESUME_SHIFT, + USB_DVSTCTR0_RESUME); + Userdef_USB_usb0_host_delay_xms(20); + + buf = USB200.DVSTCTR0; + buf &= (uint16_t)(~(USB_HOST_BITRESUME)); + buf |= USB_HOST_BITUACT; + USB200.DVSTCTR0 = buf; + + g_usb0_host_driver_state &= (uint16_t)~USB_HOST_DRV_SUSPEND; + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb0_host_UsbSuspend +* Description : Issues the USB suspend signal. +* Arguments : none +* Return Value : int32_t ; DEVDRV_SUCCESS :not SUSPEND +* : ; DEVDRV_ERROR :SUSPEND +*******************************************************************************/ +int32_t usb0_host_UsbSuspend (void) +{ + uint16_t buf; + + if ((g_usb0_host_driver_state & USB_HOST_DRV_SUSPEND) != 0) + { + /* SUSPEND */ + return DEVDRV_ERROR; + } + + RZA_IO_RegWrite_16(&USB200.DVSTCTR0, + 0, + USB_DVSTCTR0_UACT_SHIFT, + USB_DVSTCTR0_UACT); + + Userdef_USB_usb0_host_delay_xms(5); + + buf = RZA_IO_RegRead_16(&USB200.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + if ((buf != USB_HOST_FS_JSTS) && (buf != USB_HOST_LS_JSTS)) + { + usb0_host_UsbDetach(); + } + else + { + g_usb0_host_driver_state |= USB_HOST_DRV_SUSPEND; + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb0_host_Enable_DetachINT +* Description : Enables the USB disconnection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_Enable_DetachINT (void) +{ + USB200.INTSTS1 = (uint16_t)(~(USB_HOST_BITDTCH)); + RZA_IO_RegWrite_16(&USB200.INTENB1, + 1, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); +} + +/******************************************************************************* +* Function Name: usb0_host_Disable_DetachINT +* Description : Disables the USB disconnection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_Disable_DetachINT (void) +{ + USB200.INTSTS1 = (uint16_t)(~(USB_HOST_BITDTCH)); + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); +} + +/******************************************************************************* +* Function Name: usb0_host_Enable_AttachINT +* Description : Enables the USB connection detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_Enable_AttachINT (void) +{ + USB200.INTSTS1 = (uint16_t)(~(USB_HOST_BITATTCH)); + RZA_IO_RegWrite_16(&USB200.INTENB1, + 1, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); +} + +/******************************************************************************* +* Function Name: usb0_host_Disable_AttachINT +* Description : Disables the USB connection detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_Disable_AttachINT (void) +{ + USB200.INTSTS1 = (uint16_t)(~(USB_HOST_BITATTCH)); + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); +} + +/******************************************************************************* +* Function Name: usb0_host_Disable_BchgINT +* Description : Disables the USB bus change detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_Disable_BchgINT (void) +{ + USB200.INTSTS1 = (uint16_t)(~(USB_HOST_BITBCHG)); + RZA_IO_RegWrite_16(&USB200.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); +} + +/******************************************************************************* +* Function Name: usb0_host_set_devadd +* Description : DEVADDn register is set by specified value +* Arguments : uint16_t addr : Device address +* : uint16_t *devadd : Set value +* Return Value : none +*******************************************************************************/ +void usb0_host_set_devadd (uint16_t addr, uint16_t * devadd) +{ + uint16_t * ptr; + uint16_t ret_flag = DEVDRV_FLAG_ON; // avoid warning. + + switch (addr) + { + case USB_HOST_DEVICE_0: + ptr = (uint16_t *)&USB200.DEVADD0; + break; + + case USB_HOST_DEVICE_1: + ptr = (uint16_t *)&USB200.DEVADD1; + break; + + case USB_HOST_DEVICE_2: + ptr = (uint16_t *)&USB200.DEVADD2; + break; + + case USB_HOST_DEVICE_3: + ptr = (uint16_t *)&USB200.DEVADD3; + break; + + case USB_HOST_DEVICE_4: + ptr = (uint16_t *)&USB200.DEVADD4; + break; + + case USB_HOST_DEVICE_5: + ptr = (uint16_t *)&USB200.DEVADD5; + break; + + case USB_HOST_DEVICE_6: + ptr = (uint16_t *)&USB200.DEVADD6; + break; + + case USB_HOST_DEVICE_7: + ptr = (uint16_t *)&USB200.DEVADD7; + break; + + case USB_HOST_DEVICE_8: + ptr = (uint16_t *)&USB200.DEVADD8; + break; + + case USB_HOST_DEVICE_9: + ptr = (uint16_t *)&USB200.DEVADD9; + break; + + case USB_HOST_DEVICE_10: + ptr = (uint16_t *)&USB200.DEVADDA; + break; + + default: + ret_flag = DEVDRV_FLAG_OFF; + break; + } + + if (ret_flag == DEVDRV_FLAG_ON) + { + *ptr = (uint16_t)(*devadd & USB_HOST_DEVADD_MASK); + } +} + +/******************************************************************************* +* Function Name: usb0_host_get_devadd +* Description : DEVADDn register is obtained +* Arguments : uint16_t addr : Device address +* : uint16_t *devadd : USB_HOST_DEVADD register value +* Return Value : none +*******************************************************************************/ +void usb0_host_get_devadd (uint16_t addr, uint16_t * devadd) +{ + uint16_t * ptr; + uint16_t ret_flag = DEVDRV_FLAG_ON; // avoid warning. + + switch (addr) + { + case USB_HOST_DEVICE_0: + ptr = (uint16_t *)&USB200.DEVADD0; + break; + + case USB_HOST_DEVICE_1: + ptr = (uint16_t *)&USB200.DEVADD1; + break; + + case USB_HOST_DEVICE_2: + ptr = (uint16_t *)&USB200.DEVADD2; + break; + + case USB_HOST_DEVICE_3: + ptr = (uint16_t *)&USB200.DEVADD3; + break; + + case USB_HOST_DEVICE_4: + ptr = (uint16_t *)&USB200.DEVADD4; + break; + + case USB_HOST_DEVICE_5: + ptr = (uint16_t *)&USB200.DEVADD5; + break; + + case USB_HOST_DEVICE_6: + ptr = (uint16_t *)&USB200.DEVADD6; + break; + + case USB_HOST_DEVICE_7: + ptr = (uint16_t *)&USB200.DEVADD7; + break; + + case USB_HOST_DEVICE_8: + ptr = (uint16_t *)&USB200.DEVADD8; + break; + + case USB_HOST_DEVICE_9: + ptr = (uint16_t *)&USB200.DEVADD9; + break; + + case USB_HOST_DEVICE_10: + ptr = (uint16_t *)&USB200.DEVADDA; + break; + + default: + ret_flag = DEVDRV_FLAG_OFF; + break; + } + + if (ret_flag == DEVDRV_FLAG_ON) + { + *devadd = *ptr; + } +} + +/******************************************************************************* +* Function Name: usb0_host_EnableINT_Module +* Description : Enables BEMP/NRDY/BRDY interrupt and SIGN/SACK interrupt. +* : Enables NRDY/BEMP interrupt in the pipe0. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb0_host_EnableINT_Module (void) +{ + uint16_t buf; + + buf = USB200.INTENB0; + buf |= (USB_HOST_BITBEMPE | USB_HOST_BITNRDYE | USB_HOST_BITBRDYE); + USB200.INTENB0 = buf; + + buf = USB200.INTENB1; + buf |= (USB_HOST_BITSIGNE | USB_HOST_BITSACKE); + USB200.INTENB1 = buf; + + usb0_host_enable_nrdy_int(USB_HOST_PIPE0); + usb0_host_enable_bemp_int(USB_HOST_PIPE0); +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/src/userdef/usb0_host_dmacdrv.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,698 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_dmacdrv.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "r_typedefs.h" +#include "iodefine.h" +#include "rza_io_regrw.h" +#include "usb0_host_dmacdrv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define DMAC_INDEFINE (255) /* Macro definition when REQD bit is not used */ + +/* ==== Request setting information for on-chip peripheral module ==== */ +typedef enum dmac_peri_req_reg_type +{ + DMAC_REQ_MID, + DMAC_REQ_RID, + DMAC_REQ_AM, + DMAC_REQ_LVL, + DMAC_REQ_REQD +} dmac_peri_req_reg_type_t; + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +/* ==== Prototype declaration ==== */ + +/* ==== Global variable ==== */ +/* On-chip peripheral module request setting table */ +static const uint8_t usb0_host_dmac_peri_req_init_table[8][5] = +{ + /* MID,RID, AM,LVL,REQD */ + { 32, 3, 2, 1, 1}, /* USB_0 channel 0 transmit FIFO empty */ + { 32, 3, 2, 1, 0}, /* USB_0 channel 0 receive FIFO full */ + { 33, 3, 2, 1, 1}, /* USB_0 channel 1 transmit FIFO empty */ + { 33, 3, 2, 1, 0}, /* USB_0 channel 1 receive FIFO full */ + { 34, 3, 2, 1, 1}, /* USB_1 channel 0 transmit FIFO empty */ + { 34, 3, 2, 1, 0}, /* USB_1 channel 0 receive FIFO full */ + { 35, 3, 2, 1, 1}, /* USB_1 channel 1 transmit FIFO empty */ + { 35, 3, 2, 1, 0}, /* USB_1 channel 1 receive FIFO full */ +}; + + +/******************************************************************************* +* Function Name: usb0_host_DMAC1_PeriReqInit +* Description : Sets the register mode for DMA mode and the on-chip peripheral +* : module request for transfer request for DMAC channel 1. +* : Executes DMAC initial setting using the DMA information +* : specified by the argument *trans_info and the enabled/disabled +* : continuous transfer specified by the argument continuation. +* : Registers DMAC channel 1 interrupt handler function and sets +* : the interrupt priority level. Then enables transfer completion +* : interrupt. +* Arguments : dmac_transinfo_t * trans_info : Setting information to DMAC +* : : register +* : uint32_t dmamode : DMA mode (only for DMAC_MODE_REGISTER) +* : uint32_t continuation : Set continuous transfer to be valid +* : : after DMA transfer has been completed +* : DMAC_SAMPLE_CONTINUATION : Execute continuous transfer +* : DMAC_SAMPLE_SINGLE : Do not execute continuous +* : : transfer +* : uint32_t request_factor : Factor for on-chip peripheral module +* : : request +* : DMAC_REQ_OSTM0TINT : OSTM_0 compare match +* : DMAC_REQ_OSTM1TINT : OSTM_1 compare match +* : DMAC_REQ_TGI0A : MTU2_0 input capture/compare match +* : : +* : uint32_t req_direction : Setting value of CHCFG_n register +* : : REQD bit +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC1_PeriReqInit (const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction) +{ + /* ==== Register mode ==== */ + if (DMAC_MODE_REGISTER == dmamode) + { + /* ==== Next0 register set ==== */ + DMAC1.N0SA_n = trans_info->src_addr; /* Start address of transfer source */ + DMAC1.N0DA_n = trans_info->dst_addr; /* Start address of transfer destination */ + DMAC1.N0TB_n = trans_info->count; /* Total transfer byte count */ + + /* DAD : Transfer destination address counting direction */ + /* SAD : Transfer source address counting direction */ + /* DDS : Transfer destination transfer size */ + /* SDS : Transfer source transfer size */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + trans_info->daddr_dir, + DMAC1_CHCFG_n_DAD_SHIFT, + DMAC1_CHCFG_n_DAD); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + trans_info->saddr_dir, + DMAC1_CHCFG_n_SAD_SHIFT, + DMAC1_CHCFG_n_SAD); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + trans_info->dst_size, + DMAC1_CHCFG_n_DDS_SHIFT, + DMAC1_CHCFG_n_DDS); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + trans_info->src_size, + DMAC1_CHCFG_n_SDS_SHIFT, + DMAC1_CHCFG_n_SDS); + + /* DMS : Register mode */ + /* RSEL : Select Next0 register set */ + /* SBE : No discharge of buffer data when aborted */ + /* DEM : No DMA interrupt mask */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_DMS_SHIFT, + DMAC1_CHCFG_n_DMS); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_RSEL_SHIFT, + DMAC1_CHCFG_n_RSEL); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_SBE_SHIFT, + DMAC1_CHCFG_n_SBE); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_DEM_SHIFT, + DMAC1_CHCFG_n_DEM); + + /* ---- Continuous transfer ---- */ + if (DMAC_SAMPLE_CONTINUATION == continuation) + { + /* REN : Execute continuous transfer */ + /* RSW : Change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 1, + DMAC1_CHCFG_n_REN_SHIFT, + DMAC1_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 1, + DMAC1_CHCFG_n_RSW_SHIFT, + DMAC1_CHCFG_n_RSW); + } + /* ---- Single transfer ---- */ + else + { + /* REN : Do not execute continuous transfer */ + /* RSW : Do not change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_REN_SHIFT, + DMAC1_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_RSW_SHIFT, + DMAC1_CHCFG_n_RSW); + } + + /* TM : Single transfer */ + /* SEL : Channel setting */ + /* HIEN, LOEN : On-chip peripheral module request */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_TM_SHIFT, + DMAC1_CHCFG_n_TM); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 1, + DMAC1_CHCFG_n_SEL_SHIFT, + DMAC1_CHCFG_n_SEL); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 1, + DMAC1_CHCFG_n_HIEN_SHIFT, + DMAC1_CHCFG_n_HIEN); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + 0, + DMAC1_CHCFG_n_LOEN_SHIFT, + DMAC1_CHCFG_n_LOEN); + + /* ---- Set factor by specified on-chip peripheral module request ---- */ + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_AM], + DMAC1_CHCFG_n_AM_SHIFT, + DMAC1_CHCFG_n_AM); + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_LVL], + DMAC1_CHCFG_n_LVL_SHIFT, + DMAC1_CHCFG_n_LVL); + if (usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD] != DMAC_INDEFINE) + { + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD], + DMAC1_CHCFG_n_REQD_SHIFT, + DMAC1_CHCFG_n_REQD); + } + else + { + RZA_IO_RegWrite_32(&DMAC1.CHCFG_n, + req_direction, + DMAC1_CHCFG_n_REQD_SHIFT, + DMAC1_CHCFG_n_REQD); + } + RZA_IO_RegWrite_32(&DMAC01.DMARS, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_RID], + DMAC01_DMARS_CH1_RID_SHIFT, + DMAC01_DMARS_CH1_RID); + RZA_IO_RegWrite_32(&DMAC01.DMARS, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_MID], + DMAC01_DMARS_CH1_MID_SHIFT, + DMAC01_DMARS_CH1_MID); + + /* PR : Round robin mode */ + RZA_IO_RegWrite_32(&DMAC07.DCTRL_0_7, + 1, + DMAC07_DCTRL_0_7_PR_SHIFT, + DMAC07_DCTRL_0_7_PR); + } +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC1_Open +* Description : Enables DMAC channel 1 transfer. +* Arguments : uint32_t req : DMAC request mode +* Return Value : 0 : Succeeded in enabling DMA transfer +* : -1 : Failed to enable DMA transfer (due to DMA operation) +*******************************************************************************/ +int32_t usb0_host_DMAC1_Open (uint32_t req) +{ + int32_t ret; + volatile uint8_t dummy; + + /* Transferable? */ + if ((0 == RZA_IO_RegRead_32(&DMAC1.CHSTAT_n, + DMAC1_CHSTAT_n_EN_SHIFT, + DMAC1_CHSTAT_n_EN)) && + (0 == RZA_IO_RegRead_32(&DMAC1.CHSTAT_n, + DMAC1_CHSTAT_n_TACT_SHIFT, + DMAC1_CHSTAT_n_TACT))) + { + /* Clear Channel Status Register */ + RZA_IO_RegWrite_32(&DMAC1.CHCTRL_n, + 1, + DMAC1_CHCTRL_n_SWRST_SHIFT, + DMAC1_CHCTRL_n_SWRST); + dummy = RZA_IO_RegRead_32(&DMAC1.CHCTRL_n, + DMAC1_CHCTRL_n_SWRST_SHIFT, + DMAC1_CHCTRL_n_SWRST); + /* Enable DMA transfer */ + RZA_IO_RegWrite_32(&DMAC1.CHCTRL_n, + 1, + DMAC1_CHCTRL_n_SETEN_SHIFT, + DMAC1_CHCTRL_n_SETEN); + + /* ---- Request by software ---- */ + if (DMAC_REQ_MODE_SOFT == req) + { + /* DMA transfer Request by software */ + RZA_IO_RegWrite_32(&DMAC1.CHCTRL_n, + 1, + DMAC1_CHCTRL_n_STG_SHIFT, + DMAC1_CHCTRL_n_STG); + } + + ret = 0; + } + else + { + ret = -1; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC1_Close +* Description : Aborts DMAC channel 1 transfer. Returns the remaining transfer +* : byte count at the time of DMA transfer abort to the argument +* : *remain. +* Arguments : uint32_t * remain : Remaining transfer byte count when +* : : DMA transfer is aborted +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC1_Close (uint32_t * remain) +{ + + /* ==== Abort transfer ==== */ + RZA_IO_RegWrite_32(&DMAC1.CHCTRL_n, + 1, + DMAC1_CHCTRL_n_CLREN_SHIFT, + DMAC1_CHCTRL_n_CLREN); + + while (1 == RZA_IO_RegRead_32(&DMAC1.CHSTAT_n, + DMAC1_CHSTAT_n_TACT_SHIFT, + DMAC1_CHSTAT_n_TACT)) + { + /* Loop until transfer is aborted */ + } + + while (1 == RZA_IO_RegRead_32(&DMAC1.CHSTAT_n, + DMAC1_CHSTAT_n_EN_SHIFT, + DMAC1_CHSTAT_n_EN)) + { + /* Loop until 0 is set in EN before checking the remaining transfer byte count */ + } + /* ==== Obtain remaining transfer byte count ==== */ + *remain = DMAC1.CRTB_n; +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC1_Load_Set +* Description : Sets the transfer source address, transfer destination +* : address, and total transfer byte count respectively +* : specified by the argument src_addr, dst_addr, and count to +* : DMAC channel 1 as DMA transfer information. +* : Sets the register set selected by the CHCFG_n register +* : RSEL bit from the Next0 or Next1 register set. +* : This function should be called when DMA transfer of DMAC +* : channel 1 is aboted. +* Arguments : uint32_t src_addr : Transfer source address +* : uint32_t dst_addr : Transfer destination address +* : uint32_t count : Total transfer byte count +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC1_Load_Set (uint32_t src_addr, uint32_t dst_addr, uint32_t count) +{ + uint8_t reg_set; + + /* Obtain register set in use */ + reg_set = RZA_IO_RegRead_32(&DMAC1.CHSTAT_n, + DMAC1_CHSTAT_n_SR_SHIFT, + DMAC1_CHSTAT_n_SR); + + /* ==== Load ==== */ + if (0 == reg_set) + { + /* ---- Next0 Register Set ---- */ + DMAC1.N0SA_n = src_addr; /* Start address of transfer source */ + DMAC1.N0DA_n = dst_addr; /* Start address of transfer destination */ + DMAC1.N0TB_n = count; /* Total transfer byte count */ + } + else + { + /* ---- Next1 Register Set ---- */ + DMAC1.N1SA_n = src_addr; /* Start address of transfer source */ + DMAC1.N1DA_n = dst_addr; /* Start address of transfer destination */ + DMAC1.N1TB_n = count; /* Total transfer byte count */ + } +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC2_PeriReqInit +* Description : Sets the register mode for DMA mode and the on-chip peripheral +* : module request for transfer request for DMAC channel 2. +* : Executes DMAC initial setting using the DMA information +* : specified by the argument *trans_info and the enabled/disabled +* : continuous transfer specified by the argument continuation. +* : Registers DMAC channel 2 interrupt handler function and sets +* : the interrupt priority level. Then enables transfer completion +* : interrupt. +* Arguments : dmac_transinfo_t * trans_info : Setting information to DMAC +* : : register +* : uint32_t dmamode : DMA mode (only for DMAC_MODE_REGISTER) +* : uint32_t continuation : Set continuous transfer to be valid +* : : after DMA transfer has been completed +* : DMAC_SAMPLE_CONTINUATION : Execute continuous transfer +* : DMAC_SAMPLE_SINGLE : Do not execute continuous +* : : transfer +* : uint32_t request_factor : Factor for on-chip peripheral module +* : : request +* : DMAC_REQ_OSTM0TINT : OSTM_0 compare match +* : DMAC_REQ_OSTM1TINT : OSTM_1 compare match +* : DMAC_REQ_TGI0A : MTU2_0 input capture/compare match +* : : +* : uint32_t req_direction : Setting value of CHCFG_n register +* : : REQD bit +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC2_PeriReqInit (const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction) +{ + /* ==== Register mode ==== */ + if (DMAC_MODE_REGISTER == dmamode) + { + /* ==== Next0 register set ==== */ + DMAC2.N0SA_n = trans_info->src_addr; /* Start address of transfer source */ + DMAC2.N0DA_n = trans_info->dst_addr; /* Start address of transfer destination */ + DMAC2.N0TB_n = trans_info->count; /* Total transfer byte count */ + + /* DAD : Transfer destination address counting direction */ + /* SAD : Transfer source address counting direction */ + /* DDS : Transfer destination transfer size */ + /* SDS : Transfer source transfer size */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + trans_info->daddr_dir, + DMAC2_CHCFG_n_DAD_SHIFT, + DMAC2_CHCFG_n_DAD); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + trans_info->saddr_dir, + DMAC2_CHCFG_n_SAD_SHIFT, + DMAC2_CHCFG_n_SAD); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + trans_info->dst_size, + DMAC2_CHCFG_n_DDS_SHIFT, + DMAC2_CHCFG_n_DDS); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + trans_info->src_size, + DMAC2_CHCFG_n_SDS_SHIFT, + DMAC2_CHCFG_n_SDS); + + /* DMS : Register mode */ + /* RSEL : Select Next0 register set */ + /* SBE : No discharge of buffer data when aborted */ + /* DEM : No DMA interrupt mask */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_DMS_SHIFT, + DMAC2_CHCFG_n_DMS); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_RSEL_SHIFT, + DMAC2_CHCFG_n_RSEL); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_SBE_SHIFT, + DMAC2_CHCFG_n_SBE); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_DEM_SHIFT, + DMAC2_CHCFG_n_DEM); + + /* ---- Continuous transfer ---- */ + if (DMAC_SAMPLE_CONTINUATION == continuation) + { + /* REN : Execute continuous transfer */ + /* RSW : Change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 1, + DMAC2_CHCFG_n_REN_SHIFT, + DMAC2_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 1, + DMAC2_CHCFG_n_RSW_SHIFT, + DMAC2_CHCFG_n_RSW); + } + /* ---- Single transfer ---- */ + else + { + /* REN : Do not execute continuous transfer */ + /* RSW : Do not change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_REN_SHIFT, + DMAC2_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_RSW_SHIFT, + DMAC2_CHCFG_n_RSW); + } + + /* TM : Single transfer */ + /* SEL : Channel setting */ + /* HIEN, LOEN : On-chip peripheral module request */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_TM_SHIFT, + DMAC2_CHCFG_n_TM); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 2, + DMAC2_CHCFG_n_SEL_SHIFT, + DMAC2_CHCFG_n_SEL); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 1, + DMAC2_CHCFG_n_HIEN_SHIFT, + DMAC2_CHCFG_n_HIEN); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + 0, + DMAC2_CHCFG_n_LOEN_SHIFT, + DMAC2_CHCFG_n_LOEN); + + /* ---- Set factor by specified on-chip peripheral module request ---- */ + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_AM], + DMAC2_CHCFG_n_AM_SHIFT, + DMAC2_CHCFG_n_AM); + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_LVL], + DMAC2_CHCFG_n_LVL_SHIFT, + DMAC2_CHCFG_n_LVL); + if (usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD] != DMAC_INDEFINE) + { + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD], + DMAC2_CHCFG_n_REQD_SHIFT, + DMAC2_CHCFG_n_REQD); + } + else + { + RZA_IO_RegWrite_32(&DMAC2.CHCFG_n, + req_direction, + DMAC2_CHCFG_n_REQD_SHIFT, + DMAC2_CHCFG_n_REQD); + } + RZA_IO_RegWrite_32(&DMAC23.DMARS, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_RID], + DMAC23_DMARS_CH2_RID_SHIFT, + DMAC23_DMARS_CH2_RID); + RZA_IO_RegWrite_32(&DMAC23.DMARS, + usb0_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_MID], + DMAC23_DMARS_CH2_MID_SHIFT, + DMAC23_DMARS_CH2_MID); + + /* PR : Round robin mode */ + RZA_IO_RegWrite_32(&DMAC07.DCTRL_0_7, + 1, + DMAC07_DCTRL_0_7_PR_SHIFT, + DMAC07_DCTRL_0_7_PR); + } +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC2_Open +* Description : Enables DMAC channel 2 transfer. +* Arguments : uint32_t req : DMAC request mode +* Return Value : 0 : Succeeded in enabling DMA transfer +* : -1 : Failed to enable DMA transfer (due to DMA operation) +*******************************************************************************/ +int32_t usb0_host_DMAC2_Open (uint32_t req) +{ + int32_t ret; + volatile uint8_t dummy; + + /* Transferable? */ + if ((0 == RZA_IO_RegRead_32(&DMAC2.CHSTAT_n, + DMAC2_CHSTAT_n_EN_SHIFT, + DMAC2_CHSTAT_n_EN)) && + (0 == RZA_IO_RegRead_32(&DMAC2.CHSTAT_n, + DMAC2_CHSTAT_n_TACT_SHIFT, + DMAC2_CHSTAT_n_TACT))) + { + /* Clear Channel Status Register */ + RZA_IO_RegWrite_32(&DMAC2.CHCTRL_n, + 1, + DMAC2_CHCTRL_n_SWRST_SHIFT, + DMAC2_CHCTRL_n_SWRST); + dummy = RZA_IO_RegRead_32(&DMAC2.CHCTRL_n, + DMAC2_CHCTRL_n_SWRST_SHIFT, + DMAC2_CHCTRL_n_SWRST); + /* Enable DMA transfer */ + RZA_IO_RegWrite_32(&DMAC2.CHCTRL_n, + 1, + DMAC2_CHCTRL_n_SETEN_SHIFT, + DMAC2_CHCTRL_n_SETEN); + + /* ---- Request by software ---- */ + if (DMAC_REQ_MODE_SOFT == req) + { + /* DMA transfer Request by software */ + RZA_IO_RegWrite_32(&DMAC2.CHCTRL_n, + 1, + DMAC2_CHCTRL_n_STG_SHIFT, + DMAC2_CHCTRL_n_STG); + } + + ret = 0; + } + else + { + ret = -1; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC2_Close +* Description : Aborts DMAC channel 2 transfer. Returns the remaining transfer +* : byte count at the time of DMA transfer abort to the argument +* : *remain. +* Arguments : uint32_t * remain : Remaining transfer byte count when +* : : DMA transfer is aborted +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC2_Close (uint32_t * remain) +{ + + /* ==== Abort transfer ==== */ + RZA_IO_RegWrite_32(&DMAC2.CHCTRL_n, + 1, + DMAC2_CHCTRL_n_CLREN_SHIFT, + DMAC2_CHCTRL_n_CLREN); + + while (1 == RZA_IO_RegRead_32(&DMAC2.CHSTAT_n, + DMAC2_CHSTAT_n_TACT_SHIFT, + DMAC2_CHSTAT_n_TACT)) + { + /* Loop until transfer is aborted */ + } + + while (1 == RZA_IO_RegRead_32(&DMAC2.CHSTAT_n, + DMAC2_CHSTAT_n_EN_SHIFT, + DMAC2_CHSTAT_n_EN)) + { + /* Loop until 0 is set in EN before checking the remaining transfer byte count */ + } + /* ==== Obtain remaining transfer byte count ==== */ + *remain = DMAC2.CRTB_n; +} + +/******************************************************************************* +* Function Name: usb0_host_DMAC2_Load_Set +* Description : Sets the transfer source address, transfer destination +* : address, and total transfer byte count respectively +* : specified by the argument src_addr, dst_addr, and count to +* : DMAC channel 2 as DMA transfer information. +* : Sets the register set selected by the CHCFG_n register +* : RSEL bit from the Next0 or Next1 register set. +* : This function should be called when DMA transfer of DMAC +* : channel 2 is aboted. +* Arguments : uint32_t src_addr : Transfer source address +* : uint32_t dst_addr : Transfer destination address +* : uint32_t count : Total transfer byte count +* Return Value : none +*******************************************************************************/ +void usb0_host_DMAC2_Load_Set (uint32_t src_addr, uint32_t dst_addr, uint32_t count) +{ + uint8_t reg_set; + + /* Obtain register set in use */ + reg_set = RZA_IO_RegRead_32(&DMAC2.CHSTAT_n, + DMAC2_CHSTAT_n_SR_SHIFT, + DMAC2_CHSTAT_n_SR); + + /* ==== Load ==== */ + if (0 == reg_set) + { + /* ---- Next0 Register Set ---- */ + DMAC2.N0SA_n = src_addr; /* Start address of transfer source */ + DMAC2.N0DA_n = dst_addr; /* Start address of transfer destination */ + DMAC2.N0TB_n = count; /* Total transfer byte count */ + } + else + { + /* ---- Next1 Register Set ---- */ + DMAC2.N1SA_n = src_addr; /* Start address of transfer source */ + DMAC2.N1DA_n = dst_addr; /* Start address of transfer destination */ + DMAC2.N1TB_n = count; /* Total transfer byte count */ + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb0/src/userdef/usb0_host_userdef.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,778 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb0_host_userdef.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include <stdio.h> +#include "cmsis_os.h" +#include "r_typedefs.h" +#include "iodefine.h" +#include "devdrv_usb_host_api.h" +#include "usb0_host.h" +#include "VKRZA1H.h" /* INTC Driver Header */ +#include "usb0_host_dmacdrv.h" +#include "ohci_wrapp_RZ_A1_local.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define DUMMY_ACCESS OSTM0CNT + +/* #define CACHE_WRITEBACK */ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +extern int32_t io_cwb(unsigned long start, unsigned long end); + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb0_host_enable_dmac0(uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc); +static void usb0_host_enable_dmac1(uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc); +static void Userdef_USB_usb0_host_delay_10us_2(void); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_d0fifo_dmaintid +* Description : get D0FIFO DMA Interrupt ID +* Arguments : none +* Return Value : D0FIFO DMA Interrupt ID +*******************************************************************************/ +uint16_t Userdef_USB_usb0_host_d0fifo_dmaintid (void) +{ +#if(1) /* ohci_wrapp */ + return 0xFFFF; +#else + return DMAINT1_IRQn; +#endif +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_d1fifo_dmaintid +* Description : get D1FIFO DMA Interrupt ID +* Arguments : none +* Return Value : D1FIFO DMA Interrupt ID +*******************************************************************************/ +uint16_t Userdef_USB_usb0_host_d1fifo_dmaintid (void) +{ +#if(1) /* ohci_wrapp */ + return 0xFFFF; +#else + return DMAINT2_IRQn; +#endif +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_attach +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_attach (void) +{ +// printf("\n"); +// printf("channel 0 attach device\n"); +// printf("\n"); + ohciwrapp_loc_Connect(1); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_detach +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_detach (void) +{ +// printf("\n"); +// printf("channel 0 detach device\n"); +// printf("\n"); + ohciwrapp_loc_Connect(0); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_delay_1ms +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_delay_1ms (void) +{ + osDelay(1); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_delay_xms +* Description : Wait for the software in the period of time specified by the +* : argument. +* : Alter this function according to the user's system. +* Arguments : uint32_t msec ; Wait Time (msec) +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_delay_xms (uint32_t msec) +{ + osDelay(msec); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_delay_10us +* Description : Waits for software for the period specified by the argument. +* : Alter this function according to the user's system. +* Arguments : uint32_t usec ; Wait Time(x 10usec) +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_delay_10us (uint32_t usec) +{ + volatile int i; + + /* Wait 10us (Please change for your MCU) */ + for (i = 0; i < usec; ++i) + { + Userdef_USB_usb0_host_delay_10us_2(); + } +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_delay_10us_2 +* Description : Waits for software for the period specified by the argument. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +static void Userdef_USB_usb0_host_delay_10us_2 (void) +{ + volatile int i; + volatile unsigned long tmp; + + /* Wait 1us (Please change for your MCU) */ + for (i = 0; i < 14; ++i) + { + tmp = DUMMY_ACCESS; + } +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_delay_500ns +* Description : Wait for software for 500ns. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_delay_500ns (void) +{ + volatile int i; + volatile unsigned long tmp; + + /* Wait 500ns (Please change for your MCU) */ + /* Wait 500ns I clock 266MHz */ + tmp = DUMMY_ACCESS; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_start_dma +* Description : Enables DMA transfer on the information specified by the argument. +* : Set DMAC register by this function to enable DMA transfer. +* : After executing this function, USB module is set to start DMA +* : transfer. DMA transfer should not wait for DMA transfer complete. +* Arguments : USB_HOST_DMA_t *dma : DMA parameter +* : typedef struct{ +* : uint32_t fifo; FIFO for using +* : uint32_t buffer; Start address of transfer source/destination +* : uint32_t bytes; Transfer size(Byte) +* : uint32_t dir; Transfer direction(0:Buffer->FIFO, 1:FIFO->Buffer) +* : uint32_t size; DMA transfer size +* : } USB_HOST_DMA_t; +* : uint16_t dfacc ; 0 : cycle steal mode +* : 1 : 16byte continuous mode +* : 2 : 32byte continuous mode +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_start_dma (USB_HOST_DMA_t * dma, uint16_t dfacc) +{ + uint32_t trncount; + uint32_t src; + uint32_t dst; + uint32_t size; + uint32_t dir; +#ifdef CACHE_WRITEBACK + uint32_t ptr; +#endif + + trncount = dma->bytes; + dir = dma->dir; + + if (dir == USB_HOST_FIFO2BUF) + { + /* DxFIFO determination */ + dst = dma->buffer; +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB200.D1FIFO.UINT32); + } + size = dma->size; + + if (size == 0) + { + src += 3; /* byte access */ + } + else if (size == 1) + { + src += 2; /* short access */ + } + else + { + /* Do Nothing */ + } +#else + size = dma->size; + + if (size == 2) + { + /* 32bit access */ + if (dfacc == 2) + { + /* 32byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFOB0); + } + else + { + src = (uint32_t)(&USB200.D1FIFOB0); + } + } + else if (dfacc == 1) + { + /* 16byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFOB0); + } + else + { + src = (uint32_t)(&USB200.D1FIFOB0); + } + } + else + { + /* normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB200.D1FIFO.UINT32); + } + } + } + else if (size == 1) + { + /* 16bit access */ + dfacc = 0; /* force normal access */ + + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB200.D1FIFO.UINT32); + } + src += 2; /* short access */ + } + else + { + /* 8bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB200.D1FIFO.UINT32); + } + src += 3; /* byte access */ + } +#endif + } + else + { + /* DxFIFO determination */ + src = dma->buffer; +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB200.D1FIFO.UINT32); + } + size = dma->size; + + if (size == 0) + { + dst += 3; /* byte access */ + } + else if (size == 1) + { + dst += 2; /* short access */ + } + else + { + /* Do Nothing */ + } +#else + size = dma->size; + if (size == 2) + { + /* 32bit access */ + if (dfacc == 2) + { + /* 32byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFOB0); + } + else + { + dst = (uint32_t)(&USB200.D1FIFOB0); + } + } + else if (dfacc == 1) + { + /* 16byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFOB0); + } + else + { + dst = (uint32_t)(&USB200.D1FIFOB0); + } + } + else + { + /* normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB200.D1FIFO.UINT32); + } + } + } + else if (size == 1) + { + /* 16bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB200.D1FIFO.UINT32); + } + dst += 2; /* short access */ + } + else + { + /* 8bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB200.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB200.D1FIFO.UINT32); + } + dst += 3; /* byte access */ + } +#endif + } + +#ifdef CACHE_WRITEBACK + ptr = (uint32_t)dma->buffer; + if ((ptr & 0x20000000ul) == 0) + { + io_cwb((uint32_t)ptr,(uint32_t)(ptr)+trncount); + } +#endif + + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + usb0_host_enable_dmac0(src, dst, trncount, size, dir, dma->fifo, dfacc); + } + else + { + usb0_host_enable_dmac1(src, dst, trncount, size, dir, dma->fifo, dfacc); + } +} + +/******************************************************************************* +* Function Name: usb0_host_enable_dmac0 +* Description : Enables DMA transfer on the information specified by the argument. +* Arguments : uint32_t src : src address +* : uint32_t dst : dst address +* : uint32_t count : transfer byte +* : uint32_t size : transfer size +* : uint32_t dir : direction +* : uint32_t fifo : FIFO(D0FIFO or D1FIFO) +* : uint16_t dfacc : 0 : normal access +* : : 1 : 16byte access +* : : 2 : 32byte access +* Return Value : none +*******************************************************************************/ +static void usb0_host_enable_dmac0 (uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc) +{ + dmac_transinfo_t trans_info; + uint32_t request_factor = 0; + int32_t ret; + + /* ==== Variable setting for DMAC initialization ==== */ + trans_info.src_addr = (uint32_t)src; /* Start address of transfer source */ + trans_info.dst_addr = (uint32_t)dst; /* Start address of transfer destination */ + trans_info.count = (uint32_t)count; /* Total byte count to be transferred */ +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } +#else + if (dfacc == 2) + { + /* 32byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_256; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_256; /* Transfer destination transfer size */ + } + else if (dfacc == 1) + { + /* 16byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_128; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_128; /* Transfer destination transfer size */ + } + else + { + /* normal access */ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } + } +#endif + + if (dir == USB_HOST_FIFO2BUF) + { + request_factor = DMAC_REQ_USB0_DMA0_RX; /* USB_0 channel 0 receive FIFO full */ + trans_info.saddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer destination address */ + } + else if (dir == USB_HOST_BUF2FIFO) + { + request_factor = DMAC_REQ_USB0_DMA0_TX; /* USB_0 channel 0 receive FIFO empty */ + trans_info.saddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer destination address */ + } + else + { + /* Do Nothing */ + } + + /* ==== DMAC initialization ==== */ + usb0_host_DMAC1_PeriReqInit((const dmac_transinfo_t *)&trans_info, + DMAC_MODE_REGISTER, + DMAC_SAMPLE_SINGLE, + request_factor, + 0); /* Don't care DMAC_REQ_REQD is setting in usb0_host_DMAC1_PeriReqInit() */ + + /* ==== DMAC startup ==== */ + ret = usb0_host_DMAC1_Open(DMAC_REQ_MODE_PERI); + + if (ret != 0) + { +// printf("DMAC1 Open error!!\n"); + } + + return; +} + +/******************************************************************************* +* Function Name: usb0_host_enable_dmac1 +* Description : Enables DMA transfer on the information specified by the argument. +* Arguments : uint32_t src : src address +* : uint32_t dst : dst address +* : uint32_t count : transfer byte +* : uint32_t size : transfer size +* : uint32_t dir : direction +* : uint32_t fifo : FIFO(D0FIFO or D1FIFO) +* : uint16_t dfacc : 0 : normal access +* : : 1 : 16byte access +* : : 2 : 32byte access +* Return Value : none +*******************************************************************************/ +static void usb0_host_enable_dmac1 (uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc) +{ + dmac_transinfo_t trans_info; + uint32_t request_factor = 0; + int32_t ret; + + /* ==== Variable setting for DMAC initialization ==== */ + trans_info.src_addr = (uint32_t)src; /* Start address of transfer source */ + trans_info.dst_addr = (uint32_t)dst; /* Start address of transfer destination */ + trans_info.count = (uint32_t)count; /* Total byte count to be transferred */ +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } +#else + if (dfacc == 2) + { + /* 32byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_256; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_256; /* Transfer destination transfer size */ + } + else if (dfacc == 1) + { + /* 16byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_128; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_128; /* Transfer destination transfer size */ + } + else + { + /* normal access */ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } + } +#endif + + if (dir == USB_HOST_FIFO2BUF) + { + request_factor =DMAC_REQ_USB0_DMA1_RX; /* USB_0 channel 0 receive FIFO full */ + trans_info.saddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer destination address */ + } + else if (dir == USB_HOST_BUF2FIFO) + { + request_factor =DMAC_REQ_USB0_DMA1_TX; /* USB_0 channel 0 receive FIFO empty */ + trans_info.saddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer destination address */ + } + else + { + /* Do Nothing */ + } + + /* ==== DMAC initialization ==== */ + usb0_host_DMAC2_PeriReqInit((const dmac_transinfo_t *)&trans_info, + DMAC_MODE_REGISTER, + DMAC_SAMPLE_SINGLE, + request_factor, + 0); /* Don't care DMAC_REQ_REQD is setting in usb0_host_DMAC2_PeriReqInit() */ + + /* ==== DMAC startup ==== */ + ret = usb0_host_DMAC2_Open(DMAC_REQ_MODE_PERI); + + if (ret != 0) + { +// printf("DMAC2 Open error!!\n"); + } + + return; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_stop_dma0 +* Description : Disables DMA transfer. +* Arguments : none +* Return Value : uint32_t return Transfer Counter register(DMATCRn) value +* : regarding to the bus width. +* Notice : This function should be executed to DMAC executed at the time +* : of specification of D0_FIF0_DMA in dma->fifo. +*******************************************************************************/ +uint32_t Userdef_USB_usb0_host_stop_dma0 (void) +{ + uint32_t remain; + + /* ==== DMAC release ==== */ + usb0_host_DMAC1_Close(&remain); + + return remain; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_stop_dma1 +* Description : Disables DMA transfer. +* : This function should be executed to DMAC executed at the time +* : of specification of D1_FIF0_DMA in dma->fifo. +* Arguments : none +* Return Value : uint32_t return Transfer Counter register(DMATCRn) value +* : regarding to the bus width. +*******************************************************************************/ +uint32_t Userdef_USB_usb0_host_stop_dma1 (void) +{ + uint32_t remain; + + /* ==== DMAC release ==== */ + usb0_host_DMAC2_Close(&remain); + + return remain; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_notice +* Description : Notice of USER +* Arguments : const char *format +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_notice (const char * format) +{ +// printf(format); + + return; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb0_host_user_rdy +* Description : This function notify a user and wait for trigger +* Arguments : const char *format +* : uint16_t data +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb0_host_user_rdy (const char * format, uint16_t data) +{ +// printf(format, data); + getchar(); + + return; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/inc/usb1_host.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,156 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB1_HOST_H +#define USB1_HOST_H + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "devdrv_usb_host_api.h" +#include "usb_host.h" + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +extern const uint16_t g_usb1_host_bit_set[]; +extern uint32_t g_usb1_host_data_count[USB_HOST_MAX_PIPE_NO + 1]; +extern uint8_t *g_usb1_host_data_pointer[USB_HOST_MAX_PIPE_NO + 1]; + +extern uint16_t g_usb1_host_PipeIgnore[]; +extern uint16_t g_usb1_host_PipeTbl[]; +extern uint16_t g_usb1_host_pipe_status[]; +extern uint32_t g_usb1_host_PipeDataSize[]; + +extern USB_HOST_DMA_t g_usb1_host_DmaInfo[]; +extern uint16_t g_usb1_host_DmaPipe[]; +extern uint16_t g_usb1_host_DmaBval[]; +extern uint16_t g_usb1_host_DmaStatus[]; + +extern uint16_t g_usb1_host_driver_state; +extern uint16_t g_usb1_host_ConfigNum; +extern uint16_t g_usb1_host_CmdStage; +extern uint16_t g_usb1_host_bchg_flag; +extern uint16_t g_usb1_host_detach_flag; +extern uint16_t g_usb1_host_attach_flag; + +extern uint16_t g_usb1_host_UsbAddress; +extern uint16_t g_usb1_host_setUsbAddress; +extern uint16_t g_usb1_host_default_max_packet[USB_HOST_MAX_DEVICE + 1]; +extern uint16_t g_usb1_host_UsbDeviceSpeed; +extern uint16_t g_usb1_host_SupportUsbDeviceSpeed; + +extern uint16_t g_usb1_host_SavReq; +extern uint16_t g_usb1_host_SavVal; +extern uint16_t g_usb1_host_SavIndx; +extern uint16_t g_usb1_host_SavLen; + +extern uint16_t g_usb1_host_pipecfg[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb1_host_pipebuf[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb1_host_pipemaxp[USB_HOST_MAX_PIPE_NO + 1]; +extern uint16_t g_usb1_host_pipeperi[USB_HOST_MAX_PIPE_NO + 1]; + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +/* ==== common ==== */ +void usb1_host_dma_stop_d0(uint16_t pipe, uint32_t remain); +void usb1_host_dma_stop_d1(uint16_t pipe, uint32_t remain); +uint16_t usb1_host_is_hispeed(void); +uint16_t usb1_host_is_hispeed_enable(void); +uint16_t usb1_host_start_send_transfer(uint16_t pipe, uint32_t size, uint8_t *data); +uint16_t usb1_host_write_buffer(uint16_t pipe); +uint16_t usb1_host_write_buffer_c(uint16_t pipe); +uint16_t usb1_host_write_buffer_d0(uint16_t pipe); +uint16_t usb1_host_write_buffer_d1(uint16_t pipe); +void usb1_host_start_receive_transfer(uint16_t pipe, uint32_t size, uint8_t *data); +uint16_t usb1_host_read_buffer(uint16_t pipe); +uint16_t usb1_host_read_buffer_c(uint16_t pipe); +uint16_t usb1_host_read_buffer_d0(uint16_t pipe); +uint16_t usb1_host_read_buffer_d1(uint16_t pipe); +uint16_t usb1_host_change_fifo_port(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw); +void usb1_host_set_curpipe(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw); +void usb1_host_set_curpipe2(uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw, uint16_t dfacc); +uint16_t usb1_host_get_mbw(uint32_t trncount, uint32_t dtptr); +uint16_t usb1_host_read_dma(uint16_t pipe); +void usb1_host_stop_transfer(uint16_t pipe); +void usb1_host_brdy_int(uint16_t status, uint16_t int_enb); +void usb1_host_nrdy_int(uint16_t status, uint16_t int_enb); +void usb1_host_bemp_int(uint16_t status, uint16_t int_enb); +void usb1_host_setting_interrupt(uint8_t level); +void usb1_host_reset_module(uint16_t clockmode); +uint16_t usb1_host_get_buf_size(uint16_t pipe); +uint16_t usb1_host_get_mxps(uint16_t pipe); +void usb1_host_enable_brdy_int(uint16_t pipe); +void usb1_host_disable_brdy_int(uint16_t pipe); +void usb1_host_clear_brdy_sts(uint16_t pipe); +void usb1_host_enable_bemp_int(uint16_t pipe); +void usb1_host_disable_bemp_int(uint16_t pipe); +void usb1_host_clear_bemp_sts(uint16_t pipe); +void usb1_host_enable_nrdy_int(uint16_t pipe); +void usb1_host_disable_nrdy_int(uint16_t pipe); +void usb1_host_clear_nrdy_sts(uint16_t pipe); +void usb1_host_set_pid_buf(uint16_t pipe); +void usb1_host_set_pid_nak(uint16_t pipe); +void usb1_host_set_pid_stall(uint16_t pipe); +void usb1_host_clear_pid_stall(uint16_t pipe); +uint16_t usb1_host_get_pid(uint16_t pipe); +void usb1_host_set_sqclr(uint16_t pipe); +void usb1_host_set_sqset(uint16_t pipe); +void usb1_host_set_csclr(uint16_t pipe); +void usb1_host_aclrm(uint16_t pipe); +void usb1_host_set_aclrm(uint16_t pipe); +void usb1_host_clr_aclrm(uint16_t pipe); +uint16_t usb1_host_get_sqmon(uint16_t pipe); +uint16_t usb1_host_get_inbuf(uint16_t pipe); + +/* ==== host ==== */ +void usb1_host_init_pipe_status(void); +int32_t usb1_host_CtrlTransStart(uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len, uint8_t *Buf); +void usb1_host_SetupStage(uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len); +void usb1_host_CtrlReadStart(uint32_t Bsize, uint8_t *Table); +uint16_t usb1_host_CtrlWriteStart(uint32_t Bsize, uint8_t *Table); +void usb1_host_StatusStage(void); +void usb1_host_get_devadd(uint16_t addr, uint16_t *devadd); +void usb1_host_set_devadd(uint16_t addr, uint16_t *devadd); +void usb1_host_InitModule(void); +uint16_t usb1_host_CheckAttach(void); +void usb1_host_UsbDetach(void); +void usb1_host_UsbDetach2(void); +void usb1_host_UsbAttach(void); +uint16_t usb1_host_UsbBusReset(void); +int32_t usb1_host_UsbResume(void); +int32_t usb1_host_UsbSuspend(void); +void usb1_host_Enable_DetachINT(void); +void usb1_host_Disable_DetachINT(void); +void usb1_host_UsbStateManager(void); + + +#endif /* USB1_HOST_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/inc/usb1_host_api.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,112 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_api.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB1_HOST_API_H +#define USB1_HOST_API_H + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Variable Externs +*******************************************************************************/ + + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +void usb1_host_interrupt(uint32_t int_sense); +void usb1_host_dma_interrupt_d0fifo(uint32_t int_sense); +void usb1_host_dma_interrupt_d1fifo(uint32_t int_sense); + +uint16_t usb1_api_host_init(uint8_t int_level, uint16_t mode, uint16_t clockmode); +int32_t usb1_api_host_enumeration(uint16_t devadr); +int32_t usb1_api_host_detach(void); +int32_t usb1_api_host_data_in(uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t usb1_api_host_data_out(uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t *data_buf); +int32_t usb1_api_host_control_transfer(uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len, uint8_t *Buf); +int32_t usb1_api_host_set_endpoint(uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t *configdescriptor); +int32_t usb1_api_host_clear_endpoint(USB_HOST_CFG_PIPETBL_t *user_table); +int32_t usb1_api_host_clear_endpoint_pipe(uint16_t pipe_sel, USB_HOST_CFG_PIPETBL_t *user_table); +uint16_t usb1_api_host_SetEndpointTable(uint16_t devadr, USB_HOST_CFG_PIPETBL_t *user_table, uint8_t *Table); +int32_t usb1_api_host_data_count(uint16_t pipe, uint32_t *data_count); + +int32_t usb1_api_host_GetDeviceDescriptor(uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t usb1_api_host_GetConfigDescriptor(uint16_t devadr, uint16_t size, uint8_t *buf); +int32_t usb1_api_host_SetConfig(uint16_t devadr, uint16_t confignum); +int32_t usb1_api_host_SetInterface(uint16_t devadr, uint16_t interface_alt, uint16_t interface_index); +int32_t usb1_api_host_ClearStall(uint16_t devadr, uint16_t ep_dir); +uint16_t usb1_api_host_GetUsbDeviceState(void); + +void usb1_api_host_elt_4_4(void); +void usb1_api_host_elt_4_5(void); +void usb1_api_host_elt_4_6(void); +void usb1_api_host_elt_4_7(void); +void usb1_api_host_elt_4_8(void); +void usb1_api_host_elt_4_9(void); +void usb1_api_host_elt_get_desc(void); + +void usb1_host_EL_ModeInit(void); +void usb1_host_EL_SetUACT(void); +void usb1_host_EL_ClearUACT(void); +void usb1_host_EL_SetTESTMODE(uint16_t mode); +void usb1_host_EL_ClearNRDYSTS(uint16_t pipe); +uint16_t usb1_host_EL_GetINTSTS1(void); +void usb1_host_EL_UsbBusReset(void); +void usb1_host_EL_UsbAttach(void); +void usb1_host_EL_SetupStage(uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len); +void usb1_host_EL_StatusStage(void); +void usb1_host_EL_CtrlReadStart(uint32_t Bsize, uint8_t *Table); +int32_t usb1_host_EL_UsbSuspend(void); +int32_t usb1_host_EL_UsbResume(void); + +#if 0 /* prototype in devdrv_usb_host_api.h */ +uint16_t Userdef_USB_usb1_host_d0fifo_dmaintid(void); +uint16_t Userdef_USB_usb1_host_d1fifo_dmaintid(void); +void Userdef_USB_usb1_host_attach(void); +void Userdef_USB_usb1_host_detach(void); +void Userdef_USB_usb1_host_delay_1ms(void); +void Userdef_USB_usb1_host_delay_xms(uint32_t msec); +void Userdef_USB_usb1_host_delay_10us(uint32_t usec); +void Userdef_USB_usb1_host_delay_500ns(void); +void Userdef_USB_usb1_host_start_dma(USB_HOST_DMA_t *dma, uint16_t dfacc); +uint32_t Userdef_USB_usb1_host_stop_dma0(void); +uint32_t Userdef_USB_usb1_host_stop_dma1(void); +#endif + +#endif /* USB1_HOST_API_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/inc/usb1_host_dmacdrv.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,139 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_dmacdrv.h +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Description : RZ/A1H R7S72100 USB Sample Program +*******************************************************************************/ +#ifndef USB1_HOST_DMACDRV_H +#define USB1_HOST_DMACDRV_H + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ +typedef struct dmac_transinfo +{ + uint32_t src_addr; /* Transfer source address */ + uint32_t dst_addr; /* Transfer destination address */ + uint32_t count; /* Transfer byte count */ + uint32_t src_size; /* Transfer source data size */ + uint32_t dst_size; /* Transfer destination data size */ + uint32_t saddr_dir; /* Transfer source address direction */ + uint32_t daddr_dir; /* Transfer destination address direction */ +} dmac_transinfo_t; + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +/* ==== Transfer specification of the sample program ==== */ +#define DMAC_SAMPLE_SINGLE (0) /* Single transfer */ +#define DMAC_SAMPLE_CONTINUATION (1) /* Continuous transfer (use REN bit) */ + +/* ==== DMA modes ==== */ +#define DMAC_MODE_REGISTER (0) /* Register mode */ +#define DMAC_MODE_LINK (1) /* Link mode */ + +/* ==== Transfer requests ==== */ +#define DMAC_REQ_MODE_EXT (0) /* External request */ +#define DMAC_REQ_MODE_PERI (1) /* On-chip peripheral module request */ +#define DMAC_REQ_MODE_SOFT (2) /* Auto-request (request by software) */ + +/* ==== DMAC transfer sizes ==== */ +#define DMAC_TRANS_SIZE_8 (0) /* 8 bits */ +#define DMAC_TRANS_SIZE_16 (1) /* 16 bits */ +#define DMAC_TRANS_SIZE_32 (2) /* 32 bits */ +#define DMAC_TRANS_SIZE_64 (3) /* 64 bits */ +#define DMAC_TRANS_SIZE_128 (4) /* 128 bits */ +#define DMAC_TRANS_SIZE_256 (5) /* 256 bits */ +#define DMAC_TRANS_SIZE_512 (6) /* 512 bits */ +#define DMAC_TRANS_SIZE_1024 (7) /* 1024 bits */ + +/* ==== Address increment for transferring ==== */ +#define DMAC_TRANS_ADR_NO_INC (1) /* Not increment */ +#define DMAC_TRANS_ADR_INC (0) /* Increment */ + +/* ==== Method for detecting DMA request ==== */ +#define DMAC_REQ_DET_FALL (0) /* Falling edge detection */ +#define DMAC_REQ_DET_RISE (1) /* Rising edge detection */ +#define DMAC_REQ_DET_LOW (2) /* Low level detection */ +#define DMAC_REQ_DET_HIGH (3) /* High level detection */ + +/* ==== Request Direction ==== */ +#define DMAC_REQ_DIR_SRC (0) /* DMAREQ is the source/ DMAACK is active when reading */ +#define DMAC_REQ_DIR_DST (1) /* DMAREQ is the destination/ DMAACK is active when writing */ + +/* ==== Descriptors ==== */ +#define DMAC_DESC_HEADER (0) /* Header */ +#define DMAC_DESC_SRC_ADDR (1) /* Source Address */ +#define DMAC_DESC_DST_ADDR (2) /* Destination Address */ +#define DMAC_DESC_COUNT (3) /* Transaction Byte */ +#define DMAC_DESC_CHCFG (4) /* Channel Confg */ +#define DMAC_DESC_CHITVL (5) /* Channel Interval */ +#define DMAC_DESC_CHEXT (6) /* Channel Extension */ +#define DMAC_DESC_LINK_ADDR (7) /* Link Address */ + +/* ==== On-chip peripheral module requests ===== */ +typedef enum dmac_request_factor +{ + DMAC_REQ_USB0_DMA0_TX, /* USB_0 channel 0 transmit FIFO empty */ + DMAC_REQ_USB0_DMA0_RX, /* USB_0 channel 0 receive FIFO full */ + DMAC_REQ_USB0_DMA1_TX, /* USB_0 channel 1 transmit FIFO empty */ + DMAC_REQ_USB0_DMA1_RX, /* USB_0 channel 1 receive FIFO full */ + DMAC_REQ_USB1_DMA0_TX, /* USB_1 channel 0 transmit FIFO empty */ + DMAC_REQ_USB1_DMA0_RX, /* USB_1 channel 0 receive FIFO full */ + DMAC_REQ_USB1_DMA1_TX, /* USB_1 channel 1 transmit FIFO empty */ + DMAC_REQ_USB1_DMA1_RX, /* USB_1 channel 1 receive FIFO full */ +} dmac_request_factor_t; + + +/******************************************************************************* +Variable Externs +*******************************************************************************/ + + +/******************************************************************************* +Functions Prototypes +*******************************************************************************/ +void usb1_host_DMAC3_PeriReqInit(const dmac_transinfo_t *trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction); +int32_t usb1_host_DMAC3_Open(uint32_t req); +void usb1_host_DMAC3_Close(uint32_t *remain); +void usb1_host_DMAC3_Load_Set(uint32_t src_addr, uint32_t dst_addr, uint32_t count); + +void usb1_host_DMAC4_PeriReqInit(const dmac_transinfo_t *trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction); +int32_t usb1_host_DMAC4_Open(uint32_t req); +void usb1_host_DMAC4_Close(uint32_t *remain); +void usb1_host_DMAC4_Load_Set(uint32_t src_addr, uint32_t dst_addr, uint32_t count); + +#endif /* USB1_HOST_DMACDRV_H */ + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/src/common/usb1_host_dataio.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,2835 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_dataio.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +static uint16_t g_usb1_host_mbw[(USB_HOST_MAX_PIPE_NO + 1)]; + +static void usb1_host_start_receive_trns_c(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb1_host_start_receive_trns_d0(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb1_host_start_receive_trns_d1(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb1_host_start_receive_dma_d0(uint16_t pipe, uint32_t size, uint8_t *data); +static void usb1_host_start_receive_dma_d1(uint16_t pipe, uint32_t size, uint8_t *data); +static uint16_t usb1_host_read_dma_d0(uint16_t pipe); +static uint16_t usb1_host_read_dma_d1(uint16_t pipe); +static uint16_t usb1_host_write_dma_d0(uint16_t pipe); +static uint16_t usb1_host_write_dma_d1(uint16_t pipe); + +static void usb1_host_read_c_fifo(uint16_t pipe, uint16_t count); +static void usb1_host_write_c_fifo(uint16_t Pipe, uint16_t count); +static void usb1_host_read_d0_fifo(uint16_t pipe, uint16_t count); +static void usb1_host_write_d0_fifo(uint16_t pipe, uint16_t count); +static void usb1_host_read_d1_fifo(uint16_t pipe, uint16_t count); +static void usb1_host_write_d1_fifo(uint16_t pipe, uint16_t count); + +static void usb1_host_clear_transaction_counter(uint16_t pipe); +static void usb1_host_set_transaction_counter(uint16_t pipe, uint32_t count); + +static uint32_t usb1_host_com_get_dmasize(uint32_t trncount, uint32_t dtptr); + +static uint16_t usb1_host_set_dfacc_d0(uint16_t mbw, uint32_t count); +static uint16_t usb1_host_set_dfacc_d1(uint16_t mbw, uint32_t count); + + +/******************************************************************************* +* Function Name: usb1_host_start_send_transfer +* Description : Starts the USB data communication using pipe specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data data Address +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_start_send_transfer (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t status; + uint16_t usefifo; + uint16_t mbw; + + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + usb1_host_clear_bemp_sts(pipe); + usb1_host_clear_brdy_sts(pipe); + usb1_host_clear_nrdy_sts(pipe); + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + + usefifo = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + case USB_HOST_D0FIFO_DMA: + usefifo = USB_HOST_D0USE; + break; + + case USB_HOST_D1FIFO_USE: + case USB_HOST_D1FIFO_DMA: + usefifo = USB_HOST_D1USE; + break; + + default: + usefifo = USB_HOST_CUSE; + break; + }; + + usb1_host_set_curpipe(USB_HOST_PIPE0, usefifo, USB_HOST_NO, mbw); + + usb1_host_clear_transaction_counter(pipe); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + status = usb1_host_write_buffer(pipe); + + if (status != USB_HOST_FIFOERROR) + { + usb1_host_set_pid_buf(pipe); + } + + return status; +} + +/******************************************************************************* +* Function Name: usb1_host_write_buffer +* Description : Writes data in the buffer allocated in the pipe specified by +* : the argument. The FIFO for using is set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_write_buffer (uint16_t pipe) +{ + uint16_t status; + uint16_t usefifo; + + g_usb1_host_PipeIgnore[pipe] = 0; + usefifo = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + status = usb1_host_write_buffer_d0(pipe); + break; + + case USB_HOST_D1FIFO_USE: + status = usb1_host_write_buffer_d1(pipe); + break; + + case USB_HOST_D0FIFO_DMA: + status = usb1_host_write_dma_d0(pipe); + break; + + case USB_HOST_D1FIFO_DMA: + status = usb1_host_write_dma_d1(pipe); + break; + + default: + status = usb1_host_write_buffer_c(pipe); + break; + }; + + switch (status) + { + case USB_HOST_WRITING: /* Continue of data write */ + usb1_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + usb1_host_enable_brdy_int(pipe); /* Enable Ready Interrupt */ + break; + + case USB_HOST_WRITEEND: /* End of data write */ + case USB_HOST_WRITESHRT: /* End of data write */ + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + + usb1_host_clear_nrdy_sts(pipe); + usb1_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + + /* for last transfer */ + usb1_host_enable_bemp_int(pipe); /* Enable Empty Interrupt */ + break; + + case USB_HOST_WRITEDMA: /* DMA write */ + usb1_host_clear_nrdy_sts(pipe); + usb1_host_enable_nrdy_int(pipe); /* Error (NORES or STALL) */ + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + usb1_host_disable_bemp_int(pipe); /* Disable Empty Interrupt */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_write_buffer_c +* Description : Writes data in the buffer allocated in the pipe specified in +* : the argument. Writes data by CPU transfer using CFIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_write_buffer_c (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + + if (pipe == USB_HOST_PIPE0) + { + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_CFIFO_WRITE, mbw); + } + else + { + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_NO, mbw); + } + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb1_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb1_host_write_c_fifo(pipe, (uint16_t)count); + + if (g_usb1_host_data_count[pipe] < (uint32_t)size) + { + g_usb1_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB201.CFIFOCTR, + USB_CFIFOCTR_BVAL_SHIFT, + USB_CFIFOCTR_BVAL) == 0) + { + USB201.CFIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb1_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_write_buffer_d0 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by CPU transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_write_buffer_d0 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D0USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb1_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb1_host_write_d0_fifo(pipe, (uint16_t)count); + + if (g_usb1_host_data_count[pipe] < (uint32_t)size) + { + g_usb1_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB201.D0FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + USB201.D0FIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb1_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_write_buffer_d1 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by CPU transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND ; Write end +* : USB_HOST_WRITESHRT ; short data +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_WRITEDMA ; Write DMA +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_write_buffer_d1 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D1USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] <= (uint32_t)size) + { + status = USB_HOST_WRITEEND; /* write continues */ + count = g_usb1_host_data_count[pipe]; + + if (count == 0) + { + status = USB_HOST_WRITESHRT; /* Null Packet is end of write */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + } + else + { + status = USB_HOST_WRITING; /* write continues */ + count = (uint32_t)size; + } + + usb1_host_write_d1_fifo(pipe, (uint16_t)count); + + if (g_usb1_host_data_count[pipe] < (uint32_t)size) + { + g_usb1_host_data_count[pipe] = 0; + + if (RZA_IO_RegRead_16(&USB201.D1FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + USB201.D1FIFOCTR = USB_HOST_BITBVAL; /* Short Packet */ + } + } + else + { + g_usb1_host_data_count[pipe] -= count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_write_dma_d0 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by DMA transfer using D0FIFO. +* : The DMA-ch for using is specified by Userdef_USB_usb1_host_start_dma(). +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND : Write end +* : USB_HOST_WRITESHRT : short data +* : USB_HOST_WRITING : Continue of data write +* : USB_HOST_WRITEDMA : Write DMA +* : USB_HOST_FIFOERROR : FIFO status +*******************************************************************************/ +static uint16_t usb1_host_write_dma_d0 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + count = g_usb1_host_data_count[pipe]; + + if (count != 0) + { + g_usb1_host_DmaPipe[USB_HOST_D0FIFO] = pipe; + + if ((count % size) != 0) + { + g_usb1_host_DmaBval[USB_HOST_D0FIFO] = 1; + } + else + { + g_usb1_host_DmaBval[USB_HOST_D0FIFO] = 0; + } + + dfacc = usb1_host_set_dfacc_d0(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 0; /* 8bit transfer */ + } + + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].fifo = USB_HOST_D0FIFO_DMA; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].dir = USB_HOST_BUF2FIFO; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].buffer = (uint32_t)g_usb1_host_data_pointer[pipe]; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].bytes = count; + + Userdef_USB_usb1_host_start_dma(&g_usb1_host_DmaInfo[USB_HOST_D0FIFO], dfacc); + + usb1_host_set_curpipe2(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw, dfacc); + + RZA_IO_RegWrite_16(&USB201.D0FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + + g_usb1_host_data_count[pipe] = 0; + g_usb1_host_data_pointer[pipe] += count; + + status = USB_HOST_WRITEDMA; /* DMA write */ + } + else + { + if (RZA_IO_RegRead_16(&USB201.D0FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + RZA_IO_RegWrite_16(&USB201.D0FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); /* Short Packet */ + } + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_write_dma_d1 +* Description : Writes data in the buffer allocated in the pipe specified in the argument. +* : Writes data by DMA transfer using D1FIFO. +* : The DMA-ch for using is specified by Userdef_USB_usb1_host_start_dma(). +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_WRITEEND : Write end +* : USB_HOST_WRITESHRT : short data +* : USB_HOST_WRITING : Continue of data write +* : USB_HOST_WRITEDMA : Write DMA +* : USB_HOST_FIFOERROR : FIFO status +*******************************************************************************/ +static uint16_t usb1_host_write_dma_d1 (uint16_t pipe) +{ + uint32_t count; + uint16_t size; + uint16_t buffer; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + count = g_usb1_host_data_count[pipe]; + + if (count != 0) + { + g_usb1_host_DmaPipe[USB_HOST_D1FIFO] = pipe; + + if ((count % size) != 0) + { + g_usb1_host_DmaBval[USB_HOST_D1FIFO] = 1; + } + else + { + g_usb1_host_DmaBval[USB_HOST_D1FIFO] = 0; + } + + dfacc = usb1_host_set_dfacc_d1(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 0; /* 8bit transfer */ + } + + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].fifo = USB_HOST_D1FIFO_DMA; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].dir = USB_HOST_BUF2FIFO; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].buffer = (uint32_t)g_usb1_host_data_pointer[pipe]; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].bytes = count; + + Userdef_USB_usb1_host_start_dma(&g_usb1_host_DmaInfo[USB_HOST_D1FIFO], dfacc); + + usb1_host_set_curpipe2(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw , dfacc); + + RZA_IO_RegWrite_16(&USB201.D1FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + + g_usb1_host_data_count[pipe] = 0; + g_usb1_host_data_pointer[pipe] += count; + + status = USB_HOST_WRITEDMA; /* DMA write */ + } + else + { + if (RZA_IO_RegRead_16(&USB201.D1FIFOCTR, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL) == 0) + { + RZA_IO_RegWrite_16(&USB201.D1FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); /* Short Packet */ + } + status = USB_HOST_WRITESHRT; /* Short Packet is end of write */ + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_transfer +* Description : Starts USB data reception using the pipe specified in the argument. +* : The FIFO for using is set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +void usb1_host_start_receive_transfer (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t usefifo; + + usb1_host_clear_bemp_sts(pipe); + usb1_host_clear_brdy_sts(pipe); + usb1_host_clear_nrdy_sts(pipe); + + usefifo = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + usb1_host_start_receive_trns_d0(pipe, size, data); + break; + + case USB_HOST_D1FIFO_USE: + usb1_host_start_receive_trns_d1(pipe, size, data); + break; + + case USB_HOST_D0FIFO_DMA: + usb1_host_start_receive_dma_d0(pipe, size, data); + break; + + case USB_HOST_D1FIFO_DMA: + usb1_host_start_receive_dma_d1(pipe, size, data); + break; + + default: + usb1_host_start_receive_trns_c(pipe, size, data); + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_trns_c +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using CFIFO. +* : When storing data in the buffer allocated in the pipe specified in the +* : argument, BRDY interrupt is generated to read data +* : in the interrupt. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb1_host_start_receive_trns_c (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb1_host_set_pid_nak(pipe); + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_PipeIgnore[pipe] = 0; + + g_usb1_host_PipeDataSize[pipe] = size; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_CFIFO_READ, mbw); + USB201.CFIFOCTR = USB_HOST_BITBCLR; + + usb1_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + + usb1_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_trns_d0 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, BRDY interrupt is generated to read data in the +* : interrupt. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb1_host_start_receive_trns_d0 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb1_host_set_pid_nak(pipe); + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_PipeIgnore[pipe] = 0; + + g_usb1_host_PipeDataSize[pipe] = size; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, mbw); + + usb1_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + + usb1_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_trns_d1 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using D1FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, BRDY interrupt is generated to read data. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb1_host_start_receive_trns_d1 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb1_host_set_pid_nak(pipe); + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_PipeIgnore[pipe] = 0; + + g_usb1_host_PipeDataSize[pipe] = size; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, mbw); + + usb1_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + + usb1_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_dma_d0 +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by DMA transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, delivered read request to DMAC to read data from +* : the buffer by DMAC. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb1_host_start_receive_dma_d0 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb1_host_set_pid_nak(pipe); + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_PipeIgnore[pipe] = 0; + + g_usb1_host_PipeDataSize[pipe] = 0; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, mbw); + + usb1_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + usb1_host_read_dma(pipe); + + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + } + else + { + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + } + + usb1_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_start_receive_dma_d1 +* Description : Read data from the buffer allocated in the pipe specified in the argument. +* : Reads data by DMA transfer using D0FIFO. +* : This function does not read data from the buffer. +* : When storing data in the buffer allocated in the pipe specified +* : in the argument, delivered read request to DMAC to read data from +* : the buffer by DMAC. +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t size ; Data Size +* : uint8_t *data ; Data Address +* Return Value : none +*******************************************************************************/ +static void usb1_host_start_receive_dma_d1 (uint16_t pipe, uint32_t size, uint8_t * data) +{ + uint16_t mbw; + + usb1_host_set_pid_nak(pipe); + g_usb1_host_data_count[pipe] = size; + g_usb1_host_data_pointer[pipe] = (uint8_t *)data; + g_usb1_host_PipeIgnore[pipe] = 0; + + g_usb1_host_PipeDataSize[pipe] = 0; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_WAIT; + + mbw = usb1_host_get_mbw(size, (uint32_t)data); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, mbw); + + usb1_host_set_transaction_counter(pipe, size); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + usb1_host_read_dma(pipe); + + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + } + else + { + usb1_host_enable_nrdy_int(pipe); + usb1_host_enable_brdy_int(pipe); + } + + usb1_host_set_pid_buf(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_read_buffer +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Uses FIF0 set in the pipe definition table. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_read_buffer (uint16_t pipe) +{ + uint16_t status; + + g_usb1_host_PipeIgnore[pipe] = 0; + + if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_USE) + { + status = usb1_host_read_buffer_d0(pipe); + } + else if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_USE) + { + status = usb1_host_read_buffer_d1(pipe); + } + else + { + status = usb1_host_read_buffer_c(pipe); + } + + switch (status) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb1_host_disable_brdy_int(pipe); + g_usb1_host_PipeDataSize[pipe] -= g_usb1_host_data_count[pipe]; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + break; + + case USB_HOST_READOVER: /* buffer over */ + if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_USE) + { + USB201.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_USE) + { + USB201.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + USB201.CFIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#else + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; +#endif + g_usb1_host_PipeDataSize[pipe] -= g_usb1_host_data_count[pipe]; + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_buffer_c +* Description : Reads data from the buffer allocated in the pipe specified in the argument. +* : Reads data by CPU transfer using CFIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_read_buffer_c (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_CUSE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb1_host_data_count[pipe]; + } + else if (g_usb1_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + } + + if (count == 0) /* 0 length packet */ + { + USB201.CFIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb1_host_read_c_fifo(pipe, (uint16_t)count); + } + + g_usb1_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_buffer_d0 +* Description : Reads data from the buffer allocated in the pipe specified in +* : the argument. +* : Reads data by CPU transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_read_buffer_d0 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t pipebuf_size; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D0USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb1_host_data_count[pipe]; + } + else if (g_usb1_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + else + { + pipebuf_size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + } + } + + if (count == 0) /* 0 length packet */ + { + USB201.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb1_host_read_d0_fifo(pipe, (uint16_t)count); + } + + g_usb1_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_buffer_d1 +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by CPU transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_read_buffer_d1 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t pipebuf_size; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D1USE, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = g_usb1_host_data_count[pipe]; + } + else if (g_usb1_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + usb1_host_set_pid_nak(pipe); /* Set NAK */ + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) !=0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + else + { + pipebuf_size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + usb1_host_set_pid_nak(pipe); /* Set NAK */ + } + } + } + + if (count == 0) /* 0 length packet */ + { + USB201.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + } + else + { + usb1_host_read_d1_fifo(pipe, (uint16_t)count); + } + + g_usb1_host_data_count[pipe] -= count; + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_dma +* Description : Reads data from the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by DMA transfer using D0FIFO or D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +uint16_t usb1_host_read_dma (uint16_t pipe) +{ + uint16_t status; + + g_usb1_host_PipeIgnore[pipe] = 0; + + if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_DMA) + { + status = usb1_host_read_dma_d0(pipe); + } + else + { + status = usb1_host_read_dma_d1(pipe); + } + + switch (status) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READZERO: /* End of data read */ + usb1_host_disable_brdy_int(pipe); + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb1_host_disable_brdy_int(pipe); + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + g_usb1_host_PipeDataSize[pipe] -= g_usb1_host_data_count[pipe]; + } + break; + + case USB_HOST_READOVER: /* buffer over */ + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + g_usb1_host_PipeDataSize[pipe] -= g_usb1_host_data_count[pipe]; + } +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#else + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; +#endif + break; + + case USB_HOST_FIFOERROR: /* FIFO access status */ + default: + usb1_host_disable_brdy_int(pipe); /* Disable Ready Interrupt */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_ERROR; + break; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_dma_d0 +* Description : Writes data in the buffer allocated in the pipe specified +* : in the argument. +* : Reads data by DMA transfer using D0FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +static uint16_t usb1_host_read_dma_d0 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + uint16_t pipebuf_size; + + g_usb1_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_READY; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + count = g_usb1_host_data_count[pipe]; + status = USB_HOST_READING; + } + else + { + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + count = g_usb1_host_data_count[pipe]; + } + else if (g_usb1_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + else + { + pipebuf_size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + } + } + + if (count == 0) /* 0 length packet */ + { + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + USB201.D0FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + status = USB_HOST_READZERO; /* Null Packet receive */ + } + else + { + usb1_host_set_curpipe(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw); + /* transaction counter No set */ + /* FRDY = 1, DTLN = 0 -> BRDY */ + } + } + else + { + dfacc = usb1_host_set_dfacc_d0(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size = 0; /* 8bit transfer */ + } + + g_usb1_host_DmaPipe[USB_HOST_D0FIFO] = pipe; /* not use in read operation */ + g_usb1_host_DmaBval[USB_HOST_D0FIFO] = 0; /* not use in read operation */ + + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].fifo = USB_HOST_D0FIFO_DMA; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].dir = USB_HOST_FIFO2BUF; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].buffer = (uint32_t)g_usb1_host_data_pointer[pipe]; + g_usb1_host_DmaInfo[USB_HOST_D0FIFO].bytes = count; + + if (status == USB_HOST_READING) + { + g_usb1_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_BUSY; + } + else + { + g_usb1_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_BUSYEND; + } + + Userdef_USB_usb1_host_start_dma(&g_usb1_host_DmaInfo[USB_HOST_D0FIFO], dfacc); + + usb1_host_set_curpipe2(pipe, USB_HOST_D0DMA, USB_HOST_NO, mbw , dfacc); + + RZA_IO_RegWrite_16(&USB201.D0FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + g_usb1_host_data_count[pipe] -= count; + g_usb1_host_data_pointer[pipe] += count; + g_usb1_host_PipeDataSize[pipe] += count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_read_dma_d1 +* Description : Reads data from the buffer allocated in the pipe specified in +* : the argument. +* : Reads data by DMA transfer using D1FIFO. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : USB_HOST_READEND ; Read end +* : USB_HOST_READSHRT ; short data +* : USB_HOST_READZERO ; zero data +* : USB_HOST_READING ; Continue of data read +* : USB_HOST_READOVER ; buffer over +* : USB_HOST_FIFOERROR ; FIFO status +*******************************************************************************/ +static uint16_t usb1_host_read_dma_d1 (uint16_t pipe) +{ + uint32_t count; + uint32_t dtln; + uint16_t buffer; + uint16_t mxps; + uint16_t status; + uint16_t mbw; + uint16_t dfacc = 0; + uint16_t pipebuf_size; + + g_usb1_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_READY; + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[pipe], (uint32_t)g_usb1_host_data_pointer[pipe]); + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + count = g_usb1_host_data_count[pipe]; + status = USB_HOST_READING; + } + else + { + buffer = usb1_host_change_fifo_port(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + + if (buffer == USB_HOST_FIFOERROR) /* FIFO access status */ + { + return USB_HOST_FIFOERROR; + } + + dtln = (uint32_t)(buffer & USB_HOST_BITDTLN); + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if (g_usb1_host_data_count[pipe] < dtln) /* Buffer Over ? */ + { + status = USB_HOST_READOVER; + count = g_usb1_host_data_count[pipe]; + } + else if (g_usb1_host_data_count[pipe] == dtln) /* just Receive Size */ + { + status = USB_HOST_READEND; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + else /* continue Receive data */ + { + status = USB_HOST_READING; + count = dtln; + + if (count == 0) + { + status = USB_HOST_READSHRT; /* Null Packet receive */ + } + + if ((count % mxps) != 0) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + else + { + pipebuf_size = usb1_host_get_buf_size(pipe); /* Data buffer size */ + + if (count != pipebuf_size) + { + status = USB_HOST_READSHRT; /* Short Packet receive */ + } + } + } + } + + if (count == 0) /* 0 length packet */ + { + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + USB201.D1FIFOCTR = USB_HOST_BITBCLR; /* Clear BCLR */ + status = USB_HOST_READZERO; /* Null Packet receive */ + } + else + { + usb1_host_set_curpipe(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw); + /* transaction counter No set */ + /* FRDY = 1, DTLN = 0 -> BRDY */ + } + } + else + { + dfacc = usb1_host_set_dfacc_d1(mbw, count); + + if (mbw == USB_HOST_BITMBW_32) + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 2; /* 32bit transfer */ + } + else if (mbw == USB_HOST_BITMBW_16) + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 1; /* 16bit transfer */ + } + else + { + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size = 0; /* 8bit transfer */ + } + + g_usb1_host_DmaPipe[USB_HOST_D1FIFO] = pipe; /* not use in read operation */ + g_usb1_host_DmaBval[USB_HOST_D1FIFO] = 0; /* not use in read operation */ + + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].fifo = USB_HOST_D1FIFO_DMA; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].dir = USB_HOST_FIFO2BUF; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].buffer = (uint32_t)g_usb1_host_data_pointer[pipe]; + g_usb1_host_DmaInfo[USB_HOST_D1FIFO].bytes = count; + + if (status == USB_HOST_READING) + { + g_usb1_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_BUSY; + } + else + { + g_usb1_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_BUSYEND; + } + + Userdef_USB_usb1_host_start_dma(&g_usb1_host_DmaInfo[USB_HOST_D1FIFO], dfacc); + + usb1_host_set_curpipe2(pipe, USB_HOST_D1DMA, USB_HOST_NO, mbw , dfacc); + + RZA_IO_RegWrite_16(&USB201.D1FIFOSEL, + 1, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + g_usb1_host_data_count[pipe] -= count; + g_usb1_host_data_pointer[pipe] += count; + g_usb1_host_PipeDataSize[pipe] += count; + } + + return status; /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_change_fifo_port +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument. After allocating FIF0, waits in the software +* : till the corresponding pipe becomes ready. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* Return Value : USB_HOST_FIFOERROR ; Error +* : Others ; CFIFOCTR/D0FIFOCTR/D1FIFOCTR Register Value +*******************************************************************************/ +uint16_t usb1_host_change_fifo_port (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw) +{ + uint16_t buffer; + uint32_t loop; + volatile uint32_t loop2; + + usb1_host_set_curpipe(pipe, fifosel, isel, mbw); + + for (loop = 0; loop < 4; loop++) + { + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB201.CFIFOCTR; + break; + + case USB_HOST_D0USE: + case USB_HOST_D0DMA: + buffer = USB201.D0FIFOCTR; + break; + + case USB_HOST_D1USE: + case USB_HOST_D1DMA: + buffer = USB201.D1FIFOCTR; + break; + + default: + buffer = 0; + break; + } + + if ((buffer & USB_HOST_BITFRDY) == USB_HOST_BITFRDY) + { + return buffer; + } + + loop2 = 25; + + while (loop2-- > 0) + { + /* wait */ + } + } + + return USB_HOST_FIFOERROR; +} + +/******************************************************************************* +* Function Name: usb1_host_set_curpipe +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* Return Value : none +*******************************************************************************/ +void usb1_host_set_curpipe (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw) +{ + uint16_t buffer; + uint32_t loop; + volatile uint32_t loop2; + + g_usb1_host_mbw[pipe] = mbw; + + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB201.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(~isel & USB_HOST_BITISEL); + USB201.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(isel | pipe | mbw); + USB201.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D0DMA: + case USB_HOST_D0USE: + buffer = USB201.D0FIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + USB201.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB201.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D1DMA: + case USB_HOST_D1USE: + buffer = USB201.D1FIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + USB201.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB201.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + default: + break; + } + + /* Cautions !!! + * Depending on the external bus speed of CPU, you may need to wait for 450ns here. + * For details, please look at the data sheet. */ + loop2 = 100; + + while (loop2-- > 0) + { + /* wait */ + } +} + +/******************************************************************************* +* Function Name: usb1_host_set_curpipe2 +* Description : Allocates FIF0 specified by the argument in the pipe assigned +* : by the argument.(DFACC) +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t fifosel ; Select FIFO +* : uint16_t isel ; FIFO Access Direction +* : uint16_t mbw ; FIFO Port Access Bit Width +* : uint16_t dfacc ; DFACC Access mode +* Return Value : none +*******************************************************************************/ +void usb1_host_set_curpipe2 (uint16_t pipe, uint16_t fifosel, uint16_t isel, uint16_t mbw, uint16_t dfacc) +{ + uint16_t buffer; + uint32_t loop; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + uint32_t dummy; +#endif + volatile uint32_t loop2; + + g_usb1_host_mbw[pipe] = mbw; + + switch (fifosel) + { + case USB_HOST_CUSE: + buffer = USB201.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(~isel & USB_HOST_BITISEL); + USB201.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + + buffer &= (uint16_t)~(USB_HOST_BITISEL | USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(isel | pipe | mbw); + USB201.CFIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.CFIFOSEL & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE)) + == (buffer & (USB_HOST_BITISEL | USB_HOST_BITCURPIPE))) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D0DMA: + case USB_HOST_D0USE: + buffer = USB201.D0FIFOSEL; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + + if (dfacc != 0) + { + buffer |= (uint16_t)(USB_HOST_BITMBW_32); + } +#else + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); +#endif + USB201.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + +#ifdef __USB_HOST_DF_ACC_ENABLE__ + if (dfacc != 0) + { + dummy = USB201.D0FIFO.UINT32; + } +#endif + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB201.D0FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D0FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + case USB_HOST_D1DMA: + case USB_HOST_D1USE: + buffer = USB201.D1FIFOSEL; +#ifdef __USB_HOST_DF_ACC_ENABLE__ + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + + if (dfacc != 0) + { + buffer |= (uint16_t)(USB_HOST_BITMBW_32); + } +#else + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); +#endif + USB201.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + +#ifdef __USB_HOST_DF_ACC_ENABLE__ + if (dfacc != 0) + { + dummy = USB201.D1FIFO.UINT32; + loop = dummy; // avoid warning. + } +#endif + + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE | USB_HOST_BITMBW); + buffer |= (uint16_t)(pipe | mbw); + USB201.D1FIFOSEL = buffer; + + for (loop = 0; loop < 4; loop++) + { + if ((USB201.D1FIFOSEL & USB_HOST_BITCURPIPE) == (buffer & USB_HOST_BITCURPIPE)) + { + break; + } + + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } + } + break; + + default: + break; + } + + /* Cautions !!! + * Depending on the external bus speed of CPU, you may need to wait for 450ns here. + * For details, please look at the data sheet. */ + loop2 = 100; + while (loop2-- > 0) + { + /* wait */ + } +} + +/******************************************************************************* +* Function Name: usb1_host_write_c_fifo +* Description : Writes data in CFIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_write_c_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB201.CFIFO.UINT8[HH] = *g_usb1_host_data_pointer[pipe]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB201.CFIFO.UINT16[H] = *((uint16_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB201.CFIFO.UINT32 = *((uint32_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_read_c_fifo +* Description : Reads data from CFIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_read_c_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb1_host_data_pointer[pipe] = USB201.CFIFO.UINT8[HH]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb1_host_data_pointer[pipe]) = USB201.CFIFO.UINT16[H]; + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb1_host_data_pointer[pipe]) = USB201.CFIFO.UINT32; + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_write_d0_fifo +* Description : Writes data in D0FIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating CFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_write_d0_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB201.D0FIFO.UINT8[HH] = *g_usb1_host_data_pointer[pipe]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB201.D0FIFO.UINT16[H] = *((uint16_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB201.D0FIFO.UINT32 = *((uint32_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_read_d0_fifo +* Description : Reads data from D0FIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating DOFIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb0_host_mbw[]. +* Arguments : uint16_t Pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_read_d0_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb1_host_data_pointer[pipe] = USB201.D0FIFO.UINT8[HH]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb1_host_data_pointer[pipe]) = USB201.D0FIFO.UINT16[H]; + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb1_host_data_pointer[pipe]) = USB201.D0FIFO.UINT32; + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_write_d1_fifo +* Description : Writes data in D1FIFO. +* : Writes data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating D1FIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_write_d1_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + USB201.D1FIFO.UINT8[HH] = *g_usb1_host_data_pointer[pipe]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)(count / 2); even; --even) + { + USB201.D1FIFO.UINT16[H] = *((uint16_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)(count / 4); even; --even) + { + USB201.D1FIFO.UINT32 = *((uint32_t *)g_usb1_host_data_pointer[pipe]); + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_read_d1_fifo +* Description : Reads data from D1FIFO. +* : Reads data by BYTE/WORD/LONG according to access size +* : to the pipe specified by the arguments. +* : Before executing this function, allocating D1FIF0 in the specified pipe +* : should be completed. +* : Before executing this function, access size to the specified pipe +* : should be fixed and set in g_usb1_host_mbw[]. +* Arguments : uint16_t pipe ; Pipe Number +* : uint16_t count ; Data Size(Byte) +* Return Value : none +*******************************************************************************/ +static void usb1_host_read_d1_fifo (uint16_t pipe, uint16_t count) +{ + uint16_t even; + + if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_8) + { + for (even = count; even; --even) + { + *g_usb1_host_data_pointer[pipe] = USB201.D1FIFO.UINT8[HH]; + g_usb1_host_data_pointer[pipe] += 1; + } + } + else if (g_usb1_host_mbw[pipe] == USB_HOST_BITMBW_16) + { + for (even = (uint16_t)((count + 1) / 2); even; --even) + { + *((uint16_t *)g_usb1_host_data_pointer[pipe]) = USB201.D1FIFO.UINT16[H]; + g_usb1_host_data_pointer[pipe] += 2; + } + } + else + { + for (even = (uint16_t)((count + 3) / 4); even; --even) + { + *((uint32_t *)g_usb1_host_data_pointer[pipe]) = USB201.D1FIFO.UINT32; + g_usb1_host_data_pointer[pipe] += 4; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_com_get_dmasize +* Description : Calculates access width of DMA transfer by the argument to + return as the Return Value. +* Arguments : uint32_t trncount : transfer byte +* : uint32_t dtptr : transfer data pointer +* Return Value : DMA transfer size : 0 8bit +* : : 1 16bit +* : : 2 32bit +*******************************************************************************/ +static uint32_t usb1_host_com_get_dmasize (uint32_t trncount, uint32_t dtptr) +{ + uint32_t size; + + if (((trncount & 0x0001) != 0) || ((dtptr & 0x00000001) != 0)) + { + /* When transfer byte count is odd */ + /* or transfer data area is 8-bit alignment */ + size = 0; /* 8bit */ + } + else if (((trncount & 0x0003) != 0) || ((dtptr & 0x00000003) != 0)) + { + /* When the transfer byte count is multiples of 2 */ + /* or the transfer data area is 16-bit alignment */ + size = 1; /* 16bit */ + } + else + { + /* When the transfer byte count is multiples of 4 */ + /* or the transfer data area is 32-bit alignment */ + size = 2; /* 32bit */ + } + + return size; +} + +/******************************************************************************* +* Function Name: usb1_host_get_mbw +* Description : Calculates access width of DMA to return the value set in MBW. +* Arguments : uint32_t trncount : transfer byte +* : uint32_t dtptr : transfer data pointer +* Return Value : FIFO transfer size : USB_HOST_BITMBW_8 8bit +* : : USB_HOST_BITMBW_16 16bit +* : : USB_HOST_BITMBW_32 32bit +*******************************************************************************/ +uint16_t usb1_host_get_mbw (uint32_t trncount, uint32_t dtptr) +{ + uint32_t size; + uint16_t mbw; + + size = usb1_host_com_get_dmasize(trncount, dtptr); + + if (size == 0) + { + /* 8bit */ + mbw = USB_HOST_BITMBW_8; + } + else if (size == 1) + { + /* 16bit */ + mbw = USB_HOST_BITMBW_16; + } + else + { + /* 32bit */ + mbw = USB_HOST_BITMBW_32; + } + + return mbw; +} + +/******************************************************************************* +* Function Name: usb1_host_set_transaction_counter +* Description : Sets transaction counter by the argument(PIPEnTRN). +* : Clears transaction before setting to enable transaction counter setting. +* Arguments : uint16_t pipe ; Pipe number +* : uint32_t bsize : Data transfer size +* Return Value : none +*******************************************************************************/ +static void usb1_host_set_transaction_counter (uint16_t pipe, uint32_t bsize) +{ + uint16_t mxps; + uint16_t cnt; + + if (bsize == 0) + { + return; + } + + mxps = usb1_host_get_mxps(pipe); /* Max Packet Size */ + + if ((bsize % mxps) == 0) + { + cnt = (uint16_t)(bsize / mxps); + } + else + { + cnt = (uint16_t)((bsize / mxps) + 1); + } + + switch (pipe) + { + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE1TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE1TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE2TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE2TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE3TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE3TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE4TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE4TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE5TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE5TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + USB201.PIPE9TRN = cnt; + RZA_IO_RegWrite_16(&USB201.PIPE9TRE, + 1, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_clear_transaction_counter +* Description : Clears the transaction counter by the argument. +* : After executing this function, the transaction counter is invalid. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb1_host_clear_transaction_counter (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE1TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE2TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE3TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE4TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE5TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9TRE, + 0, + USB_PIPEnTRE_TRENB_SHIFT, + USB_PIPEnTRE_TRENB); + RZA_IO_RegWrite_16(&USB201.PIPE9TRE, + 1, + USB_PIPEnTRE_TRCLR_SHIFT, + USB_PIPEnTRE_TRCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_stop_transfer +* Description : Stops the USB transfer in the pipe specified by the argument. +* : After stopping the USB transfer, clears the buffer allocated in +* : the pipe. +* : After executing this function, allocation in FIF0 becomes USB_HOST_PIPE0; +* : invalid. After executing this function, BRDY/NRDY/BEMP interrupt +* : in the corresponding pipe becomes invalid. Sequence bit is also +* : cleared. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_stop_transfer (uint16_t pipe) +{ + uint16_t usefifo; + uint32_t remain; + + usb1_host_set_pid_nak(pipe); + + usefifo = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + switch (usefifo) + { + case USB_HOST_D0FIFO_USE: + usb1_host_clear_transaction_counter(pipe); + USB201.D0FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D1FIFO_USE: + usb1_host_clear_transaction_counter(pipe); + USB201.D1FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D0FIFO_DMA: + remain = Userdef_USB_usb1_host_stop_dma0(); + usb1_host_dma_stop_d0(pipe, remain); + usb1_host_clear_transaction_counter(pipe); + USB201.D0FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + case USB_HOST_D1FIFO_DMA: + remain = Userdef_USB_usb1_host_stop_dma1(); + usb1_host_dma_stop_d1(pipe, remain); + usb1_host_clear_transaction_counter(pipe); + USB201.D1FIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + + default: + usb1_host_clear_transaction_counter(pipe); + USB201.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + break; + } + + /* Interrupt of pipe set is disabled */ + usb1_host_disable_brdy_int(pipe); + usb1_host_disable_nrdy_int(pipe); + usb1_host_disable_bemp_int(pipe); + +#if(1) /* ohci_wrapp */ +#else + usb1_host_aclrm(pipe); +#endif + usb1_host_set_csclr(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_set_dfacc_d0 +* Description : Sets the DFACC setting value in D0FIFO using the transfer size. +* Arguments : uint16_t mbw ; MBW +* : uint16_t count ; data count +* Return Value : DFACC Access mode +*******************************************************************************/ +static uint16_t usb1_host_set_dfacc_d0 (uint16_t mbw, uint32_t count) +{ + uint16_t dfacc = 0; + +#ifndef __USB_HOST_DF_ACC_ENABLE__ + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; +#else + if (mbw == USB_HOST_BITMBW_32) + { + if ((count % 32) == 0) + { + /* 32byte transfer */ + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 2, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 2; + } + else if ((count % 16) == 0) + { + /* 16byte transfer */ + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 1, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 1; + } + else + { + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + } + else if (mbw == USB_HOST_BITMBW_16) + { + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + else + { + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D0FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } +#endif + + return dfacc; +} + +/******************************************************************************* +* Function Name: usb1_host_set_dfacc_d1 +* Description : Sets the DFACC setting value in D0FIFO using the transfer size. +* Arguments : uint16_t mbw ; MBW +* : uint16_t count ; data count +* Return Value : DFACC Access mode +*******************************************************************************/ +static uint16_t usb1_host_set_dfacc_d1 (uint16_t mbw, uint32_t count) +{ + uint16_t dfacc = 0; + +#ifndef __USB_HOST_DF_ACC_ENABLE__ + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; +#else + if (mbw == USB_HOST_BITMBW_32) + { + if ((count % 32) == 0) + { + /* 32byte transfer */ + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 2, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 2; + } + else if ((count % 16) == 0) + { + /* 16byte transfer */ + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 1, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 1; + } + else + { + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + } + else if (mbw == USB_HOST_BITMBW_16) + { + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } + else + { + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + RZA_IO_RegWrite_16(&USB201.D1FBCFG, + 0, + USB_DnFBCFG_TENDE_SHIFT, + USB_DnFBCFG_TENDE); + dfacc = 0; + } +#endif + + return dfacc; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/src/common/usb1_host_dma.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,355 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_dma.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +/* #include "usb1_host_dmacdrv.h" */ + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +static void usb1_host_dmaint(uint16_t fifo); +static void usb1_host_dmaint_buf2fifo(uint16_t pipe); +static void usb1_host_dmaint_fifo2buf(uint16_t pipe); + + +/******************************************************************************* +* Function Name: usb1_host_dma_stop_d0 +* Description : D0FIFO DMA stop +* Arguments : uint16_t pipe : pipe number +* : uint32_t remain : transfer byte +* Return Value : none +*******************************************************************************/ +void usb1_host_dma_stop_d0 (uint16_t pipe, uint32_t remain) +{ + uint16_t dtln; + uint16_t dfacc; + uint16_t buffer; + uint16_t sds_b = 1; + + dfacc = RZA_IO_RegRead_16(&USB201.D0FBCFG, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + if (dfacc == 2) + { + sds_b = 32; + } + else if (dfacc == 1) + { + sds_b = 16; + } + else + { + if (g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size == 2) + { + sds_b = 4; + } + else if (g_usb1_host_DmaInfo[USB_HOST_D0FIFO].size == 1) + { + sds_b = 2; + } + else + { + sds_b = 1; + } + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + if (g_usb1_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + buffer = USB201.D0FIFOCTR; + dtln = (buffer & USB_HOST_BITDTLN); + + if ((dtln % sds_b) != 0) + { + remain += (sds_b - (dtln % sds_b)); + } + g_usb1_host_PipeDataSize[pipe] = (g_usb1_host_data_count[pipe] - remain); + g_usb1_host_data_count[pipe] = remain; + } + } + + RZA_IO_RegWrite_16(&USB201.D0FIFOSEL, + 0, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); +} + +/******************************************************************************* +* Function Name: usb1_host_dma_stop_d1 +* Description : D1FIFO DMA stop +* Arguments : uint16_t pipe : pipe number +* : uint32_t remain : transfer byte +* Return Value : none +*******************************************************************************/ +void usb1_host_dma_stop_d1 (uint16_t pipe, uint32_t remain) +{ + uint16_t dtln; + uint16_t dfacc; + uint16_t buffer; + uint16_t sds_b = 1; + + dfacc = RZA_IO_RegRead_16(&USB201.D1FBCFG, + USB_DnFBCFG_DFACC_SHIFT, + USB_DnFBCFG_DFACC); + if (dfacc == 2) + { + sds_b = 32; + } + else if (dfacc == 1) + { + sds_b = 16; + } + else + { + if (g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size == 2) + { + sds_b = 4; + } + else if (g_usb1_host_DmaInfo[USB_HOST_D1FIFO].size == 1) + { + sds_b = 2; + } + else + { + sds_b = 1; + } + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 1) + { + if (g_usb1_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + buffer = USB201.D1FIFOCTR; + dtln = (buffer & USB_HOST_BITDTLN); + + if ((dtln % sds_b) != 0) + { + remain += (sds_b - (dtln % sds_b)); + } + g_usb1_host_PipeDataSize[pipe] = (g_usb1_host_data_count[pipe] - remain); + g_usb1_host_data_count[pipe] = remain; + } + } + + RZA_IO_RegWrite_16(&USB201.D1FIFOSEL, + 0, + USB_DnFIFOSEL_DREQE_SHIFT, + USB_DnFIFOSEL_DREQE); +} + +/******************************************************************************* +* Function Name: usb1_host_dma_interrupt_d0fifo +* Description : This function is DMA interrupt handler entry. +* : Execute usb1_host_dmaint() after disabling DMA interrupt in this function. +* : Disable DMA interrupt to DMAC executed when USB_HOST_D0FIFO_DMA is +* : specified by dma->fifo. +* : Register this function as DMA complete interrupt. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb1_host_dma_interrupt_d0fifo (uint32_t int_sense) +{ + usb1_host_dmaint(USB_HOST_D0FIFO); + g_usb1_host_DmaStatus[USB_HOST_D0FIFO] = USB_HOST_DMA_READY; +} + +/******************************************************************************* +* Function Name: usb1_host_dma_interrupt_d1fifo +* Description : This function is DMA interrupt handler entry. +* : Execute usb0_host_dmaint() after disabling DMA interrupt in this function. +* : Disable DMA interrupt to DMAC executed when USB_HOST_D1FIFO_DMA is +* : specified by dma->fifo. +* : Register this function as DMA complete interrupt. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb1_host_dma_interrupt_d1fifo (uint32_t int_sense) +{ + usb1_host_dmaint(USB_HOST_D1FIFO); + g_usb1_host_DmaStatus[USB_HOST_D1FIFO] = USB_HOST_DMA_READY; +} + +/******************************************************************************* +* Function Name: usb1_host_dmaint +* Description : This function is DMA transfer end interrupt +* Arguments : uint16_t fifo ; fifo number +* : ; USB_HOST_D0FIFO +* : ; USB_HOST_D1FIFO +* Return Value : none +*******************************************************************************/ +static void usb1_host_dmaint (uint16_t fifo) +{ + uint16_t pipe; + + pipe = g_usb1_host_DmaPipe[fifo]; + + if (g_usb1_host_DmaInfo[fifo].dir == USB_HOST_BUF2FIFO) + { + usb1_host_dmaint_buf2fifo(pipe); + } + else + { + usb1_host_dmaint_fifo2buf(pipe); + } +} + +/******************************************************************************* +* Function Name: usb1_host_dmaint_fifo2buf +* Description : Executes read completion from FIFO by DMAC. +* Arguments : uint16_t pipe : pipe number +* Return Value : none +*******************************************************************************/ +static void usb1_host_dmaint_fifo2buf (uint16_t pipe) +{ + uint32_t remain; + uint16_t useport; + + if (g_usb1_host_pipe_status[pipe] != USB_HOST_PIPE_DONE) + { + useport = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + if (useport == USB_HOST_D0FIFO_DMA) + { + remain = Userdef_USB_usb1_host_stop_dma0(); + usb1_host_dma_stop_d0(pipe, remain); + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + if (g_usb1_host_DmaStatus[USB_HOST_D0FIFO] == USB_HOST_DMA_BUSYEND) + { + USB201.D0FIFOCTR = USB_HOST_BITBCLR; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + else + { + usb1_host_enable_brdy_int(pipe); + } + } + } + else + { + remain = Userdef_USB_usb1_host_stop_dma1(); + usb1_host_dma_stop_d1(pipe, remain); + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + if (g_usb1_host_DmaStatus[USB_HOST_D1FIFO] == USB_HOST_DMA_BUSYEND) + { + USB201.D1FIFOCTR = USB_HOST_BITBCLR; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + else + { + usb1_host_enable_brdy_int(pipe); + } + } + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_dmaint_buf2fifo +* Description : Executes write completion in FIFO by DMAC. +* Arguments : uint16_t pipe : pipe number +* Return Value : none +*******************************************************************************/ +static void usb1_host_dmaint_buf2fifo (uint16_t pipe) +{ + uint16_t useport; + uint32_t remain; + + useport = (uint16_t)(g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE); + + if (useport == USB_HOST_D0FIFO_DMA) + { + remain = Userdef_USB_usb1_host_stop_dma0(); + usb1_host_dma_stop_d0(pipe, remain); + + if (g_usb1_host_DmaBval[USB_HOST_D0FIFO] != 0) + { + RZA_IO_RegWrite_16(&USB201.D0FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); + } + } + else + { + remain = Userdef_USB_usb1_host_stop_dma1(); + usb1_host_dma_stop_d1(pipe, remain); + + if (g_usb1_host_DmaBval[USB_HOST_D1FIFO] != 0) + { + RZA_IO_RegWrite_16(&USB201.D1FIFOCTR, + 1, + USB_DnFIFOCTR_BVAL_SHIFT, + USB_DnFIFOCTR_BVAL); + } + } + + usb1_host_enable_bemp_int(pipe); +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/src/common/usb1_host_intrn.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,285 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_intrn.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#if(1) /* ohci_wrapp */ +#include "ohci_wrapp_RZ_A1_local.h" +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_brdy_int +* Description : Executes BRDY interrupt(USB_HOST_PIPE1-9). +* : According to the pipe that interrupt is generated in, +* : reads/writes buffer allocated in the pipe. +* : This function is executed in the BRDY interrupt handler. +* : This function clears BRDY interrupt status and BEMP interrupt +* : status. +* Arguments : uint16_t status ; BRDYSTS Register Value +* : uint16_t int_enb ; BRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_brdy_int (uint16_t status, uint16_t int_enb) +{ + uint32_t int_sense = 0; + uint16_t pipe; + uint16_t pipebit; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + pipebit = g_usb1_host_bit_set[pipe]; + + if ((status & pipebit) && (int_enb & pipebit)) + { + USB201.BRDYSTS = (uint16_t)~pipebit; + USB201.BEMPSTS = (uint16_t)~pipebit; + + if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D0FIFO_DMA) + { + if (g_usb1_host_DmaStatus[USB_HOST_D0FIFO] != USB_HOST_DMA_READY) + { + usb1_host_dma_interrupt_d0fifo(int_sense); + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + usb1_host_read_dma(pipe); + usb1_host_disable_brdy_int(pipe); + } + else + { + USB201.D0FIFOCTR = USB_HOST_BITBCLR; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + } + else if ((g_usb1_host_PipeTbl[pipe] & USB_HOST_FIFO_USE) == USB_HOST_D1FIFO_DMA) + { + if (g_usb1_host_DmaStatus[USB_HOST_D1FIFO] != USB_HOST_DMA_READY) + { + usb1_host_dma_interrupt_d1fifo(int_sense); + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_BFRE_SHIFT, USB_PIPECFG_BFRE) == 0) + { + usb1_host_read_dma(pipe); + usb1_host_disable_brdy_int(pipe); + } + else + { + USB201.D1FIFOCTR = USB_HOST_BITBCLR; + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; + } + } + else + { + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 0) + { + usb1_host_read_buffer(pipe); + } + else + { + usb1_host_write_buffer(pipe); + } + } +#if(1) /* ohci_wrapp */ + switch (g_usb1_host_pipe_status[pipe]) + { + case USB_HOST_PIPE_DONE: + ohciwrapp_loc_TransEnd(pipe, TD_CC_NOERROR); + break; + case USB_HOST_PIPE_NORES: + case USB_HOST_PIPE_STALL: + case USB_HOST_PIPE_ERROR: + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); + break; + default: + /* Do Nothing */ + break; + } +#endif + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_nrdy_int +* Description : Executes NRDY interrupt(USB_HOST_PIPE1-9). +* : Checks NRDY interrupt cause by PID. When the cause if STALL, +* : regards the pipe state as STALL and ends the processing. +* : Then the cause is not STALL, increments the error count to +* : communicate again. When the error count is 3, determines +* : the pipe state as USB_HOST_PIPE_NORES and ends the processing. +* : This function is executed in the NRDY interrupt handler. +* : This function clears NRDY interrupt status. +* Arguments : uint16_t status ; NRDYSTS Register Value +* : uint16_t int_enb ; NRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_nrdy_int (uint16_t status, uint16_t int_enb) +{ + uint16_t pid; + uint16_t pipe; + uint16_t bitcheck; + + bitcheck = (uint16_t)(status & int_enb); + + USB201.NRDYSTS = (uint16_t)~status; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + if ((bitcheck&g_usb1_host_bit_set[pipe]) == g_usb1_host_bit_set[pipe]) + { + if (RZA_IO_RegRead_16(&USB201.SYSCFG0, + USB_SYSCFG_DCFM_SHIFT, + USB_SYSCFG_DCFM) == 1) + { + if (g_usb1_host_pipe_status[pipe] == USB_HOST_PIPE_WAIT) + { + pid = usb1_host_get_pid(pipe); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_STALL; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); +#endif + } + else + { +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_NORES; + ohciwrapp_loc_TransEnd(pipe, TD_CC_DEVICENOTRESPONDING); +#else + g_usb1_host_PipeIgnore[pipe]++; + + if (g_usb1_host_PipeIgnore[pipe] == 3) + { + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_NORES; + } + else + { + usb1_host_set_pid_buf(pipe); + } +#endif + } + } + } + else + { + /* USB Function */ + } + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_bemp_int +* Description : Executes BEMP interrupt(USB_HOST_PIPE1-9). +* Arguments : uint16_t status ; BEMPSTS Register Value +* : uint16_t int_enb ; BEMPENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_bemp_int (uint16_t status, uint16_t int_enb) +{ + uint16_t pid; + uint16_t pipe; + uint16_t bitcheck; + uint16_t inbuf; + + bitcheck = (uint16_t)(status & int_enb); + + USB201.BEMPSTS = (uint16_t)~status; + + for (pipe = USB_HOST_PIPE1; pipe <= USB_HOST_MAX_PIPE_NO; pipe++) + { + if ((bitcheck&g_usb1_host_bit_set[pipe]) == g_usb1_host_bit_set[pipe]) + { + pid = usb1_host_get_pid(pipe); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_STALL; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_STALL); +#endif + } + else + { + inbuf = usb1_host_get_inbuf(pipe); + + if (inbuf == 0) + { + usb1_host_disable_bemp_int(pipe); + usb1_host_set_pid_nak(pipe); + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_DONE; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(pipe, TD_CC_NOERROR); +#endif + } + } + } + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/src/common/usb1_host_lib.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,1598 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_lib.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#if(1) /* ohci_wrapp */ +#include "VKRZA1H.h" /* INTC Driver Header */ +#else +#include "devdrv_intc.h" /* INTC Driver Header */ +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_enable_brdy_int +* Description : Enables BRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : BRDY. Enables BRDY interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_enable_brdy_int (uint16_t pipe) +{ + /* enable brdy interrupt */ + USB201.BRDYENB |= (uint16_t)g_usb1_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb1_host_disable_brdy_int +* Description : Disables BRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : BRDY. Enables BRDY interrupt in the pipe specified by the argument +* : in the disabled status. After disabling BRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_disable_brdy_int (uint16_t pipe) +{ + /* disable brdy interrupt */ + USB201.BRDYENB &= (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_clear_brdy_sts +* Description : Clear BRDY interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_clear_brdy_sts (uint16_t pipe) +{ + /* clear brdy status */ + USB201.BRDYSTS = (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_enable_bemp_int +* Description : Enables BEMP interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : BEMP. Enables BEMP interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BEMP, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_enable_bemp_int (uint16_t pipe) +{ + /* enable bemp interrupt */ + USB201.BEMPENB |= (uint16_t)g_usb1_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb1_host_disable_bemp_int +* Description : Disables BEMP interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : BEMP. Enables BEMP interrupt in the pipe specified by the argument +* : in the disabled status. After enabling BEMP, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_disable_bemp_int (uint16_t pipe) +{ + /* disable bemp interrupt */ + USB201.BEMPENB &= (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_clear_bemp_sts +* Description : Clear BEMP interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_clear_bemp_sts (uint16_t pipe) +{ + /* clear bemp status */ + USB201.BEMPSTS = (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_enable_nrdy_int +* Description : Enables NRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before enabling +* : NRDY. Enables NRDY interrupt in the pipe specified by the argument +* : in the disabled status. After enabling NRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_enable_nrdy_int (uint16_t pipe) +{ + /* enable nrdy interrupt */ + USB201.NRDYENB |= (uint16_t)g_usb1_host_bit_set[pipe]; +} + +/******************************************************************************* +* Function Name: usb1_host_disable_nrdy_int +* Description : Disables NRDY interrupt in the pipe spceified by the argument. +* : Disables BEMP/NRDY/BRDY interrupts in all pipes before disabling +* : NRDY. Disables NRDY interrupt in the pipe specified by the argument +* : in the disabled status. After disabling NRDY, recover all +* : BEMP/NRDY/BRDY disabled/enabled status. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_disable_nrdy_int (uint16_t pipe) +{ + /* disable nrdy interrupt */ + USB201.NRDYENB &= (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_clear_nrdy_sts +* Description : Clear NRDY interrupt status in the pipe spceified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_clear_nrdy_sts (uint16_t pipe) +{ + /* clear nrdy status */ + USB201.NRDYSTS = (uint16_t)~(g_usb1_host_bit_set[pipe]); +} + +/******************************************************************************* +* Function Name: usb1_host_is_hispeed +* Description : Returns the result of USB reset hand shake (RHST) as +* : return value. +* Arguments : none +* Return Value : USB_HOST_HIGH_SPEED ; Hi-Speed +* : USB_HOST_FULL_SPEED ; Full-Speed +* : USB_HOST_LOW_SPEED ; Low-Speed +* : USB_HOST_NON_SPEED ; error +*******************************************************************************/ +uint16_t usb1_host_is_hispeed (void) +{ + uint16_t rhst; + uint16_t speed; + + rhst = RZA_IO_RegRead_16(&USB201.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (rhst == USB_HOST_HSMODE) + { + speed = USB_HOST_HIGH_SPEED; + } + else if (rhst == USB_HOST_FSMODE) + { + speed = USB_HOST_FULL_SPEED; + } + else if (rhst == USB_HOST_LSMODE) + { + speed = USB_HOST_LOW_SPEED; + } + else + { + speed = USB_HOST_NON_SPEED; + } + + return speed; +} + +/******************************************************************************* +* Function Name: usb1_host_is_hispeed_enable +* Description : Returns the USB High-Speed connection enabled status as +* : return value. +* Arguments : none +* Return Value : USB_HOST_YES : Hi-Speed Enable +* : USB_HOST_NO : Hi-Speed Disable +*******************************************************************************/ +uint16_t usb1_host_is_hispeed_enable (void) +{ + uint16_t ret; + + ret = USB_HOST_NO; + + if (RZA_IO_RegRead_16(&USB201.SYSCFG0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE) == 1) + { + ret = USB_HOST_YES; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_host_set_pid_buf +* Description : Enables communicaqtion in the pipe specified by the argument +* : (BUF). +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_pid_buf (uint16_t pipe) +{ + uint16_t pid; + + pid = usb1_host_get_pid(pipe); + + if (pid == USB_HOST_PID_STALL2) + { + usb1_host_set_pid_nak(pipe); + } + + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + USB_HOST_PID_BUF, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + USB_HOST_PID_BUF, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_set_pid_nak +* Description : Disables communication (NAK) in the pipe specified by the argument. +* : When the pipe status was enabling communication (BUF) before +* : executing before executing this function, waits in the software +* : until the pipe becomes ready after setting disabled. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_pid_nak (uint16_t pipe) +{ + uint16_t pid; + uint16_t pbusy; + uint32_t loop; + + pid = usb1_host_get_pid(pipe); + + if (pid == USB_HOST_PID_STALL2) + { + usb1_host_set_pid_stall(pipe); + } + + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + USB_HOST_PID_NAK, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + USB_HOST_PID_NAK, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + + if (pid == USB_HOST_PID_BUF) + { + for (loop = 0; loop < 200; loop++) + { + switch (pipe) + { + case USB_HOST_PIPE0: + pbusy = RZA_IO_RegRead_16(&USB201.DCPCTR, + USB_DCPCTR_PBUSY_SHIFT, + USB_DCPCTR_PBUSY); + break; + + case USB_HOST_PIPE1: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE1CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE2: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE2CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE3: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE3CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE4: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE4CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE5: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE5CTR, + USB_PIPEnCTR_1_5_PBUSY_SHIFT, + USB_PIPEnCTR_1_5_PBUSY); + break; + + case USB_HOST_PIPE6: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE6CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE7: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE7CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE8: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE8CTR, + USB_PIPEnCTR_6_8_PBUSY_SHIFT, + USB_PIPEnCTR_6_8_PBUSY); + break; + + case USB_HOST_PIPE9: + pbusy = RZA_IO_RegRead_16(&USB201.PIPE9CTR, + USB_PIPEnCTR_9_PBUSY_SHIFT, + USB_PIPEnCTR_9_PBUSY); + break; + + default: + pbusy = 1; + break; + } + + if (pbusy == 0) + { + break; + } + + Userdef_USB_usb1_host_delay_500ns(); + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_set_pid_stall +* Description : Disables communication (STALL) in the pipe specified by the +* : argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_pid_stall (uint16_t pipe) +{ + uint16_t pid; + + pid = usb1_host_get_pid(pipe); + + if (pid == USB_HOST_PID_BUF) + { + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + USB_HOST_PID_STALL2, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + USB_HOST_PID_STALL2, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + } + else + { + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + USB_HOST_PID_STALL, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + USB_HOST_PID_STALL, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + break; + } + } +} + +/******************************************************************************* +* Function Name: usb1_host_clear_pid_stall +* Description : Disables communication (NAK) in the pipe specified by the argument. +* Arguments : uint16_t pipe ; pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_clear_pid_stall (uint16_t pipe) +{ + usb1_host_set_pid_nak(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_get_pid +* Description : Returns the pipe state specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : PID +*******************************************************************************/ +uint16_t usb1_host_get_pid (uint16_t pipe) +{ + uint16_t pid; + + switch (pipe) + { + case USB_HOST_PIPE0: + pid = RZA_IO_RegRead_16(&USB201.DCPCTR, + USB_DCPCTR_PID_SHIFT, + USB_DCPCTR_PID); + break; + + case USB_HOST_PIPE1: + pid = RZA_IO_RegRead_16(&USB201.PIPE1CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE2: + pid = RZA_IO_RegRead_16(&USB201.PIPE2CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE3: + pid = RZA_IO_RegRead_16(&USB201.PIPE3CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE4: + pid = RZA_IO_RegRead_16(&USB201.PIPE4CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE5: + pid = RZA_IO_RegRead_16(&USB201.PIPE5CTR, + USB_PIPEnCTR_1_5_PID_SHIFT, + USB_PIPEnCTR_1_5_PID); + break; + + case USB_HOST_PIPE6: + pid = RZA_IO_RegRead_16(&USB201.PIPE6CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE7: + pid = RZA_IO_RegRead_16(&USB201.PIPE7CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE8: + pid = RZA_IO_RegRead_16(&USB201.PIPE8CTR, + USB_PIPEnCTR_6_8_PID_SHIFT, + USB_PIPEnCTR_6_8_PID); + break; + + case USB_HOST_PIPE9: + pid = RZA_IO_RegRead_16(&USB201.PIPE9CTR, + USB_PIPEnCTR_9_PID_SHIFT, + USB_PIPEnCTR_9_PID); + break; + + default: + pid = 0; + break; + } + + return pid; +} + +/******************************************************************************* +* Function Name: usb1_host_set_csclr +* Description : CSPLIT status clear setting of sprit transaction in specified +* : pipe is performed. +* : When SQSET bit or SQCLR bit, and SQSET bit or SQCLR bit +* : in DCPCTR register are continuously changed (when the sequence +* : toggle bit of data PID is continuously changed over two or more pipes), +* : the access cycle with 120 ns and more than 5 cycle bus clock is necessary. +* : Do not set both SQCLR bit and SQSET bit to 1 at the same time. +* : In addition, both bits should be operated after PID is set to NAK. +* : However, when it is set to the isochronous transfer as the transfer type +* : (TYPE=11), writing in SQSET bit is disabled. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_csclr (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + 1, + USB_DCPCTR_CSCLR_SHIFT, + USB_DCPCTR_CSCLR); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_CSCLR_SHIFT, + USB_PIPEnCTR_1_5_CSCLR); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_CSCLR_SHIFT, + USB_PIPEnCTR_6_8_CSCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + 1, + USB_PIPEnCTR_9_CSCLR_SHIFT, + USB_PIPEnCTR_9_CSCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_set_sqclr +* Description : Sets the sequence bit of the pipe specified by the argument to +* : DATA0. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_sqclr (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + 1, + USB_DCPCTR_SQCLR_SHIFT, + USB_DCPCTR_SQCLR); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_SQCLR_SHIFT, + USB_PIPEnCTR_1_5_SQCLR); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_SQCLR_SHIFT, + USB_PIPEnCTR_6_8_SQCLR); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + 1, + USB_PIPEnCTR_9_SQCLR_SHIFT, + USB_PIPEnCTR_9_SQCLR); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_set_sqset +* Description : Sets the sequence bit of the pipe specified by the argument to +* : DATA1. +* Arguments : uint16_t pipe ; Pipe number +* Return Value : none +*******************************************************************************/ +void usb1_host_set_sqset (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + RZA_IO_RegWrite_16(&USB201.DCPCTR, + 1, + USB_DCPCTR_SQSET_SHIFT, + USB_DCPCTR_SQSET); + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_SQSET_SHIFT, + USB_PIPEnCTR_1_5_SQSET); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_SQSET_SHIFT, + USB_PIPEnCTR_6_8_SQSET); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + 1, + USB_PIPEnCTR_9_SQSET_SHIFT, + USB_PIPEnCTR_9_SQSET); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_get_sqmon +* Description : Toggle bit of specified pipe is obtained +* Arguments : uint16_t pipe ; Pipe number +* Return Value : sqmon +*******************************************************************************/ +uint16_t usb1_host_get_sqmon (uint16_t pipe) +{ + uint16_t sqmon; + + switch (pipe) + { + case USB_HOST_PIPE0: + sqmon = RZA_IO_RegRead_16(&USB201.DCPCTR, + USB_DCPCTR_SQMON_SHIFT, + USB_DCPCTR_SQMON); + break; + + case USB_HOST_PIPE1: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE1CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE2: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE2CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE3: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE3CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE4: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE4CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE5: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE5CTR, + USB_PIPEnCTR_1_5_SQMON_SHIFT, + USB_PIPEnCTR_1_5_SQMON); + break; + + case USB_HOST_PIPE6: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE6CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE7: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE7CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE8: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE8CTR, + USB_PIPEnCTR_6_8_SQMON_SHIFT, + USB_PIPEnCTR_6_8_SQMON); + break; + + case USB_HOST_PIPE9: + sqmon = RZA_IO_RegRead_16(&USB201.PIPE9CTR, + USB_PIPEnCTR_9_SQMON_SHIFT, + USB_PIPEnCTR_9_SQMON); + break; + + default: + sqmon = 0; + break; + } + + return sqmon; +} + +/******************************************************************************* +* Function Name: usb1_host_aclrm +* Description : The buffer of specified pipe is initialized +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb1_host_aclrm (uint16_t pipe) +{ + usb1_host_set_aclrm(pipe); + usb1_host_clr_aclrm(pipe); +} + +/******************************************************************************* +* Function Name: usb1_host_set_aclrm +* Description : The auto buffer clear mode of specified pipe is enabled +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb1_host_set_aclrm (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + 1, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + 1, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + 1, + USB_PIPEnCTR_9_ACLRM_SHIFT, + USB_PIPEnCTR_9_ACLRM); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_clr_aclrm +* Description : The auto buffer clear mode of specified pipe is enabled +* Arguments : uint16_t pipe : Pipe +* Return Value : none +*******************************************************************************/ +void usb1_host_clr_aclrm (uint16_t pipe) +{ + switch (pipe) + { + case USB_HOST_PIPE0: + break; + + case USB_HOST_PIPE1: + RZA_IO_RegWrite_16(&USB201.PIPE1CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE2: + RZA_IO_RegWrite_16(&USB201.PIPE2CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE3: + RZA_IO_RegWrite_16(&USB201.PIPE3CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE4: + RZA_IO_RegWrite_16(&USB201.PIPE4CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE5: + RZA_IO_RegWrite_16(&USB201.PIPE5CTR, + 0, + USB_PIPEnCTR_1_5_ACLRM_SHIFT, + USB_PIPEnCTR_1_5_ACLRM); + break; + + case USB_HOST_PIPE6: + RZA_IO_RegWrite_16(&USB201.PIPE6CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE7: + RZA_IO_RegWrite_16(&USB201.PIPE7CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE8: + RZA_IO_RegWrite_16(&USB201.PIPE8CTR, + 0, + USB_PIPEnCTR_6_8_ACLRM_SHIFT, + USB_PIPEnCTR_6_8_ACLRM); + break; + + case USB_HOST_PIPE9: + RZA_IO_RegWrite_16(&USB201.PIPE9CTR, + 0, + USB_PIPEnCTR_9_ACLRM_SHIFT, + USB_PIPEnCTR_9_ACLRM); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_get_inbuf +* Description : Returns INBUFM of the pipe specified by the argument. +* Arguments : uint16_t pipe ; Pipe Number +* Return Value : inbuf +*******************************************************************************/ +uint16_t usb1_host_get_inbuf (uint16_t pipe) +{ + uint16_t inbuf; + + switch (pipe) + { + case USB_HOST_PIPE0: + inbuf = 0; + break; + + case USB_HOST_PIPE1: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE1CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE2: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE2CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE3: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE3CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE4: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE4CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE5: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE5CTR, + USB_PIPEnCTR_1_5_INBUFM_SHIFT, + USB_PIPEnCTR_1_5_INBUFM); + break; + + case USB_HOST_PIPE6: + inbuf = 0; + break; + + case USB_HOST_PIPE7: + inbuf = 0; + break; + + case USB_HOST_PIPE8: + inbuf = 0; + break; + + case USB_HOST_PIPE9: + inbuf = RZA_IO_RegRead_16(&USB201.PIPE9CTR, + USB_PIPEnCTR_9_INBUFM_SHIFT, + USB_PIPEnCTR_9_INBUFM); + break; + + default: + inbuf = 0; + break; + } + + return inbuf; +} + +/******************************************************************************* +* Function Name: usb1_host_setting_interrupt +* Description : Sets the USB module interrupt level. +* Arguments : uint8_t level ; interrupt level +* Return Value : none +*******************************************************************************/ +void usb1_host_setting_interrupt (uint8_t level) +{ +#if(1) /* ohci_wrapp */ + IRQn_Type d0fifo_dmaintid; + IRQn_Type d1fifo_dmaintid; + + InterruptHandlerRegister(USBI1_IRQn, usb1_host_interrupt); + GIC_SetPriority(USBI1_IRQn, level); + GIC_EnableIRQ(USBI1_IRQn); + + d0fifo_dmaintid = (IRQn_Type)Userdef_USB_usb1_host_d0fifo_dmaintid(); + + if (d0fifo_dmaintid != 0xFFFF) + { + InterruptHandlerRegister(d0fifo_dmaintid, usb1_host_dma_interrupt_d0fifo); + GIC_SetPriority(d0fifo_dmaintid, level); + GIC_EnableIRQ(d0fifo_dmaintid); + } + + d1fifo_dmaintid = (IRQn_Type)Userdef_USB_usb1_host_d1fifo_dmaintid(); + + if (d1fifo_dmaintid != 0xFFFF) + { + InterruptHandlerRegister(d1fifo_dmaintid, usb1_host_dma_interrupt_d1fifo); + GIC_SetPriority(d1fifo_dmaintid, level); + GIC_EnableIRQ(d1fifo_dmaintid); + } +#else + uint16_t d0fifo_dmaintid; + uint16_t d1fifo_dmaintid; + + R_INTC_RegistIntFunc(INTC_ID_USBI1, usb1_host_interrupt); + R_INTC_SetPriority(INTC_ID_USBI1, level); + R_INTC_Enable(INTC_ID_USBI1); + + d0fifo_dmaintid = Userdef_USB_usb1_host_d0fifo_dmaintid(); + + if (d0fifo_dmaintid != 0xFFFF) + { + R_INTC_RegistIntFunc(d0fifo_dmaintid, usb1_host_dma_interrupt_d0fifo); + R_INTC_SetPriority(d0fifo_dmaintid, level); + R_INTC_Enable(d0fifo_dmaintid); + } + + d1fifo_dmaintid = Userdef_USB_usb1_host_d1fifo_dmaintid(); + + if (d1fifo_dmaintid != 0xFFFF) + { + R_INTC_RegistIntFunc(d1fifo_dmaintid, usb1_host_dma_interrupt_d1fifo); + R_INTC_SetPriority(d1fifo_dmaintid, level); + R_INTC_Enable(d1fifo_dmaintid); + } +#endif +} + +/******************************************************************************* +* Function Name: usb1_host_reset_module +* Description : Initializes the USB module. +* : Enables providing clock to the USB module. +* : Sets USB bus wait register. +* Arguments : uint16_t clockmode ; 48MHz ; USBHCLOCK_X1_48MHZ +* : ; 12MHz ; USBHCLOCK_EXTAL_12MHZ +* Return Value : none +*******************************************************************************/ +void usb1_host_reset_module (uint16_t clockmode) +{ + if (RZA_IO_RegRead_16(&USB200.SYSCFG0, + USB_SYSCFG_UPLLE_SHIFT, + USB_SYSCFG_UPLLE) == 1) + { + if ((USB200.SYSCFG0 & USB_HOST_BITUCKSEL) != clockmode) + { + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + USB201.SYSCFG0 = 0; + USB200.SYSCFG0 = 0; + USB200.SYSCFG0 = (USB_HOST_BITUPLLE | clockmode); + Userdef_USB_usb1_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + else + { + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + Userdef_USB_usb1_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + } + else + { + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 0, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + USB201.SYSCFG0 = 0; + USB200.SYSCFG0 = 0; + USB200.SYSCFG0 = (USB_HOST_BITUPLLE | clockmode); + Userdef_USB_usb1_host_delay_xms(1); + RZA_IO_RegWrite_16(&USB200.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + RZA_IO_RegWrite_16(&USB201.SUSPMODE, + 1, + USB_SUSPMODE_SUSPM_SHIFT, + USB_SUSPMODE_SUSPM); + } + + USB201.BUSWAIT = (uint16_t)(USB_HOST_BUSWAIT_05 & USB_HOST_BITBWAIT); +} + +/******************************************************************************* +* Function Name: usb1_host_get_buf_size +* Description : Obtains pipe buffer size specified by the argument and +* : maximum packet size of the USB device in use. +* : When USB_HOST_PIPE0 is specified by the argument, obtains the maximum +* : packet size of the USB device using the corresponding pipe. +* : For the case that USB_HOST_PIPE0 is not assigned by the argument, when the +* : corresponding pipe is in continuous transfer mode, +* : obtains the buffer size allocated in the corresponcing pipe, +* : when incontinuous transfer, obtains maximum packet size. +* Arguments : uint16_t ; pipe Number +* Return Value : Maximum packet size or buffer size +*******************************************************************************/ +uint16_t usb1_host_get_buf_size (uint16_t pipe) +{ + uint16_t size; + uint16_t bufsize; + + if (pipe == USB_HOST_PIPE0) + { + size = RZA_IO_RegRead_16(&USB201.DCPMAXP, + USB_DCPMAXP_MXPS_SHIFT, + USB_DCPMAXP_MXPS); + } + else + { + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[pipe], USB_PIPECFG_CNTMD_SHIFT, USB_PIPECFG_CNTMD) == 1) + { + bufsize = RZA_IO_RegRead_16(&g_usb1_host_pipebuf[pipe], USB_PIPEBUF_BUFSIZE_SHIFT, USB_PIPEBUF_BUFSIZE); + size = (uint16_t)((bufsize + 1) * USB_HOST_PIPExBUF); + } + else + { + size = RZA_IO_RegRead_16(&g_usb1_host_pipemaxp[pipe], USB_PIPEMAXP_MXPS_SHIFT, USB_PIPEMAXP_MXPS); + } + } + return size; +} + +/******************************************************************************* +* Function Name: usb1_host_get_mxps +* Description : Obtains maximum packet size of the USB device using the pipe +* : specified by the argument. +* Arguments : uint16_t ; Pipe Number +* Return Value : Max Packet Size +*******************************************************************************/ +uint16_t usb1_host_get_mxps (uint16_t pipe) +{ + uint16_t size; + + if (pipe == USB_HOST_PIPE0) + { + size = RZA_IO_RegRead_16(&USB201.DCPMAXP, + USB_DCPMAXP_MXPS_SHIFT, + USB_DCPMAXP_MXPS); + } + else + { + size = RZA_IO_RegRead_16(&g_usb1_host_pipemaxp[pipe], USB_PIPEMAXP_MXPS_SHIFT, USB_PIPEMAXP_MXPS); + } + + return size; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/src/host/usb1_host_controlrw.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,434 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_controlrw.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_CtrlTransStart +* Description : Executes USB control transfer. +* Arguments : uint16_t devadr ; device address +* : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* : uint8_t *Buf ; Data buffer +* Return Value : DEVDRV_SUCCESS ; SUCCESS +* : DEVDRV_ERROR ; ERROR +*******************************************************************************/ +int32_t usb1_host_CtrlTransStart (uint16_t devadr, uint16_t Req, uint16_t Val, + uint16_t Indx, uint16_t Len, uint8_t * Buf) +{ + if (g_usb1_host_UsbDeviceSpeed == USB_HOST_LOW_SPEED) + { + RZA_IO_RegWrite_16(&USB201.SOFCFG, + 1, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + else + { + RZA_IO_RegWrite_16(&USB201.SOFCFG, + 0, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + + USB201.DCPMAXP = (uint16_t)((uint16_t)(devadr << 12) + g_usb1_host_default_max_packet[devadr]); + + if (g_usb1_host_pipe_status[USB_HOST_PIPE0] == USB_HOST_PIPE_IDLE) + { + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_WAIT; + g_usb1_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + g_usb1_host_CmdStage = (USB_HOST_STAGE_SETUP | USB_HOST_CMD_IDLE); + + if (Len == 0) + { + g_usb1_host_CmdStage |= USB_HOST_MODE_NO_DATA; /* No-data Control */ + } + else + { + if ((Req & 0x0080) != 0) + { + g_usb1_host_CmdStage |= USB_HOST_MODE_READ; /* Control Read */ + } + else + { + g_usb1_host_CmdStage |= USB_HOST_MODE_WRITE; /* Control Write */ + } + } + + g_usb1_host_SavReq = Req; /* save request */ + g_usb1_host_SavVal = Val; + g_usb1_host_SavIndx = Indx; + g_usb1_host_SavLen = Len; + } + else + { + if ((g_usb1_host_SavReq != Req) || (g_usb1_host_SavVal != Val) + || (g_usb1_host_SavIndx != Indx) || (g_usb1_host_SavLen != Len)) + { + return DEVDRV_ERROR; + } + } + + switch ((g_usb1_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + /* --------------- SETUP STAGE --------------- */ + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_IDLE): + usb1_host_SetupStage(Req, Val, Indx, Len); + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_DONE): /* goto next stage */ + g_usb1_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + switch ((g_usb1_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_WRITE: + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_DATA; + break; + + case USB_HOST_MODE_READ: + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_DATA; + break; + + case USB_HOST_MODE_NO_DATA: + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_STATUS; + break; + + default: + break; + } + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + case (USB_HOST_STAGE_SETUP | USB_HOST_CMD_NORES): + if (g_usb1_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb1_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_IDLE; + } + break; + + /* --------------- DATA STAGE --------------- */ + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_IDLE): + switch ((g_usb1_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_WRITE: + usb1_host_CtrlWriteStart((uint32_t)Len, Buf); + break; + + case USB_HOST_MODE_READ: + usb1_host_CtrlReadStart((uint32_t)Len, Buf); + break; + + default: + break; + } + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DONE): /* goto next stage */ + g_usb1_host_PipeIgnore[USB_HOST_PIPE0] = 0; /* Ignore count clear */ + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_STATUS; + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_NORES): + if (g_usb1_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb1_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DOING; + usb1_host_clear_pid_stall(USB_HOST_PIPE0); + usb1_host_set_pid_buf(USB_HOST_PIPE0); + } + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_STALL): + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + break; + + /* --------------- STATUS STAGE --------------- */ + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_IDLE): + usb1_host_StatusStage(); + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + /* do nothing */ + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DONE): /* end of Control transfer */ + usb1_host_set_pid_nak(USB_HOST_PIPE0); + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_DONE; /* exit DONE */ + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_NORES): + if (g_usb1_host_PipeIgnore[USB_HOST_PIPE0] == 3) + { + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + } + else + { + g_usb1_host_PipeIgnore[USB_HOST_PIPE0]++; /* Ignore count */ + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DOING; + usb1_host_clear_pid_stall(USB_HOST_PIPE0); + usb1_host_set_pid_buf(USB_HOST_PIPE0); + } + break; + + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_STALL): + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + break; + + default: + break; + } + + if (g_usb1_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_WAIT) + { + RZA_IO_RegWrite_16(&USB201.SOFCFG, + 0, + USB_SOFCFG_TRNENSEL_SHIFT, + USB_SOFCFG_TRNENSEL); + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb1_host_SetupStage +* Description : Executes USB control transfer/set up stage. +* Arguments : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* Return Value : none +*******************************************************************************/ +void usb1_host_SetupStage (uint16_t Req, uint16_t Val, uint16_t Indx, uint16_t Len) +{ + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DOING; + + USB201.INTSTS1 = (uint16_t)~(USB_HOST_BITSACK | USB_HOST_BITSIGN); /* Status Clear */ + USB201.USBREQ = Req; + USB201.USBVAL = Val; + USB201.USBINDX = Indx; + USB201.USBLENG = Len; + USB201.DCPCTR = USB_HOST_BITSUREQ; /* PID=NAK & Send Setup */ +} + +/******************************************************************************* +* Function Name: usb1_host_StatusStage +* Description : Executes USB control transfer/status stage. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_StatusStage (void) +{ + uint8_t Buf1[16]; + + switch ((g_usb1_host_CmdStage & (USB_HOST_MODE_FIELD))) + { + case USB_HOST_MODE_READ: + usb1_host_CtrlWriteStart((uint32_t)0, (uint8_t*)&Buf1); + break; + + case USB_HOST_MODE_WRITE: + usb1_host_CtrlReadStart((uint32_t)0, (uint8_t*)&Buf1); + break; + + case USB_HOST_MODE_NO_DATA: + usb1_host_CtrlReadStart((uint32_t)0, (uint8_t*)&Buf1); + break; + + default: + break; + } +} + +/******************************************************************************* +* Function Name: usb1_host_CtrlWriteStart +* Description : Executes USB control transfer/data stage(write). +* Arguments : uint32_t Bsize ; Data Size +* : uint8_t *Table ; Data Table Address +* Return Value : USB_HOST_WRITESHRT ; End of data write +* : USB_HOST_WRITEEND ; End of data write (not null) +* : USB_HOST_WRITING ; Continue of data write +* : USB_HOST_FIFOERROR ; FIFO access error +*******************************************************************************/ +uint16_t usb1_host_CtrlWriteStart (uint32_t Bsize, uint8_t * Table) +{ + uint16_t EndFlag_K; + uint16_t mbw; + + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DOING; + + usb1_host_set_pid_nak(USB_HOST_PIPE0); /* Set NAK */ + g_usb1_host_data_count[USB_HOST_PIPE0] = Bsize; /* Transfer size set */ + g_usb1_host_data_pointer[USB_HOST_PIPE0] = Table; /* Transfer address set */ + + USB201.DCPCTR = USB_HOST_BITSQSET; /* SQSET=1, PID=NAK */ +#if(1) /* ohci_wrapp */ + Userdef_USB_usb1_host_delay_10us(3); +#endif + RZA_IO_RegWrite_16(&USB201.DCPCFG, + 1, + USB_DCPCFG_DIR_SHIFT, + USB_DCPCFG_DIR); + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[USB_HOST_PIPE0], (uint32_t)g_usb1_host_data_pointer[USB_HOST_PIPE0]); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_BITISEL, mbw); + USB201.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + + usb1_host_clear_pid_stall(USB_HOST_PIPE0); + EndFlag_K = usb1_host_write_buffer_c(USB_HOST_PIPE0); + /* Host Control sequence */ + switch (EndFlag_K) + { + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_STATUS; + usb1_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb1_host_enable_bemp_int(USB_HOST_PIPE0); /* Enable Empty Interrupt */ + break; + + case USB_HOST_WRITEEND: /* End of data write (not null) */ + case USB_HOST_WRITING: /* Continue of data write */ + usb1_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb1_host_enable_bemp_int(USB_HOST_PIPE0); /* Enable Empty Interrupt */ + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + break; + + default: + break; + } + usb1_host_set_pid_buf(USB_HOST_PIPE0); /* Set BUF */ + return (EndFlag_K); /* End or Err or Continue */ +} + +/******************************************************************************* +* Function Name: usb1_host_CtrlReadStart +* Description : Executes USB control transfer/data stage(read). +* Arguments : uint32_t Bsize ; Data Size +* : uint8_t *Table ; Data Table Address +* Return Value : none +*******************************************************************************/ +void usb1_host_CtrlReadStart (uint32_t Bsize, uint8_t * Table) +{ + uint16_t mbw; + + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DOING; + + usb1_host_set_pid_nak(USB_HOST_PIPE0); /* Set NAK */ + g_usb1_host_data_count[USB_HOST_PIPE0] = Bsize; /* Transfer size set */ + g_usb1_host_data_pointer[USB_HOST_PIPE0] = Table; /* Transfer address set */ + + USB201.DCPCTR = USB_HOST_BITSQSET; /* SQSET=1, PID=NAK */ +#if(1) /* ohci_wrapp */ + Userdef_USB_usb1_host_delay_10us(3); +#endif + RZA_IO_RegWrite_16(&USB201.DCPCFG, + 0, + USB_DCPCFG_DIR_SHIFT, + USB_DCPCFG_DIR); + + mbw = usb1_host_get_mbw(g_usb1_host_data_count[USB_HOST_PIPE0], (uint32_t)g_usb1_host_data_pointer[USB_HOST_PIPE0]); + usb1_host_set_curpipe(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_NO, mbw); + USB201.CFIFOCTR = USB_HOST_BITBCLR; /* Buffer Clear */ + + usb1_host_enable_nrdy_int(USB_HOST_PIPE0); /* Error (NORES or STALL) */ + usb1_host_enable_brdy_int(USB_HOST_PIPE0); /* Ok */ + usb1_host_clear_pid_stall(USB_HOST_PIPE0); + usb1_host_set_pid_buf(USB_HOST_PIPE0); /* Set BUF */ +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/src/host/usb1_host_drv_api.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,889 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_drv_api.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb1_host_resetEP(USB_HOST_CFG_PIPETBL_t *tbl); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_api_host_init +* Description : Initializes USB module in the USB host mode. +* : USB connection is executed when executing this function in +* : the states that USB device isconnected to the USB port. +* Arguments : uint8_t int_level : USB Module interrupt level +* : USBU16 mode : USB_HOST_HIGH_SPEED +* : USB_HOST_FULL_SPEED +* : uint16_t clockmode : USB Clock mode +* Return Value : USB detach or attach +* : USB_HOST_ATTACH +* : USB_HOST_DETACH +*******************************************************************************/ +uint16_t usb1_api_host_init (uint8_t int_level, uint16_t mode, uint16_t clockmode) +{ + uint16_t connect; + volatile uint8_t dummy_buf; + + CPG.STBCR7 &= 0xfc; /*The clock of USB0/1 modules is permitted */ + dummy_buf = CPG.STBCR7; /* (Dummy read) */ + + g_usb1_host_SupportUsbDeviceSpeed = mode; + + usb1_host_setting_interrupt(int_level); + usb1_host_reset_module(clockmode); + + g_usb1_host_bchg_flag = USB_HOST_NO; + g_usb1_host_detach_flag = USB_HOST_NO; + g_usb1_host_attach_flag = USB_HOST_NO; + + g_usb1_host_driver_state = USB_HOST_DRV_DETACHED; + g_usb1_host_default_max_packet[USB_HOST_DEVICE_0] = 64; + + usb1_host_InitModule(); + + connect = usb1_host_CheckAttach(); + + if (connect == USB_HOST_ATTACH) + { + g_usb1_host_attach_flag = USB_HOST_YES; + } + else + { + usb1_host_UsbDetach2(); + } + + return connect; +} + +#if(1) /* ohci_wrapp */ +#else +/******************************************************************************* +* Function Name: usb1_api_host_enumeration +* Description : Initializes USB module in the USB host mode. +* : USB connection is executed when executing this function in +* : the states that USB device isconnected to the USB port. +* Arguments : uint16_t devadr : device address +* Return Value : DEVDRV_USBH_DETACH_ERR : device detach +* : DEVDRV_SUCCESS : device enumeration success +* : DEVDRV_ERROR : device enumeration error +*******************************************************************************/ +int32_t usb1_api_host_enumeration (uint16_t devadr) +{ + int32_t ret; + uint16_t driver_sts; + + g_usb1_host_setUsbAddress = devadr; + + while (1) + { + driver_sts = usb1_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + ret = DEVDRV_USBH_DETACH_ERR; + break; + } + else if (driver_sts == USB_HOST_DRV_CONFIGURED) + { + ret = DEVDRV_SUCCESS; + break; + } + else if (driver_sts == USB_HOST_DRV_STALL) + { + ret = DEVDRV_ERROR; + break; + } + else if (driver_sts == USB_HOST_DRV_NORES) + { + ret = DEVDRV_ERROR; + break; + } + else + { + /* Do Nothing */ + } + } + + if (driver_sts == USB_HOST_DRV_NORES) + { + while (1) + { + driver_sts = usb1_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + break; + } + } + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_api_host_detach +* Description : USB detach routine +* Arguments : none +* Return Value : USB_HOST_DETACH : USB detach +* : USB_HOST_ATTACH : USB attach +* : DEVDRV_ERROR : error +*******************************************************************************/ +int32_t usb1_api_host_detach (void) +{ + int32_t ret; + uint16_t driver_sts; + + while (1) + { + driver_sts = usb1_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + ret = USB_HOST_DETACH; + break; + } + else if (driver_sts == USB_HOST_DRV_CONFIGURED) + { + ret = USB_HOST_ATTACH; + break; + } + else if (driver_sts == USB_HOST_DRV_STALL) + { + ret = DEVDRV_ERROR; + break; + } + else if (driver_sts == USB_HOST_DRV_NORES) + { + ret = DEVDRV_ERROR; + break; + } + else + { + /* Do Nothing */ + } + } + + if (driver_sts == USB_HOST_DRV_NORES) + { + while (1) + { + driver_sts = usb1_api_host_GetUsbDeviceState(); + + if (driver_sts == USB_HOST_DRV_DETACHED) + { + break; + } + } + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_api_host_data_in +* Description : Executes USB transfer as data-in in the argument specified pipe. +* Arguments : uint16_t devadr ; device address +* : uint16_t Pipe ; Pipe Number +* : uint32_t Size ; Data Size +* : uint8_t *data_buf ; Data data_buf Address +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_data_in (uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t * data_buf) +{ + int32_t ret; + + if (Pipe == USB_HOST_PIPE0) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipemaxp[Pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL) != devadr) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[Pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 1) + { + return DEVDRV_ERROR; + } + + if (g_usb1_host_pipe_status[Pipe] == USB_HOST_PIPE_IDLE) + { + usb1_host_start_receive_transfer(Pipe, Size, data_buf); + } + else + { + return DEVDRV_ERROR; /* Now pipe is busy */ + } + + /* waiting for completing routine */ + do + { + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb1_host_pipe_status[Pipe] != USB_HOST_PIPE_IDLE) && (g_usb1_host_pipe_status[Pipe] != USB_HOST_PIPE_WAIT)) + { + break; + } + + } while (1); + + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb1_host_pipe_status[Pipe]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + usb1_host_stop_transfer(Pipe); + + g_usb1_host_pipe_status[Pipe] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_api_host_data_out +* Description : Executes USB transfer as data-out in the argument specified pipe. +* Arguments : uint16_t devadr ; device address +* : uint16_t Pipe ; Pipe Number +* : uint32_t Size ; Data Size +* : uint8_t *data_buf ; Data data_buf Address +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_data_out (uint16_t devadr, uint16_t Pipe, uint32_t Size, uint8_t * data_buf) +{ + int32_t ret; + + if (Pipe == USB_HOST_PIPE0) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipemaxp[Pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL) != devadr) + { + return DEVDRV_ERROR; + } + + if (RZA_IO_RegRead_16(&g_usb1_host_pipecfg[Pipe], USB_PIPECFG_DIR_SHIFT, USB_PIPECFG_DIR) == 0) + { + return DEVDRV_ERROR; + } + + if (g_usb1_host_pipe_status[Pipe] == USB_HOST_PIPE_IDLE) + { + usb1_host_start_send_transfer(Pipe, Size, data_buf); + } + else + { + return DEVDRV_ERROR; /* Now pipe is busy */ + } + + /* waiting for completing routine */ + do + { + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb1_host_pipe_status[Pipe] != USB_HOST_PIPE_IDLE) && (g_usb1_host_pipe_status[Pipe] != USB_HOST_PIPE_WAIT)) + { + break; + } + + } while (1); + + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb1_host_pipe_status[Pipe]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + usb1_host_stop_transfer(Pipe); + + g_usb1_host_pipe_status[Pipe] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_api_host_control_transfer +* Description : Executes USB control transfer. +* Arguments : uint16_t devadr ; device address +* : uint16_t Req ; bmRequestType & bRequest +* : uint16_t Val ; wValue +* : uint16_t Indx ; wIndex +* : uint16_t Len ; wLength +* : uint8_t *buf ; Buffer +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_USBH_DETACH_ERR ; device detach +* : DEVDRV_USBH_CTRL_COM_ERR ; device no response +* : DEVDRV_USBH_STALL ; STALL +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_control_transfer (uint16_t devadr, uint16_t Req, uint16_t Val, uint16_t Indx, + uint16_t Len, uint8_t * Buf) +{ + int32_t ret; + + do + { + ret = usb1_host_CtrlTransStart(devadr, Req, Val, Indx, Len, Buf); + + if (ret == DEVDRV_SUCCESS) + { + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + break; + } + + if ((g_usb1_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_IDLE) + && (g_usb1_host_pipe_status[USB_HOST_PIPE0] != USB_HOST_PIPE_WAIT)) + { + break; + } + } + else + { + return DEVDRV_ERROR; + } + } while (1); + + if (g_usb1_host_detach_flag == USB_HOST_YES) + { + return DEVDRV_USBH_DETACH_ERR; + } + + switch (g_usb1_host_pipe_status[USB_HOST_PIPE0]) + { + case USB_HOST_PIPE_DONE: + ret = DEVDRV_SUCCESS; + break; + + case USB_HOST_PIPE_STALL: + ret = DEVDRV_USBH_STALL; + break; + + case USB_HOST_PIPE_NORES: + ret = DEVDRV_USBH_CTRL_COM_ERR; + break; + + default: + ret = DEVDRV_ERROR; + break; + } + + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_IDLE; + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_api_host_set_endpoint +* Description : Sets end point on the information specified in the argument. +* Arguments : uint16_t devadr ; device address +* : uint8_t *configdescriptor ; device configration descriptor +* : USB_HOST_CFG_PIPETBL_t *user_table ; pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_set_endpoint (uint16_t devadr, USB_HOST_CFG_PIPETBL_t * user_table, uint8_t * configdescriptor) +{ + uint16_t ret; + uint32_t end_point; + uint32_t offset; + uint32_t totalLength; + USB_HOST_CFG_PIPETBL_t * pipe_table; + + /* End Point Search */ + end_point = 0; + offset = configdescriptor[0]; + totalLength = (uint16_t)(configdescriptor[2] + ((uint16_t)configdescriptor[3] << 8)); + + do + { + if (configdescriptor[offset + 1] == USB_HOST_ENDPOINT_DESC) + { + pipe_table = &user_table[end_point]; + + if (pipe_table->pipe_number == 0xffff) + { + break; + } + + ret = usb1_api_host_SetEndpointTable(devadr, pipe_table, (uint8_t *)&configdescriptor[offset]); + + if ((ret != USB_HOST_PIPE_IN) && (ret != USB_HOST_PIPE_OUT)) + { + return DEVDRV_ERROR; + } + + ++end_point; + } + + /* Next End Point Search */ + offset += configdescriptor[offset]; + + } while (offset < totalLength); + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb1_api_host_clear_endpoint +* Description : Clears the pipe definition table specified in the argument. +* Arguments : uint16_t pipe_sel : Pipe Number +* : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_clear_endpoint (USB_HOST_CFG_PIPETBL_t * user_table) +{ + uint16_t pipe; + + for (pipe = USB_HOST_PIPE0; pipe <= USB_HOST_MAX_PIPE_NO; ++pipe) + { + if (user_table->pipe_number == 0xffff) + { + break; + } + user_table->pipe_cfg &= (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD); + user_table->pipe_max_pktsize = 0; + user_table->pipe_cycle = 0; + + user_table++; + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb1_api_host_clear_endpoint_pipe +* Description : Clears the pipe definition table specified in the argument. +* Arguments : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_clear_endpoint_pipe (uint16_t pipe_sel, USB_HOST_CFG_PIPETBL_t * user_table) +{ + uint16_t pipe; + + for (pipe = USB_HOST_PIPE0; pipe <= USB_HOST_MAX_PIPE_NO; ++pipe) + { + if (user_table->pipe_number == 0xffff) + { + break; + } + + if (user_table->pipe_number == pipe_sel) + { + user_table->pipe_cfg &= (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD); + user_table->pipe_max_pktsize = 0; + user_table->pipe_cycle = 0; + break; + } + + user_table++; + } + + return DEVDRV_SUCCESS; +} +#endif + +/******************************************************************************* +* Function Name: usb1_api_host_SetEndpointTable +* Description : Sets the end point on the information specified by the argument. +* Arguments : uint16_t devadr : device address +* : USB_HOST_CFG_PIPETBL_t *user_table : pipe table +* : uint8_t *Table : Endpoint descriptor +* Return Value : USB_HOST_DIR_H_IN ; IN endpoint +* : USB_HOST_DIR_H_OUT ; OUT endpoint +* : USB_END_POINT_ERROR ; error +*******************************************************************************/ +uint16_t usb1_api_host_SetEndpointTable (uint16_t devadr, USB_HOST_CFG_PIPETBL_t * user_table, uint8_t * Table) +{ + uint16_t PipeCfg; + uint16_t PipeMaxp; + uint16_t pipe_number; + uint16_t ret; + uint16_t ret_flag = 0; // avoid warning. + + pipe_number = user_table->pipe_number; + + if (Table[1] != USB_HOST_ENDPOINT_DESC) + { + return USB_END_POINT_ERROR; + } + + switch (Table[3] & USB_HOST_EP_TYPE) + { + case USB_HOST_EP_CNTRL: + ret_flag = USB_END_POINT_ERROR; + break; + + case USB_HOST_EP_ISO: + if ((pipe_number != USB_HOST_PIPE1) && (pipe_number != USB_HOST_PIPE2)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_ISO; + break; + + case USB_HOST_EP_BULK: + if ((pipe_number < USB_HOST_PIPE1) || (pipe_number > USB_HOST_PIPE5)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_BULK; + break; + + case USB_HOST_EP_INT: + if ((pipe_number < USB_HOST_PIPE6) || (pipe_number > USB_HOST_PIPE9)) + { + return USB_END_POINT_ERROR; + } + + PipeCfg = USB_HOST_INTERRUPT; + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + + /* Set pipe configuration table */ + if ((Table[2] & USB_HOST_EP_DIR_MASK) == USB_HOST_EP_IN) /* IN(receive) */ + { + if (PipeCfg == USB_HOST_ISO) + { + /* Transfer Type is ISO*/ + PipeCfg |= USB_HOST_DIR_H_IN; + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + case USB_HOST_D0USE: + case USB_HOST_D1USE: + case USB_HOST_D0DMA: + case USB_HOST_D1DMA: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & USB_HOST_DBLBFIELD); + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + } + else + { + /* Transfer Type is BULK or INT */ + PipeCfg |= (USB_HOST_SHTNAKON | USB_HOST_DIR_H_IN); /* Compulsory SHTNAK */ + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + case USB_HOST_D0USE: + case USB_HOST_D1USE: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); + break; + + case USB_HOST_D0DMA: + case USB_HOST_D1DMA: + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); +#ifdef __USB_DMA_BFRE_ENABLE__ + /* this routine cannnot be perfomred if read operation is executed in buffer size */ + PipeCfg |= USB_HOST_BFREON; +#endif + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + } + ret = USB_HOST_PIPE_IN; + } + else /* OUT(send) */ + { + if (PipeCfg == USB_HOST_ISO) + { + /* Transfer Type is ISO*/ + PipeCfg |= (uint16_t)(user_table->pipe_cfg & USB_HOST_DBLBFIELD); + } + else + { + /* Transfer Type is BULK or INT */ + PipeCfg |= (uint16_t)(user_table->pipe_cfg & (USB_HOST_DBLBFIELD | USB_HOST_CNTMDFIELD)); + } + PipeCfg |= USB_HOST_DIR_H_OUT; + ret = USB_HOST_PIPE_OUT; + } + + switch (user_table->fifo_port) + { + case USB_HOST_CUSE: + g_usb1_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_CFIFO_USE; + break; + + case USB_HOST_D0USE: + g_usb1_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D0FIFO_USE; + break; + + case USB_HOST_D1USE: + g_usb1_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D1FIFO_USE; + break; + + case USB_HOST_D0DMA: + g_usb1_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D0FIFO_DMA; + break; + + case USB_HOST_D1DMA: + g_usb1_host_PipeTbl[pipe_number] = (uint16_t)USB_HOST_D1FIFO_DMA; + break; + + default: + ret_flag = USB_END_POINT_ERROR; + break; + } + + if (ret_flag == USB_END_POINT_ERROR) + { + return ret_flag; + } + + /* Endpoint number set */ + PipeCfg |= (uint16_t)(Table[2] & USB_HOST_EP_NUM_MASK); + g_usb1_host_PipeTbl[pipe_number] |= (uint16_t)(Table[2] & USB_HOST_EP_NUM_MASK); + + /* Max packet size set */ + PipeMaxp = (uint16_t)((uint16_t)Table[4] | (uint16_t)((uint16_t)Table[5] << 8)); + + if (PipeMaxp == 0u) + { + return USB_END_POINT_ERROR; + } + + /* Set device address */ + PipeMaxp |= (uint16_t)(devadr << 12); + + user_table->pipe_cfg = PipeCfg; + user_table->pipe_max_pktsize = PipeMaxp; + + usb1_host_resetEP(user_table); + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_host_resetEP +* Description : Sets the end point on the information specified by the argument. +* Arguments : USB_HOST_CFG_PIPETBL_t *tbl : pipe table +* Return Value : none +*******************************************************************************/ +static void usb1_host_resetEP (USB_HOST_CFG_PIPETBL_t * tbl) +{ + + uint16_t pipe; + + /* Host pipe */ + /* The pipe number of pipe definition table is obtained */ + pipe = (uint16_t)(tbl->pipe_number & USB_HOST_BITCURPIPE); /* Pipe Number */ + + /* FIFO port access pipe is set to initial value */ + /* The connection with FIFO should be cut before setting the pipe */ + if (RZA_IO_RegRead_16(&USB201.CFIFOSEL, + USB_CFIFOSEL_CURPIPE_SHIFT, + USB_CFIFOSEL_CURPIPE) == pipe) + { + usb1_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_CUSE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + if (RZA_IO_RegRead_16(&USB201.D0FIFOSEL, + USB_DnFIFOSEL_CURPIPE_SHIFT, + USB_DnFIFOSEL_CURPIPE) == pipe) + { + usb1_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_D0USE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + if (RZA_IO_RegRead_16(&USB201.D1FIFOSEL, + USB_DnFIFOSEL_CURPIPE_SHIFT, + USB_DnFIFOSEL_CURPIPE) == pipe) + { + usb1_host_change_fifo_port(USB_HOST_PIPE0, USB_HOST_D1USE, USB_HOST_NO, USB_HOST_BITMBW_16); + } + + /* Interrupt of pipe set is disabled */ + usb1_host_disable_brdy_int(pipe); + usb1_host_disable_nrdy_int(pipe); + usb1_host_disable_bemp_int(pipe); + + /* Pipe to set is set to NAK */ + usb1_host_set_pid_nak(pipe); + + /* Pipe is set */ + USB201.PIPESEL = pipe; + + USB201.PIPECFG = tbl->pipe_cfg; + USB201.PIPEBUF = tbl->pipe_buf; + USB201.PIPEMAXP = tbl->pipe_max_pktsize; + USB201.PIPEPERI = tbl->pipe_cycle; + + g_usb1_host_pipecfg[pipe] = tbl->pipe_cfg; + g_usb1_host_pipebuf[pipe] = tbl->pipe_buf; + g_usb1_host_pipemaxp[pipe] = tbl->pipe_max_pktsize; + g_usb1_host_pipeperi[pipe] = tbl->pipe_cycle; + + /* Sequence bit clear */ + usb1_host_set_sqclr(pipe); + + usb1_host_aclrm(pipe); + usb1_host_set_csclr(pipe); + + /* Pipe window selection is set to unused */ + USB201.PIPESEL = USB_HOST_PIPE0; + +} + +#if(1) /* ohci_wrapp */ +#else +/******************************************************************************* +* Function Name: usb1_api_host_data_count +* Description : Get g_usb0_host_data_count[pipe] +* Arguments : uint16_t pipe ; Pipe Number +* : uint32_t *data_count ; return g_usb0_data_count[pipe] +* Return Value : DEVDRV_SUCCESS ; success +* : DEVDRV_ERROR ; error +*******************************************************************************/ +int32_t usb1_api_host_data_count (uint16_t pipe, uint32_t * data_count) +{ + if (pipe > USB_HOST_MAX_PIPE_NO) + { + return DEVDRV_ERROR; + } + + *data_count = g_usb1_host_PipeDataSize[pipe]; + + return DEVDRV_SUCCESS; +} +#endif + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/src/host/usb1_host_global.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,137 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_global.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +const uint16_t g_usb1_host_bit_set[16] = +{ + 0x0001, 0x0002, 0x0004, 0x0008, + 0x0010, 0x0020, 0x0040, 0x0080, + 0x0100, 0x0200, 0x0400, 0x0800, + 0x1000, 0x2000, 0x4000, 0x8000 +}; + +uint32_t g_usb1_host_data_count[USB_HOST_MAX_PIPE_NO + 1]; +uint8_t * g_usb1_host_data_pointer[USB_HOST_MAX_PIPE_NO + 1]; + +uint16_t g_usb1_host_PipeIgnore[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb1_host_PipeTbl[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb1_host_pipe_status[USB_HOST_MAX_PIPE_NO + 1]; +uint32_t g_usb1_host_PipeDataSize[USB_HOST_MAX_PIPE_NO + 1]; + +USB_HOST_DMA_t g_usb1_host_DmaInfo[2]; + +uint16_t g_usb1_host_DmaPipe[2]; +uint16_t g_usb1_host_DmaBval[2]; +uint16_t g_usb1_host_DmaStatus[2]; + +uint16_t g_usb1_host_driver_state; +uint16_t g_usb1_host_ConfigNum; +uint16_t g_usb1_host_CmdStage; +uint16_t g_usb1_host_bchg_flag; +uint16_t g_usb1_host_detach_flag; +uint16_t g_usb1_host_attach_flag; + +uint16_t g_usb1_host_UsbAddress; +uint16_t g_usb1_host_setUsbAddress; +uint16_t g_usb1_host_default_max_packet[USB_HOST_MAX_DEVICE + 1]; +uint16_t g_usb1_host_UsbDeviceSpeed; +uint16_t g_usb1_host_SupportUsbDeviceSpeed; + +uint16_t g_usb1_host_SavReq; +uint16_t g_usb1_host_SavVal; +uint16_t g_usb1_host_SavIndx; +uint16_t g_usb1_host_SavLen; + +uint16_t g_usb1_host_pipecfg[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb1_host_pipebuf[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb1_host_pipemaxp[USB_HOST_MAX_PIPE_NO + 1]; +uint16_t g_usb1_host_pipeperi[USB_HOST_MAX_PIPE_NO + 1]; + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_init_pipe_status +* Description : Initialize pipe status. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_init_pipe_status (void) +{ + uint16_t loop; + + g_usb1_host_ConfigNum = 0; + + for (loop = 0; loop < (USB_HOST_MAX_PIPE_NO + 1); ++loop) + { + g_usb1_host_pipe_status[loop] = USB_HOST_PIPE_IDLE; + g_usb1_host_PipeDataSize[loop] = 0; + + /* pipe configuration in usb1_host_resetEP() */ + g_usb1_host_pipecfg[loop] = 0; + g_usb1_host_pipebuf[loop] = 0; + g_usb1_host_pipemaxp[loop] = 0; + g_usb1_host_pipeperi[loop] = 0; + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/src/host/usb1_host_usbint.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,497 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_usbint.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#if(1) /* ohci_wrapp */ +#include "ohci_wrapp_RZ_A1_local.h" +#endif + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb1_host_interrupt1(void); +static void usb1_host_BRDYInterrupt(uint16_t Status, uint16_t Int_enbl); +static void usb1_host_NRDYInterrupt(uint16_t Status, uint16_t Int_enbl); +static void usb1_host_BEMPInterrupt(uint16_t Status, uint16_t Int_enbl); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_interrupt +* Description : Executes USB interrupt. +* : Register this function in the USB interrupt handler. +* : Set CFIF0 in the pipe set before the interrupt after executing +* : this function. +* Arguments : uint32_t int_sense ; Interrupts detection mode +* : ; INTC_LEVEL_SENSITIVE : Level sense +* : ; INTC_EDGE_TRIGGER : Edge trigger +* Return Value : none +*******************************************************************************/ +void usb1_host_interrupt (uint32_t int_sense) +{ + uint16_t savepipe1; + uint16_t savepipe2; + uint16_t buffer; + + savepipe1 = USB201.CFIFOSEL; + savepipe2 = USB201.PIPESEL; + usb1_host_interrupt1(); + + /* Control transmission changes ISEL within interruption processing. */ + /* For this reason, write return of ISEL cannot be performed. */ + buffer = USB201.CFIFOSEL; + buffer &= (uint16_t)~(USB_HOST_BITCURPIPE); + buffer |= (uint16_t)(savepipe1 & USB_HOST_BITCURPIPE); + USB201.CFIFOSEL = buffer; + USB201.PIPESEL = savepipe2; +} + +/******************************************************************************* +* Function Name: usb1_host_interrupt1 +* Description : Execue the USB interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_interrupt1 (void) +{ + uint16_t intsts0; + uint16_t intsts1; + uint16_t intenb0; + uint16_t intenb1; + uint16_t brdysts; + uint16_t nrdysts; + uint16_t bempsts; + uint16_t brdyenb; + uint16_t nrdyenb; + uint16_t bempenb; + volatile uint16_t dumy_sts; + + intsts0 = USB201.INTSTS0; + intsts1 = USB201.INTSTS1; + intenb0 = USB201.INTENB0; + intenb1 = USB201.INTENB1; + + if ((intsts1 & USB_HOST_BITBCHG) && (intenb1 & USB_HOST_BITBCHGE)) + { + USB201.INTSTS1 = (uint16_t)~USB_HOST_BITBCHG; + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); + g_usb1_host_bchg_flag = USB_HOST_YES; + } + else if ((intsts1 & USB_HOST_BITSACK) && (intenb1 & USB_HOST_BITSACKE)) + { + USB201.INTSTS1 = (uint16_t)~USB_HOST_BITSACK; +#if(1) /* ohci_wrapp */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); +#else + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; +#endif + } + else if ((intsts1 & USB_HOST_BITSIGN) && (intenb1 & USB_HOST_BITSIGNE)) + { + USB201.INTSTS1 = (uint16_t)~USB_HOST_BITSIGN; +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; /* exit NORES */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#else + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_NORES; +#endif + } + else if (((intsts1 & USB_HOST_BITDTCH) == USB_HOST_BITDTCH) + && ((intenb1 & USB_HOST_BITDTCHE) == USB_HOST_BITDTCHE)) + { + USB201.INTSTS1 = (uint16_t)~USB_HOST_BITDTCH; + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); + g_usb1_host_detach_flag = USB_HOST_YES; + + Userdef_USB_usb1_host_detach(); + + usb1_host_UsbDetach2(); + } + else if (((intsts1 & USB_HOST_BITATTCH) == USB_HOST_BITATTCH) + && ((intenb1 & USB_HOST_BITATTCHE) == USB_HOST_BITATTCHE)) + { + USB201.INTSTS1 = (uint16_t)~USB_HOST_BITATTCH; + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); + g_usb1_host_attach_flag = USB_HOST_YES; + + Userdef_USB_usb1_host_attach(); + + usb1_host_UsbAttach(); + } + else if ((intsts0 & intenb0 & (USB_HOST_BITBEMP | USB_HOST_BITNRDY | USB_HOST_BITBRDY))) + { + brdysts = USB201.BRDYSTS; + nrdysts = USB201.NRDYSTS; + bempsts = USB201.BEMPSTS; + brdyenb = USB201.BRDYENB; + nrdyenb = USB201.NRDYENB; + bempenb = USB201.BEMPENB; + + if ((intsts0 & USB_HOST_BITBRDY) && (intenb0 & USB_HOST_BITBRDYE) && (brdysts & brdyenb)) + { + usb1_host_BRDYInterrupt(brdysts, brdyenb); + } + else if ((intsts0 & USB_HOST_BITBEMP) && (intenb0 & USB_HOST_BITBEMPE) && (bempsts & bempenb)) + { + usb1_host_BEMPInterrupt(bempsts, bempenb); + } + else if ((intsts0 & USB_HOST_BITNRDY) && (intenb0 & USB_HOST_BITNRDYE) && (nrdysts & nrdyenb)) + { + usb1_host_NRDYInterrupt(nrdysts, nrdyenb); + } + else + { + /* Do Nothing */ + } + } + else + { + /* Do Nothing */ + } + + /* Three dummy read for clearing interrupt requests */ + dumy_sts = USB201.INTSTS0; + dumy_sts = USB201.INTSTS1; + +} + +/******************************************************************************* +* Function Name: usb1_host_BRDYInterrupt +* Description : Executes USB BRDY interrupt. +* Arguments : uint16_t Status ; BRDYSTS Register Value +* : uint16_t Int_enbl ; BRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_BRDYInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t buffer; + volatile uint16_t dumy_sts; + + if ((Status & g_usb1_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb1_host_bit_set[USB_HOST_PIPE0])) + { + USB201.BRDYSTS = (uint16_t)~g_usb1_host_bit_set[USB_HOST_PIPE0]; + +#if(1) /* ohci_wrapp */ + switch ((g_usb1_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + buffer = usb1_host_read_buffer_c(USB_HOST_PIPE0); + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb1_host_read_buffer_c(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_READOVER: /* buffer over */ + USB201.CFIFOCTR = USB_HOST_BITBCLR; + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + break; + } +#else + switch ((g_usb1_host_CmdStage & (USB_HOST_MODE_FIELD | USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + case (USB_HOST_MODE_NO_DATA | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + buffer = usb1_host_read_buffer_c(USB_HOST_PIPE0); + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case (USB_HOST_MODE_READ | USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb1_host_read_buffer_c(USB_HOST_PIPE0); + + switch (buffer) + { + case USB_HOST_READING: /* Continue of data read */ + break; + + case USB_HOST_READEND: /* End of data read */ + case USB_HOST_READSHRT: /* End of data read */ + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case USB_HOST_READOVER: /* buffer over */ + USB201.CFIFOCTR = USB_HOST_BITBCLR; + usb1_host_disable_brdy_int(USB_HOST_PIPE0); + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + break; + } +#endif + } + else + { + usb1_host_brdy_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB201.BRDYSTS; +} + +/******************************************************************************* +* Function Name: usb1_host_NRDYInterrupt +* Description : Executes USB NRDY interrupt. +* Arguments : uint16_t Status ; NRDYSTS Register Value +* : uint16_t Int_enbl ; NRDYENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_NRDYInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t pid; + volatile uint16_t dumy_sts; + + if ((Status & g_usb1_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb1_host_bit_set[USB_HOST_PIPE0])) + { + USB201.NRDYSTS = (uint16_t)~g_usb1_host_bit_set[USB_HOST_PIPE0]; + pid = usb1_host_get_pid(USB_HOST_PIPE0); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_STALL; +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + + } + else if (pid == USB_HOST_PID_NAK) + { + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_NORES; +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_NORES; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + } + else + { + /* Do Nothing */ + } + } + else + { + usb1_host_nrdy_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB201.NRDYSTS; +} + +/******************************************************************************* +* Function Name: usb1_host_BEMPInterrupt +* Description : Executes USB BEMP interrupt. +* Arguments : uint16_t Status ; BEMPSTS Register Value +* : uint16_t Int_enbl ; BEMPENB Register Value +* Return Value : none +*******************************************************************************/ +void usb1_host_BEMPInterrupt (uint16_t Status, uint16_t Int_enbl) +{ + uint16_t buffer; + uint16_t pid; + volatile uint16_t dumy_sts; + + if ((Status & g_usb1_host_bit_set[USB_HOST_PIPE0]) && (Int_enbl & g_usb1_host_bit_set[USB_HOST_PIPE0])) + { + USB201.BEMPSTS = (uint16_t)~g_usb1_host_bit_set[USB_HOST_PIPE0]; + pid = usb1_host_get_pid(USB_HOST_PIPE0); + + if ((pid == USB_HOST_PID_STALL) || (pid == USB_HOST_PID_STALL2)) + { + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_STALL; +#if(1) /* ohci_wrapp */ + g_usb1_host_pipe_status[USB_HOST_PIPE0] = USB_HOST_PIPE_STALL; /* exit STALL */ + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_STALL); +#endif + } + else + { +#if(1) /* ohci_wrapp */ + switch ((g_usb1_host_CmdStage & (USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case (USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb1_host_write_buffer(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_WRITING: /* Continue of data write */ + case USB_HOST_WRITEEND: /* End of data write (zero-length) */ + break; + + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_STATUS; + ohciwrapp_loc_TransEnd(USB_HOST_PIPE0, TD_CC_NOERROR); + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + default: + /* do nothing */ + break; + } +#else + switch ((g_usb1_host_CmdStage & (USB_HOST_MODE_FIELD | USB_HOST_STAGE_FIELD | USB_HOST_CMD_FIELD))) + { + case (USB_HOST_MODE_READ | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_DONE; + break; + + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_DATA | USB_HOST_CMD_DOING): + buffer = usb1_host_write_buffer(USB_HOST_PIPE0); + switch (buffer) + { + case USB_HOST_WRITING: /* Continue of data write */ + case USB_HOST_WRITEEND: /* End of data write (zero-length) */ + break; + + case USB_HOST_WRITESHRT: /* End of data write */ + g_usb1_host_CmdStage &= (~USB_HOST_STAGE_FIELD); + g_usb1_host_CmdStage |= USB_HOST_STAGE_STATUS; + break; + + case USB_HOST_FIFOERROR: /* FIFO access error */ + default: + break; + } + break; + + case (USB_HOST_MODE_WRITE | USB_HOST_STAGE_STATUS | USB_HOST_CMD_DOING): + g_usb1_host_CmdStage &= (~USB_HOST_CMD_FIELD); + g_usb1_host_CmdStage |= USB_HOST_CMD_IDLE; + break; + + default: + /* do nothing */ + break; + } +#endif + } + } + else + { + usb1_host_bemp_int(Status, Int_enbl); + } + + /* Three dummy reads for clearing interrupt requests */ + dumy_sts = USB201.BEMPSTS; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/src/host/usb1_host_usbsig.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,637 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_usbsig.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "usb1_host.h" +#include "dev_drv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb1_host_EnableINT_Module(void); +static void usb1_host_Enable_AttachINT(void); +static void usb1_host_Disable_AttachINT(void); +static void usb1_host_Disable_BchgINT(void); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: usb1_host_InitModule +* Description : Initializes the USB module in USB host module. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_InitModule (void) +{ + uint16_t buf1; + uint16_t buf2; + uint16_t buf3; + + usb1_host_init_pipe_status(); + + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 1, + USB_SYSCFG_DCFM_SHIFT, + USB_SYSCFG_DCFM); /* HOST mode */ + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 1, + USB_SYSCFG_DRPD_SHIFT, + USB_SYSCFG_DRPD); /* PORT0 D+, D- setting */ + + do + { + buf1 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb1_host_delay_xms(50); + buf2 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb1_host_delay_xms(50); + buf3 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + + } while ((buf1 != buf2) || (buf1 != buf3)); + + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 1, + USB_SYSCFG_USBE_SHIFT, + USB_SYSCFG_USBE); + + USB201.CFIFOSEL = (uint16_t)(USB_HOST_BITRCNT | USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); + USB201.D0FIFOSEL = (uint16_t)( USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); + USB201.D1FIFOSEL = (uint16_t)( USB_HOST_BITMBW_8 | USB_HOST_BITBYTE_LITTLE); +} + +/******************************************************************************* +* Function Name: usb1_host_CheckAttach +* Description : Returns the USB device connection state. +* Arguments : none +* Return Value : uint16_t ; USB_HOST_ATTACH : Attached +* : ; USB_HOST_DETACH : not Attached +*******************************************************************************/ +uint16_t usb1_host_CheckAttach (void) +{ + uint16_t buf1; + uint16_t buf2; + uint16_t buf3; + uint16_t rhst; + + do + { + buf1 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb1_host_delay_xms(50); + buf2 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + Userdef_USB_usb1_host_delay_xms(50); + buf3 = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + + } while ((buf1 != buf2) || (buf1 != buf3)); + + rhst = RZA_IO_RegRead_16(&USB201.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (rhst == USB_HOST_UNDECID) + { + if (buf1 == USB_HOST_FS_JSTS) + { + if (g_usb1_host_SupportUsbDeviceSpeed == USB_HOST_HIGH_SPEED) + { + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 1, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + } + else + { + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + } + return USB_HOST_ATTACH; + } + else if (buf1 == USB_HOST_LS_JSTS) + { + /* Low Speed Device */ + RZA_IO_RegWrite_16(&USB201.SYSCFG0, + 0, + USB_SYSCFG_HSE_SHIFT, + USB_SYSCFG_HSE); + return USB_HOST_ATTACH; + } + else + { + /* Do Nothing */ + } + } + else if ((rhst == USB_HOST_HSMODE) || (rhst == USB_HOST_FSMODE)) + { + return USB_HOST_ATTACH; + } + else if (rhst == USB_HOST_LSMODE) + { + return USB_HOST_ATTACH; + } + else + { + /* Do Nothing */ + } + + return USB_HOST_DETACH; +} + +/******************************************************************************* +* Function Name: usb1_host_UsbAttach +* Description : Connects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_UsbAttach (void) +{ + usb1_host_EnableINT_Module(); + usb1_host_Disable_BchgINT(); + usb1_host_Disable_AttachINT(); + usb1_host_Enable_DetachINT(); +} + +/******************************************************************************* +* Function Name: usb1_host_UsbDetach +* Description : Disconnects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_UsbDetach (void) +{ + uint16_t pipe; + uint16_t devadr; + + g_usb1_host_driver_state = USB_HOST_DRV_DETACHED; + + /* Terminate all the pipes in which communications on port */ + /* are currently carried out */ + for (pipe = 0; pipe < (USB_HOST_MAX_PIPE_NO + 1); ++pipe) + { + if (g_usb1_host_pipe_status[pipe] != USB_HOST_PIPE_IDLE) + { + if (pipe == USB_HOST_PIPE0) + { + devadr = RZA_IO_RegRead_16(&USB201.DCPMAXP, + USB_DCPMAXP_DEVSEL_SHIFT, + USB_DCPMAXP_DEVSEL); + } + else + { + devadr = RZA_IO_RegRead_16(&g_usb1_host_pipemaxp[pipe], USB_PIPEMAXP_DEVSEL_SHIFT, USB_PIPEMAXP_DEVSEL); + } + + if (devadr == g_usb1_host_UsbAddress) + { + usb1_host_stop_transfer(pipe); + } + + g_usb1_host_pipe_status[pipe] = USB_HOST_PIPE_IDLE; + } + } + + g_usb1_host_ConfigNum = 0; + g_usb1_host_UsbAddress = 0; + g_usb1_host_default_max_packet[USB_HOST_DEVICE_0] = 64; + + usb1_host_UsbDetach2(); +} + +/******************************************************************************* +* Function Name: usb1_host_UsbDetach2 +* Description : Disconnects the USB device. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_UsbDetach2 (void) +{ + usb1_host_Disable_DetachINT(); + usb1_host_Disable_BchgINT(); + usb1_host_Enable_AttachINT(); +} + +/******************************************************************************* +* Function Name: usb1_host_UsbBusReset +* Description : Issues the USB bus reset signal. +* Arguments : none +* Return Value : uint16_t ; RHST +*******************************************************************************/ +uint16_t usb1_host_UsbBusReset (void) +{ + uint16_t buffer; + uint16_t loop; + + RZA_IO_RegWrite_16(&USB201.DVSTCTR0, + 1, + USB_DVSTCTR0_USBRST_SHIFT, + USB_DVSTCTR0_USBRST); + RZA_IO_RegWrite_16(&USB201.DVSTCTR0, + 0, + USB_DVSTCTR0_UACT_SHIFT, + USB_DVSTCTR0_UACT); + + Userdef_USB_usb1_host_delay_xms(50); + + buffer = USB201.DVSTCTR0; + buffer &= (uint16_t)(~(USB_HOST_BITRST)); + buffer |= USB_HOST_BITUACT; + USB201.DVSTCTR0 = buffer; + + Userdef_USB_usb1_host_delay_xms(20); + + for (loop = 0, buffer = USB_HOST_HSPROC; loop < 3; ++loop) + { + buffer = RZA_IO_RegRead_16(&USB201.DVSTCTR0, + USB_DVSTCTR0_RHST_SHIFT, + USB_DVSTCTR0_RHST); + if (buffer == USB_HOST_HSPROC) + { + Userdef_USB_usb1_host_delay_xms(10); + } + else + { + break; + } + } + + return buffer; +} + +/******************************************************************************* +* Function Name: usb1_host_UsbResume +* Description : Issues the USB resume signal. +* Arguments : none +* Return Value : int32_t ; DEVDRV_SUCCESS +* : ; DEVDRV_ERROR +*******************************************************************************/ +int32_t usb1_host_UsbResume (void) +{ + uint16_t buf; + + if ((g_usb1_host_driver_state & USB_HOST_DRV_SUSPEND) == 0) + { + /* not SUSPEND */ + return DEVDRV_ERROR; + } + + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); + RZA_IO_RegWrite_16(&USB201.DVSTCTR0, + 1, + USB_DVSTCTR0_RESUME_SHIFT, + USB_DVSTCTR0_RESUME); + Userdef_USB_usb1_host_delay_xms(20); + + buf = USB201.DVSTCTR0; + buf &= (uint16_t)(~(USB_HOST_BITRESUME)); + buf |= USB_HOST_BITUACT; + USB201.DVSTCTR0 = buf; + + g_usb1_host_driver_state &= (uint16_t)~USB_HOST_DRV_SUSPEND; + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb1_host_UsbSuspend +* Description : Issues the USB suspend signal. +* Arguments : none +* Return Value : int32_t ; DEVDRV_SUCCESS :not SUSPEND +* : ; DEVDRV_ERROR :SUSPEND +*******************************************************************************/ +int32_t usb1_host_UsbSuspend (void) +{ + uint16_t buf; + + if ((g_usb1_host_driver_state & USB_HOST_DRV_SUSPEND) != 0) + { + /* SUSPEND */ + return DEVDRV_ERROR; + } + + RZA_IO_RegWrite_16(&USB201.DVSTCTR0, + 0, + USB_DVSTCTR0_UACT_SHIFT, + USB_DVSTCTR0_UACT); + + Userdef_USB_usb1_host_delay_xms(5); + + buf = RZA_IO_RegRead_16(&USB201.SYSSTS0, + USB_SYSSTS0_LNST_SHIFT, + USB_SYSSTS0_LNST); + if ((buf != USB_HOST_FS_JSTS) && (buf != USB_HOST_LS_JSTS)) + { + usb1_host_UsbDetach(); + } + else + { + g_usb1_host_driver_state |= USB_HOST_DRV_SUSPEND; + } + + return DEVDRV_SUCCESS; +} + +/******************************************************************************* +* Function Name: usb1_host_Enable_DetachINT +* Description : Enables the USB disconnection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_Enable_DetachINT (void) +{ + USB201.INTSTS1 = (uint16_t)(~(USB_HOST_BITDTCH)); + RZA_IO_RegWrite_16(&USB201.INTENB1, + 1, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); +} + +/******************************************************************************* +* Function Name: usb1_host_Disable_DetachINT +* Description : Disables the USB disconnection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_Disable_DetachINT (void) +{ + USB201.INTSTS1 = (uint16_t)(~(USB_HOST_BITDTCH)); + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_DTCHE_SHIFT, + USB_INTENB1_DTCHE); +} + +/******************************************************************************* +* Function Name: usb1_host_Enable_AttachINT +* Description : Enables the USB connection detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_Enable_AttachINT (void) +{ + USB201.INTSTS1 = (uint16_t)(~(USB_HOST_BITATTCH)); + RZA_IO_RegWrite_16(&USB201.INTENB1, + 1, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); +} + +/******************************************************************************* +* Function Name: usb1_host_Disable_AttachINT +* Description : Disables the USB connection detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_Disable_AttachINT (void) +{ + USB201.INTSTS1 = (uint16_t)(~(USB_HOST_BITATTCH)); + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_ATTCHE_SHIFT, + USB_INTENB1_ATTCHE); +} + +/******************************************************************************* +* Function Name: usb1_host_Disable_BchgINT +* Description : Disables the USB bus change detection interrupt. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_Disable_BchgINT (void) +{ + USB201.INTSTS1 = (uint16_t)(~(USB_HOST_BITBCHG)); + RZA_IO_RegWrite_16(&USB201.INTENB1, + 0, + USB_INTENB1_BCHGE_SHIFT, + USB_INTENB1_BCHGE); +} + +/******************************************************************************* +* Function Name: usb1_host_set_devadd +* Description : DEVADDn register is set by specified value +* Arguments : uint16_t addr : Device address +* : uint16_t *devadd : Set value +* Return Value : none +*******************************************************************************/ +void usb1_host_set_devadd (uint16_t addr, uint16_t * devadd) +{ + uint16_t * ptr; + uint16_t ret_flag = DEVDRV_FLAG_ON; // avoid warning. + + switch (addr) + { + case USB_HOST_DEVICE_0: + ptr = (uint16_t *)&USB201.DEVADD0; + break; + + case USB_HOST_DEVICE_1: + ptr = (uint16_t *)&USB201.DEVADD1; + break; + + case USB_HOST_DEVICE_2: + ptr = (uint16_t *)&USB201.DEVADD2; + break; + + case USB_HOST_DEVICE_3: + ptr = (uint16_t *)&USB201.DEVADD3; + break; + + case USB_HOST_DEVICE_4: + ptr = (uint16_t *)&USB201.DEVADD4; + break; + + case USB_HOST_DEVICE_5: + ptr = (uint16_t *)&USB201.DEVADD5; + break; + + case USB_HOST_DEVICE_6: + ptr = (uint16_t *)&USB201.DEVADD6; + break; + + case USB_HOST_DEVICE_7: + ptr = (uint16_t *)&USB201.DEVADD7; + break; + + case USB_HOST_DEVICE_8: + ptr = (uint16_t *)&USB201.DEVADD8; + break; + + case USB_HOST_DEVICE_9: + ptr = (uint16_t *)&USB201.DEVADD9; + break; + + case USB_HOST_DEVICE_10: + ptr = (uint16_t *)&USB201.DEVADDA; + break; + + default: + ret_flag = DEVDRV_FLAG_OFF; + break; + } + + if (ret_flag == DEVDRV_FLAG_ON) + { + *ptr = (uint16_t)(*devadd & USB_HOST_DEVADD_MASK); + } +} + +/******************************************************************************* +* Function Name: usb1_host_get_devadd +* Description : DEVADDn register is obtained +* Arguments : uint16_t addr : Device address +* : uint16_t *devadd : USB_HOST_DEVADD register value +* Return Value : none +*******************************************************************************/ +void usb1_host_get_devadd (uint16_t addr, uint16_t * devadd) +{ + uint16_t * ptr; + uint16_t ret_flag = DEVDRV_FLAG_ON; // avoid warning. + + switch (addr) + { + case USB_HOST_DEVICE_0: + ptr = (uint16_t *)&USB201.DEVADD0; + break; + + case USB_HOST_DEVICE_1: + ptr = (uint16_t *)&USB201.DEVADD1; + break; + + case USB_HOST_DEVICE_2: + ptr = (uint16_t *)&USB201.DEVADD2; + break; + + case USB_HOST_DEVICE_3: + ptr = (uint16_t *)&USB201.DEVADD3; + break; + + case USB_HOST_DEVICE_4: + ptr = (uint16_t *)&USB201.DEVADD4; + break; + + case USB_HOST_DEVICE_5: + ptr = (uint16_t *)&USB201.DEVADD5; + break; + + case USB_HOST_DEVICE_6: + ptr = (uint16_t *)&USB201.DEVADD6; + break; + + case USB_HOST_DEVICE_7: + ptr = (uint16_t *)&USB201.DEVADD7; + break; + + case USB_HOST_DEVICE_8: + ptr = (uint16_t *)&USB201.DEVADD8; + break; + + case USB_HOST_DEVICE_9: + ptr = (uint16_t *)&USB201.DEVADD9; + break; + + case USB_HOST_DEVICE_10: + ptr = (uint16_t *)&USB201.DEVADDA; + break; + + default: + ret_flag = DEVDRV_FLAG_OFF; + break; + } + + if (ret_flag == DEVDRV_FLAG_ON) + { + *devadd = *ptr; + } +} + +/******************************************************************************* +* Function Name: usb1_host_EnableINT_Module +* Description : Enables BEMP/NRDY/BRDY interrupt and SIGN/SACK interrupt. +* : Enables NRDY/BEMP interrupt in the pipe0. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void usb1_host_EnableINT_Module (void) +{ + uint16_t buf; + + buf = USB201.INTENB0; + buf |= (USB_HOST_BITBEMPE | USB_HOST_BITNRDYE | USB_HOST_BITBRDYE); + USB201.INTENB0 = buf; + + buf = USB201.INTENB1; + buf |= (USB_HOST_BITSIGNE | USB_HOST_BITSACKE); + USB201.INTENB1 = buf; + + usb1_host_enable_nrdy_int(USB_HOST_PIPE0); + usb1_host_enable_bemp_int(USB_HOST_PIPE0); +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/src/userdef/usb1_host_dmacdrv.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,698 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_dmacdrv.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include "r_typedefs.h" +#include "iodefine.h" +#include "rza_io_regrw.h" +#include "usb1_host_dmacdrv.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define DMAC_INDEFINE (255) /* Macro definition when REQD bit is not used */ + +/* ==== Request setting information for on-chip peripheral module ==== */ +typedef enum dmac_peri_req_reg_type +{ + DMAC_REQ_MID, + DMAC_REQ_RID, + DMAC_REQ_AM, + DMAC_REQ_LVL, + DMAC_REQ_REQD +} dmac_peri_req_reg_type_t; + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ +/* ==== Prototype declaration ==== */ + +/* ==== Global variable ==== */ +/* On-chip peripheral module request setting table */ +static const uint8_t usb1_host_dmac_peri_req_init_table[8][5] = +{ + /* MID,RID, AM,LVL,REQD */ + { 32, 3, 2, 1, 1}, /* USB_0 channel 0 transmit FIFO empty */ + { 32, 3, 2, 1, 0}, /* USB_0 channel 0 receive FIFO full */ + { 33, 3, 2, 1, 1}, /* USB_0 channel 1 transmit FIFO empty */ + { 33, 3, 2, 1, 0}, /* USB_0 channel 1 receive FIFO full */ + { 34, 3, 2, 1, 1}, /* USB_1 channel 0 transmit FIFO empty */ + { 34, 3, 2, 1, 0}, /* USB_1 channel 0 receive FIFO full */ + { 35, 3, 2, 1, 1}, /* USB_1 channel 1 transmit FIFO empty */ + { 35, 3, 2, 1, 0}, /* USB_1 channel 1 receive FIFO full */ +}; + + +/******************************************************************************* +* Function Name: usb1_host_DMAC3_PeriReqInit +* Description : Sets the register mode for DMA mode and the on-chip peripheral +* : module request for transfer request for DMAC channel 3. +* : Executes DMAC initial setting using the DMA information +* : specified by the argument *trans_info and the enabled/disabled +* : continuous transfer specified by the argument continuation. +* : Registers DMAC channel 3 interrupt handler function and sets +* : the interrupt priority level. Then enables transfer completion +* : interrupt. +* Arguments : dmac_transinfo_t * trans_info : Setting information to DMAC +* : : register +* : uint32_t dmamode : DMA mode (only for DMAC_MODE_REGISTER) +* : uint32_t continuation : Set continuous transfer to be valid +* : : after DMA transfer has been completed +* : DMAC_SAMPLE_CONTINUATION : Execute continuous transfer +* : DMAC_SAMPLE_SINGLE : Do not execute continuous +* : : transfer +* : uint32_t request_factor : Factor for on-chip peripheral module +* : : request +* : DMAC_REQ_OSTM0TINT : OSTM_0 compare match +* : DMAC_REQ_OSTM1TINT : OSTM_1 compare match +* : DMAC_REQ_TGI0A : MTU2_0 input capture/compare match +* : : +* : uint32_t req_direction : Setting value of CHCFG_n register +* : : REQD bit +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC3_PeriReqInit (const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction) +{ + /* ==== Register mode ==== */ + if (DMAC_MODE_REGISTER == dmamode) + { + /* ==== Next0 register set ==== */ + DMAC3.N0SA_n = trans_info->src_addr; /* Start address of transfer source */ + DMAC3.N0DA_n = trans_info->dst_addr; /* Start address of transfer destination */ + DMAC3.N0TB_n = trans_info->count; /* Total transfer byte count */ + + /* DAD : Transfer destination address counting direction */ + /* SAD : Transfer source address counting direction */ + /* DDS : Transfer destination transfer size */ + /* SDS : Transfer source transfer size */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + trans_info->daddr_dir, + DMAC3_CHCFG_n_DAD_SHIFT, + DMAC3_CHCFG_n_DAD); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + trans_info->saddr_dir, + DMAC3_CHCFG_n_SAD_SHIFT, + DMAC3_CHCFG_n_SAD); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + trans_info->dst_size, + DMAC3_CHCFG_n_DDS_SHIFT, + DMAC3_CHCFG_n_DDS); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + trans_info->src_size, + DMAC3_CHCFG_n_SDS_SHIFT, + DMAC3_CHCFG_n_SDS); + + /* DMS : Register mode */ + /* RSEL : Select Next0 register set */ + /* SBE : No discharge of buffer data when aborted */ + /* DEM : No DMA interrupt mask */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_DMS_SHIFT, + DMAC3_CHCFG_n_DMS); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_RSEL_SHIFT, + DMAC3_CHCFG_n_RSEL); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_SBE_SHIFT, + DMAC3_CHCFG_n_SBE); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_DEM_SHIFT, + DMAC3_CHCFG_n_DEM); + + /* ---- Continuous transfer ---- */ + if (DMAC_SAMPLE_CONTINUATION == continuation) + { + /* REN : Execute continuous transfer */ + /* RSW : Change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 1, + DMAC3_CHCFG_n_REN_SHIFT, + DMAC3_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 1, + DMAC3_CHCFG_n_RSW_SHIFT, + DMAC3_CHCFG_n_RSW); + } + /* ---- Single transfer ---- */ + else + { + /* REN : Do not execute continuous transfer */ + /* RSW : Do not change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_REN_SHIFT, + DMAC3_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_RSW_SHIFT, + DMAC3_CHCFG_n_RSW); + } + + /* TM : Single transfer */ + /* SEL : Channel setting */ + /* HIEN, LOEN : On-chip peripheral module request */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_TM_SHIFT, + DMAC3_CHCFG_n_TM); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 3, + DMAC3_CHCFG_n_SEL_SHIFT, + DMAC3_CHCFG_n_SEL); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 1, + DMAC3_CHCFG_n_HIEN_SHIFT, + DMAC3_CHCFG_n_HIEN); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + 0, + DMAC3_CHCFG_n_LOEN_SHIFT, + DMAC3_CHCFG_n_LOEN); + + /* ---- Set factor by specified on-chip peripheral module request ---- */ + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_AM], + DMAC3_CHCFG_n_AM_SHIFT, + DMAC3_CHCFG_n_AM); + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_LVL], + DMAC3_CHCFG_n_LVL_SHIFT, + DMAC3_CHCFG_n_LVL); + if (usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD] != DMAC_INDEFINE) + { + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD], + DMAC3_CHCFG_n_REQD_SHIFT, + DMAC3_CHCFG_n_REQD); + } + else + { + RZA_IO_RegWrite_32(&DMAC3.CHCFG_n, + req_direction, + DMAC3_CHCFG_n_REQD_SHIFT, + DMAC3_CHCFG_n_REQD); + } + RZA_IO_RegWrite_32(&DMAC23.DMARS, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_RID], + DMAC23_DMARS_CH3_RID_SHIFT, + DMAC23_DMARS_CH3_RID); + RZA_IO_RegWrite_32(&DMAC23.DMARS, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_MID], + DMAC23_DMARS_CH3_MID_SHIFT, + DMAC23_DMARS_CH3_MID); + + /* PR : Round robin mode */ + RZA_IO_RegWrite_32(&DMAC07.DCTRL_0_7, + 1, + DMAC07_DCTRL_0_7_PR_SHIFT, + DMAC07_DCTRL_0_7_PR); + } +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC3_Open +* Description : Enables DMAC channel 3 transfer. +* Arguments : uint32_t req : DMAC request mode +* Return Value : 0 : Succeeded in enabling DMA transfer +* : -1 : Failed to enable DMA transfer (due to DMA operation) +*******************************************************************************/ +int32_t usb1_host_DMAC3_Open (uint32_t req) +{ + int32_t ret; + volatile uint8_t dummy; + + /* Transferable? */ + if ((0 == RZA_IO_RegRead_32(&DMAC3.CHSTAT_n, + DMAC3_CHSTAT_n_EN_SHIFT, + DMAC3_CHSTAT_n_EN)) && + (0 == RZA_IO_RegRead_32(&DMAC3.CHSTAT_n, + DMAC3_CHSTAT_n_TACT_SHIFT, + DMAC3_CHSTAT_n_TACT))) + { + /* Clear Channel Status Register */ + RZA_IO_RegWrite_32(&DMAC3.CHCTRL_n, + 1, + DMAC3_CHCTRL_n_SWRST_SHIFT, + DMAC3_CHCTRL_n_SWRST); + dummy = RZA_IO_RegRead_32(&DMAC3.CHCTRL_n, + DMAC3_CHCTRL_n_SWRST_SHIFT, + DMAC3_CHCTRL_n_SWRST); + /* Enable DMA transfer */ + RZA_IO_RegWrite_32(&DMAC3.CHCTRL_n, + 1, + DMAC3_CHCTRL_n_SETEN_SHIFT, + DMAC3_CHCTRL_n_SETEN); + + /* ---- Request by software ---- */ + if (DMAC_REQ_MODE_SOFT == req) + { + /* DMA transfer Request by software */ + RZA_IO_RegWrite_32(&DMAC3.CHCTRL_n, + 1, + DMAC3_CHCTRL_n_STG_SHIFT, + DMAC3_CHCTRL_n_STG); + } + + ret = 0; + } + else + { + ret = -1; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC3_Close +* Description : Aborts DMAC channel 3 transfer. Returns the remaining transfer +* : byte count at the time of DMA transfer abort to the argument +* : *remain. +* Arguments : uint32_t * remain : Remaining transfer byte count when +* : : DMA transfer is aborted +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC3_Close (uint32_t * remain) +{ + + /* ==== Abort transfer ==== */ + RZA_IO_RegWrite_32(&DMAC3.CHCTRL_n, + 1, + DMAC3_CHCTRL_n_CLREN_SHIFT, + DMAC3_CHCTRL_n_CLREN); + + while (1 == RZA_IO_RegRead_32(&DMAC3.CHSTAT_n, + DMAC3_CHSTAT_n_TACT_SHIFT, + DMAC3_CHSTAT_n_TACT)) + { + /* Loop until transfer is aborted */ + } + + while (1 == RZA_IO_RegRead_32(&DMAC3.CHSTAT_n, + DMAC3_CHSTAT_n_EN_SHIFT, + DMAC3_CHSTAT_n_EN)) + { + /* Loop until 0 is set in EN before checking the remaining transfer byte count */ + } + /* ==== Obtain remaining transfer byte count ==== */ + *remain = DMAC3.CRTB_n; +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC3_Load_Set +* Description : Sets the transfer source address, transfer destination +* : address, and total transfer byte count respectively +* : specified by the argument src_addr, dst_addr, and count to +* : DMAC channel 3 as DMA transfer information. +* : Sets the register set selected by the CHCFG_n register +* : RSEL bit from the Next0 or Next1 register set. +* : This function should be called when DMA transfer of DMAC +* : channel 3 is aboted. +* Arguments : uint32_t src_addr : Transfer source address +* : uint32_t dst_addr : Transfer destination address +* : uint32_t count : Total transfer byte count +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC3_Load_Set (uint32_t src_addr, uint32_t dst_addr, uint32_t count) +{ + uint8_t reg_set; + + /* Obtain register set in use */ + reg_set = RZA_IO_RegRead_32(&DMAC3.CHSTAT_n, + DMAC3_CHSTAT_n_SR_SHIFT, + DMAC3_CHSTAT_n_SR); + + /* ==== Load ==== */ + if (0 == reg_set) + { + /* ---- Next0 Register Set ---- */ + DMAC3.N0SA_n = src_addr; /* Start address of transfer source */ + DMAC3.N0DA_n = dst_addr; /* Start address of transfer destination */ + DMAC3.N0TB_n = count; /* Total transfer byte count */ + } + else + { + /* ---- Next1 Register Set ---- */ + DMAC3.N1SA_n = src_addr; /* Start address of transfer source */ + DMAC3.N1DA_n = dst_addr; /* Start address of transfer destination */ + DMAC3.N1TB_n = count; /* Total transfer byte count */ + } +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC4_PeriReqInit +* Description : Sets the register mode for DMA mode and the on-chip peripheral +* : module request for transfer request for DMAC channel 4. +* : Executes DMAC initial setting using the DMA information +* : specified by the argument *trans_info and the enabled/disabled +* : continuous transfer specified by the argument continuation. +* : Registers DMAC channel 4 interrupt handler function and sets +* : the interrupt priority level. Then enables transfer completion +* : interrupt. +* Arguments : dmac_transinfo_t * trans_info : Setting information to DMAC +* : : register +* : uint32_t dmamode : DMA mode (only for DMAC_MODE_REGISTER) +* : uint32_t continuation : Set continuous transfer to be valid +* : : after DMA transfer has been completed +* : DMAC_SAMPLE_CONTINUATION : Execute continuous transfer +* : DMAC_SAMPLE_SINGLE : Do not execute continuous +* : : transfer +* : uint32_t request_factor : Factor for on-chip peripheral module +* : : request +* : DMAC_REQ_OSTM0TINT : OSTM_0 compare match +* : DMAC_REQ_OSTM1TINT : OSTM_1 compare match +* : DMAC_REQ_TGI0A : MTU2_0 input capture/compare match +* : : +* : uint32_t req_direction : Setting value of CHCFG_n register +* : : REQD bit +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC4_PeriReqInit (const dmac_transinfo_t * trans_info, uint32_t dmamode, uint32_t continuation, + uint32_t request_factor, uint32_t req_direction) +{ + /* ==== Register mode ==== */ + if (DMAC_MODE_REGISTER == dmamode) + { + /* ==== Next0 register set ==== */ + DMAC4.N0SA_n = trans_info->src_addr; /* Start address of transfer source */ + DMAC4.N0DA_n = trans_info->dst_addr; /* Start address of transfer destination */ + DMAC4.N0TB_n = trans_info->count; /* Total transfer byte count */ + + /* DAD : Transfer destination address counting direction */ + /* SAD : Transfer source address counting direction */ + /* DDS : Transfer destination transfer size */ + /* SDS : Transfer source transfer size */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + trans_info->daddr_dir, + DMAC4_CHCFG_n_DAD_SHIFT, + DMAC4_CHCFG_n_DAD); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + trans_info->saddr_dir, + DMAC4_CHCFG_n_SAD_SHIFT, + DMAC4_CHCFG_n_SAD); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + trans_info->dst_size, + DMAC4_CHCFG_n_DDS_SHIFT, + DMAC4_CHCFG_n_DDS); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + trans_info->src_size, + DMAC4_CHCFG_n_SDS_SHIFT, + DMAC4_CHCFG_n_SDS); + + /* DMS : Register mode */ + /* RSEL : Select Next0 register set */ + /* SBE : No discharge of buffer data when aborted */ + /* DEM : No DMA interrupt mask */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_DMS_SHIFT, + DMAC4_CHCFG_n_DMS); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_RSEL_SHIFT, + DMAC4_CHCFG_n_RSEL); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_SBE_SHIFT, + DMAC4_CHCFG_n_SBE); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_DEM_SHIFT, + DMAC4_CHCFG_n_DEM); + + /* ---- Continuous transfer ---- */ + if (DMAC_SAMPLE_CONTINUATION == continuation) + { + /* REN : Execute continuous transfer */ + /* RSW : Change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 1, + DMAC4_CHCFG_n_REN_SHIFT, + DMAC4_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 1, + DMAC4_CHCFG_n_RSW_SHIFT, + DMAC4_CHCFG_n_RSW); + } + /* ---- Single transfer ---- */ + else + { + /* REN : Do not execute continuous transfer */ + /* RSW : Do not change register set when DMA transfer is completed. */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_REN_SHIFT, + DMAC4_CHCFG_n_REN); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_RSW_SHIFT, + DMAC4_CHCFG_n_RSW); + } + + /* TM : Single transfer */ + /* SEL : Channel setting */ + /* HIEN, LOEN : On-chip peripheral module request */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_TM_SHIFT, + DMAC4_CHCFG_n_TM); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 4, + DMAC4_CHCFG_n_SEL_SHIFT, + DMAC4_CHCFG_n_SEL); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 1, + DMAC4_CHCFG_n_HIEN_SHIFT, + DMAC4_CHCFG_n_HIEN); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + 0, + DMAC4_CHCFG_n_LOEN_SHIFT, + DMAC4_CHCFG_n_LOEN); + + /* ---- Set factor by specified on-chip peripheral module request ---- */ + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_AM], + DMAC4_CHCFG_n_AM_SHIFT, + DMAC4_CHCFG_n_AM); + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_LVL], + DMAC4_CHCFG_n_LVL_SHIFT, + DMAC4_CHCFG_n_LVL); + if (usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD] != DMAC_INDEFINE) + { + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_REQD], + DMAC4_CHCFG_n_REQD_SHIFT, + DMAC4_CHCFG_n_REQD); + } + else + { + RZA_IO_RegWrite_32(&DMAC4.CHCFG_n, + req_direction, + DMAC4_CHCFG_n_REQD_SHIFT, + DMAC4_CHCFG_n_REQD); + } + RZA_IO_RegWrite_32(&DMAC45.DMARS, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_RID], + DMAC45_DMARS_CH4_RID_SHIFT, + DMAC45_DMARS_CH4_RID); + RZA_IO_RegWrite_32(&DMAC45.DMARS, + usb1_host_dmac_peri_req_init_table[request_factor][DMAC_REQ_MID], + DMAC45_DMARS_CH4_MID_SHIFT, + DMAC45_DMARS_CH4_MID); + + /* PR : Round robin mode */ + RZA_IO_RegWrite_32(&DMAC07.DCTRL_0_7, + 1, + DMAC07_DCTRL_0_7_PR_SHIFT, + DMAC07_DCTRL_0_7_PR); + } +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC4_Open +* Description : Enables DMAC channel 4 transfer. +* Arguments : uint32_t req : DMAC request mode +* Return Value : 0 : Succeeded in enabling DMA transfer +* : -1 : Failed to enable DMA transfer (due to DMA operation) +*******************************************************************************/ +int32_t usb1_host_DMAC4_Open (uint32_t req) +{ + int32_t ret; + volatile uint8_t dummy; + + /* Transferable? */ + if ((0 == RZA_IO_RegRead_32(&DMAC4.CHSTAT_n, + DMAC4_CHSTAT_n_EN_SHIFT, + DMAC4_CHSTAT_n_EN)) && + (0 == RZA_IO_RegRead_32(&DMAC4.CHSTAT_n, + DMAC4_CHSTAT_n_TACT_SHIFT, + DMAC4_CHSTAT_n_TACT))) + { + /* Clear Channel Status Register */ + RZA_IO_RegWrite_32(&DMAC4.CHCTRL_n, + 1, + DMAC4_CHCTRL_n_SWRST_SHIFT, + DMAC4_CHCTRL_n_SWRST); + dummy = RZA_IO_RegRead_32(&DMAC4.CHCTRL_n, + DMAC4_CHCTRL_n_SWRST_SHIFT, + DMAC4_CHCTRL_n_SWRST); + /* Enable DMA transfer */ + RZA_IO_RegWrite_32(&DMAC4.CHCTRL_n, + 1, + DMAC4_CHCTRL_n_SETEN_SHIFT, + DMAC4_CHCTRL_n_SETEN); + + /* ---- Request by software ---- */ + if (DMAC_REQ_MODE_SOFT == req) + { + /* DMA transfer Request by software */ + RZA_IO_RegWrite_32(&DMAC4.CHCTRL_n, + 1, + DMAC4_CHCTRL_n_STG_SHIFT, + DMAC4_CHCTRL_n_STG); + } + + ret = 0; + } + else + { + ret = -1; + } + + return ret; +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC4_Close +* Description : Aborts DMAC channel 4 transfer. Returns the remaining transfer +* : byte count at the time of DMA transfer abort to the argument +* : *remain. +* Arguments : uint32_t * remain : Remaining transfer byte count when +* : : DMA transfer is aborted +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC4_Close (uint32_t * remain) +{ + + /* ==== Abort transfer ==== */ + RZA_IO_RegWrite_32(&DMAC4.CHCTRL_n, + 1, + DMAC4_CHCTRL_n_CLREN_SHIFT, + DMAC4_CHCTRL_n_CLREN); + + while (1 == RZA_IO_RegRead_32(&DMAC4.CHSTAT_n, + DMAC4_CHSTAT_n_TACT_SHIFT, + DMAC4_CHSTAT_n_TACT)) + { + /* Loop until transfer is aborted */ + } + + while (1 == RZA_IO_RegRead_32(&DMAC4.CHSTAT_n, + DMAC4_CHSTAT_n_EN_SHIFT, + DMAC4_CHSTAT_n_EN)) + { + /* Loop until 0 is set in EN before checking the remaining transfer byte count */ + } + /* ==== Obtain remaining transfer byte count ==== */ + *remain = DMAC4.CRTB_n; +} + +/******************************************************************************* +* Function Name: usb1_host_DMAC4_Load_Set +* Description : Sets the transfer source address, transfer destination +* : address, and total transfer byte count respectively +* : specified by the argument src_addr, dst_addr, and count to +* : DMAC channel 4 as DMA transfer information. +* : Sets the register set selected by the CHCFG_n register +* : RSEL bit from the Next0 or Next1 register set. +* : This function should be called when DMA transfer of DMAC +* : channel 4 is aboted. +* Arguments : uint32_t src_addr : Transfer source address +* : uint32_t dst_addr : Transfer destination address +* : uint32_t count : Total transfer byte count +* Return Value : none +*******************************************************************************/ +void usb1_host_DMAC4_Load_Set (uint32_t src_addr, uint32_t dst_addr, uint32_t count) +{ + uint8_t reg_set; + + /* Obtain register set in use */ + reg_set = RZA_IO_RegRead_32(&DMAC4.CHSTAT_n, + DMAC4_CHSTAT_n_SR_SHIFT, + DMAC4_CHSTAT_n_SR); + + /* ==== Load ==== */ + if (0 == reg_set) + { + /* ---- Next0 Register Set ---- */ + DMAC4.N0SA_n = src_addr; /* Start address of transfer source */ + DMAC4.N0DA_n = dst_addr; /* Start address of transfer destination */ + DMAC4.N0TB_n = count; /* Total transfer byte count */ + } + else + { + /* ---- Next1 Register Set ---- */ + DMAC4.N1SA_n = src_addr; /* Start address of transfer source */ + DMAC4.N1DA_n = dst_addr; /* Start address of transfer destination */ + DMAC4.N1TB_n = count; /* Total transfer byte count */ + } +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb1/src/userdef/usb1_host_userdef.c Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,778 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2012 - 2014 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ +/******************************************************************************* +* File Name : usb1_host_userdef.c +* $Rev: 1116 $ +* $Date:: 2014-07-09 16:29:19 +0900#$ +* Device(s) : RZ/A1H +* Tool-Chain : +* OS : None +* H/W Platform : +* Description : RZ/A1H R7S72100 USB Sample Program +* Operation : +* Limitations : +*******************************************************************************/ + + +/******************************************************************************* +Includes <System Includes> , "Project Includes" +*******************************************************************************/ +#include <stdio.h> +#include "cmsis_os.h" +#include "r_typedefs.h" +#include "iodefine.h" +#include "devdrv_usb_host_api.h" +#include "usb1_host.h" +#include "VKRZA1H.h" /* INTC Driver Header */ +#include "usb1_host_dmacdrv.h" +#include "ohci_wrapp_RZ_A1_local.h" + + +/******************************************************************************* +Typedef definitions +*******************************************************************************/ + + +/******************************************************************************* +Macro definitions +*******************************************************************************/ +#define DUMMY_ACCESS OSTM0CNT + +/* #define CACHE_WRITEBACK */ + + +/******************************************************************************* +Imported global variables and functions (from other files) +*******************************************************************************/ +extern int32_t io_cwb(unsigned long start, unsigned long end); + + +/******************************************************************************* +Exported global variables and functions (to be accessed by other files) +*******************************************************************************/ +static void usb1_host_enable_dmac0(uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc); +static void usb1_host_enable_dmac1(uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc); +static void Userdef_USB_usb1_host_delay_10us_2(void); + + +/******************************************************************************* +Private global variables and functions +*******************************************************************************/ + + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_d0fifo_dmaintid +* Description : get D0FIFO DMA Interrupt ID +* Arguments : none +* Return Value : D0FIFO DMA Interrupt ID +*******************************************************************************/ +uint16_t Userdef_USB_usb1_host_d0fifo_dmaintid (void) +{ +#if(1) /* ohci_wrapp */ + return 0xFFFF; +#else + return DMAINT1_IRQn; +#endif +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_d1fifo_dmaintid +* Description : get D1FIFO DMA Interrupt ID +* Arguments : none +* Return Value : D1FIFO DMA Interrupt ID +*******************************************************************************/ +uint16_t Userdef_USB_usb1_host_d1fifo_dmaintid (void) +{ +#if(1) /* ohci_wrapp */ + return 0xFFFF; +#else + return DMAINT2_IRQn; +#endif +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_attach +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_attach (void) +{ +// printf("\n"); +// printf("channel 1 attach device\n"); +// printf("\n"); + ohciwrapp_loc_Connect(1); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_detach +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_detach (void) +{ +// printf("\n"); +// printf("channel 1 detach device\n"); +// printf("\n"); + ohciwrapp_loc_Connect(0); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_delay_1ms +* Description : Wait for the software of 1ms. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_delay_1ms (void) +{ + osDelay(1); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_delay_xms +* Description : Wait for the software in the period of time specified by the +* : argument. +* : Alter this function according to the user's system. +* Arguments : uint32_t msec ; Wait Time (msec) +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_delay_xms (uint32_t msec) +{ + osDelay(msec); +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_delay_10us +* Description : Waits for software for the period specified by the argument. +* : Alter this function according to the user's system. +* Arguments : uint32_t usec ; Wait Time(x 10usec) +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_delay_10us (uint32_t usec) +{ + volatile int i; + + /* Wait 10us (Please change for your MCU) */ + for (i = 0; i < usec; ++i) + { + Userdef_USB_usb1_host_delay_10us_2(); + } +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_delay_10us_2 +* Description : Waits for software for the period specified by the argument. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +static void Userdef_USB_usb1_host_delay_10us_2 (void) +{ + volatile int i; + volatile unsigned long tmp; + + /* Wait 1us (Please change for your MCU) */ + for (i = 0; i < 14; ++i) + { + tmp = DUMMY_ACCESS; + } +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_delay_500ns +* Description : Wait for software for 500ns. +* : Alter this function according to the user's system. +* Arguments : none +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_delay_500ns (void) +{ + volatile int i; + volatile unsigned long tmp; + + /* Wait 500ns (Please change for your MCU) */ + /* Wait 500ns I clock 266MHz */ + tmp = DUMMY_ACCESS; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_start_dma +* Description : Enables DMA transfer on the information specified by the argument. +* : Set DMAC register by this function to enable DMA transfer. +* : After executing this function, USB module is set to start DMA +* : transfer. DMA transfer should not wait for DMA transfer complete. +* Arguments : USB_HOST_DMA_t *dma : DMA parameter +* : typedef struct{ +* : uint32_t fifo; FIFO for using +* : uint32_t buffer; Start address of transfer source/destination +* : uint32_t bytes; Transfer size(Byte) +* : uint32_t dir; Transfer direction(0:Buffer->FIFO, 1:FIFO->Buffer) +* : uint32_t size; DMA transfer size +* : } USB_HOST_DMA_t; +* : uint16_t dfacc ; 0 : cycle steal mode +* : 1 : 16byte continuous mode +* : 2 : 32byte continuous mode +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_start_dma (USB_HOST_DMA_t * dma, uint16_t dfacc) +{ + uint32_t trncount; + uint32_t src; + uint32_t dst; + uint32_t size; + uint32_t dir; +#ifdef CACHE_WRITEBACK + uint32_t ptr; +#endif + + trncount = dma->bytes; + dir = dma->dir; + + if (dir == USB_HOST_FIFO2BUF) + { + /* DxFIFO determination */ + dst = dma->buffer; +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB201.D1FIFO.UINT32); + } + size = dma->size; + + if (size == 0) + { + src += 3; /* byte access */ + } + else if (size == 1) + { + src += 2; /* short access */ + } + else + { + /* Do Nothing */ + } +#else + size = dma->size; + + if (size == 2) + { + /* 32bit access */ + if (dfacc == 2) + { + /* 32byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFOB0); + } + else + { + src = (uint32_t)(&USB201.D1FIFOB0); + } + } + else if (dfacc == 1) + { + /* 16byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFOB0); + } + else + { + src = (uint32_t)(&USB201.D1FIFOB0); + } + } + else + { + /* normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB201.D1FIFO.UINT32); + } + } + } + else if (size == 1) + { + /* 16bit access */ + dfacc = 0; /* force normal access */ + + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB201.D1FIFO.UINT32); + } + src += 2; /* short access */ + } + else + { + /* 8bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + src = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + src = (uint32_t)(&USB201.D1FIFO.UINT32); + } + src += 3; /* byte access */ + } +#endif + } + else + { + /* DxFIFO determination */ + src = dma->buffer; +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB201.D1FIFO.UINT32); + } + size = dma->size; + + if (size == 0) + { + dst += 3; /* byte access */ + } + else if (size == 1) + { + dst += 2; /* short access */ + } + else + { + /* Do Nothing */ + } +#else + size = dma->size; + if (size == 2) + { + /* 32bit access */ + if (dfacc == 2) + { + /* 32byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFOB0); + } + else + { + dst = (uint32_t)(&USB201.D1FIFOB0); + } + } + else if (dfacc == 1) + { + /* 16byte access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFOB0); + } + else + { + dst = (uint32_t)(&USB201.D1FIFOB0); + } + } + else + { + /* normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB201.D1FIFO.UINT32); + } + } + } + else if (size == 1) + { + /* 16bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB201.D1FIFO.UINT32); + } + dst += 2; /* short access */ + } + else + { + /* 8bit access */ + dfacc = 0; /* force normal access */ + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + dst = (uint32_t)(&USB201.D0FIFO.UINT32); + } + else + { + dst = (uint32_t)(&USB201.D1FIFO.UINT32); + } + dst += 3; /* byte access */ + } +#endif + } + +#ifdef CACHE_WRITEBACK + ptr = (uint32_t)dma->buffer; + if ((ptr & 0x20000000ul) == 0) + { + io_cwb((uint32_t)ptr,(uint32_t)(ptr)+trncount); + } +#endif + + if (dma->fifo == USB_HOST_D0FIFO_DMA) + { + usb1_host_enable_dmac0(src, dst, trncount, size, dir, dma->fifo, dfacc); + } + else + { + usb1_host_enable_dmac1(src, dst, trncount, size, dir, dma->fifo, dfacc); + } +} + +/******************************************************************************* +* Function Name: usb1_host_enable_dmac0 +* Description : Enables DMA transfer on the information specified by the argument. +* Arguments : uint32_t src : src address +* : uint32_t dst : dst address +* : uint32_t count : transfer byte +* : uint32_t size : transfer size +* : uint32_t dir : direction +* : uint32_t fifo : FIFO(D0FIFO or D1FIFO) +* : uint16_t dfacc : 0 : normal access +* : : 1 : 16byte access +* : : 2 : 32byte access +* Return Value : none +*******************************************************************************/ +static void usb1_host_enable_dmac0 (uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc) +{ + dmac_transinfo_t trans_info; + uint32_t request_factor = 0; + int32_t ret; + + /* ==== Variable setting for DMAC initialization ==== */ + trans_info.src_addr = (uint32_t)src; /* Start address of transfer source */ + trans_info.dst_addr = (uint32_t)dst; /* Start address of transfer destination */ + trans_info.count = (uint32_t)count; /* Total byte count to be transferred */ +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } +#else + if (dfacc == 2) + { + /* 32byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_256; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_256; /* Transfer destination transfer size */ + } + else if (dfacc == 1) + { + /* 16byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_128; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_128; /* Transfer destination transfer size */ + } + else + { + /* normal access */ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } + } +#endif + + if (dir == USB_HOST_FIFO2BUF) + { + request_factor = DMAC_REQ_USB1_DMA0_RX; /* USB_0 channel 0 receive FIFO full */ + trans_info.saddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer destination address */ + } + else if (dir == USB_HOST_BUF2FIFO) + { + request_factor = DMAC_REQ_USB1_DMA0_TX; /* USB_0 channel 0 receive FIFO empty */ + trans_info.saddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer destination address */ + } + else + { + /* Do Nothing */ + } + + /* ==== DMAC initialization ==== */ + usb1_host_DMAC3_PeriReqInit((const dmac_transinfo_t *)&trans_info, + DMAC_MODE_REGISTER, + DMAC_SAMPLE_SINGLE, + request_factor, + 0); /* Don't care DMAC_REQ_REQD is setting in usb1_host_DMAC3_PeriReqInit() */ + + /* ==== DMAC startup ==== */ + ret = usb1_host_DMAC3_Open(DMAC_REQ_MODE_PERI); + + if (ret != 0) + { +// printf("DMAC3 Open error!!\n"); + } + + return; +} + +/******************************************************************************* +* Function Name: usb1_host_enable_dmac1 +* Description : Enables DMA transfer on the information specified by the argument. +* Arguments : uint32_t src : src address +* : uint32_t dst : dst address +* : uint32_t count : transfer byte +* : uint32_t size : transfer size +* : uint32_t dir : direction +* : uint32_t fifo : FIFO(D0FIFO or D1FIFO) +* : uint16_t dfacc : 0 : normal access +* : : 1 : 16byte access +* : : 2 : 32byte access +* Return Value : none +*******************************************************************************/ +static void usb1_host_enable_dmac1 (uint32_t src, uint32_t dst, uint32_t count, + uint32_t size, uint32_t dir, uint32_t fifo, uint16_t dfacc) +{ + dmac_transinfo_t trans_info; + uint32_t request_factor = 0; + int32_t ret; + + /* ==== Variable setting for DMAC initialization ==== */ + trans_info.src_addr = (uint32_t)src; /* Start address of transfer source */ + trans_info.dst_addr = (uint32_t)dst; /* Start address of transfer destination */ + trans_info.count = (uint32_t)count; /* Total byte count to be transferred */ +#ifndef __USB_HOST_DF_ACC_ENABLE__ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } +#else + if (dfacc == 2) + { + /* 32byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_256; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_256; /* Transfer destination transfer size */ + } + else if (dfacc == 1) + { + /* 16byte access */ + trans_info.src_size = DMAC_TRANS_SIZE_128; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_128; /* Transfer destination transfer size */ + } + else + { + /* normal access */ + if (size == 0) + { + trans_info.src_size = DMAC_TRANS_SIZE_8; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_8; /* Transfer destination transfer size */ + } + else if (size == 1) + { + trans_info.src_size = DMAC_TRANS_SIZE_16; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_16; /* Transfer destination transfer size */ + } + else if (size == 2) + { + trans_info.src_size = DMAC_TRANS_SIZE_32; /* Transfer source transfer size */ + trans_info.dst_size = DMAC_TRANS_SIZE_32; /* Transfer destination transfer size */ + } + else + { +// printf("size error!!\n"); + } + } +#endif + + if (dir == USB_HOST_FIFO2BUF) + { + request_factor =DMAC_REQ_USB1_DMA1_RX; /* USB_0 channel 0 receive FIFO full */ + trans_info.saddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer destination address */ + } + else if (dir == USB_HOST_BUF2FIFO) + { + request_factor =DMAC_REQ_USB1_DMA1_TX; /* USB_0 channel 0 receive FIFO empty */ + trans_info.saddr_dir = DMAC_TRANS_ADR_INC; /* Count direction of transfer source address */ + trans_info.daddr_dir = DMAC_TRANS_ADR_NO_INC; /* Count direction of transfer destination address */ + } + else + { + /* Do Nothing */ + } + + /* ==== DMAC initialization ==== */ + usb1_host_DMAC4_PeriReqInit((const dmac_transinfo_t *)&trans_info, + DMAC_MODE_REGISTER, + DMAC_SAMPLE_SINGLE, + request_factor, + 0); /* Don't care DMAC_REQ_REQD is setting in usb1_host_DMAC4_PeriReqInit() */ + + /* ==== DMAC startup ==== */ + ret = usb1_host_DMAC4_Open(DMAC_REQ_MODE_PERI); + + if (ret != 0) + { +// printf("DMAC4 Open error!!\n"); + } + + return; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_stop_dma0 +* Description : Disables DMA transfer. +* Arguments : none +* Return Value : uint32_t return Transfer Counter register(DMATCRn) value +* : regarding to the bus width. +* Notice : This function should be executed to DMAC executed at the time +* : of specification of D0_FIF0_DMA in dma->fifo. +*******************************************************************************/ +uint32_t Userdef_USB_usb1_host_stop_dma0 (void) +{ + uint32_t remain; + + /* ==== DMAC release ==== */ + usb1_host_DMAC3_Close(&remain); + + return remain; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_stop_dma1 +* Description : Disables DMA transfer. +* : This function should be executed to DMAC executed at the time +* : of specification of D1_FIF0_DMA in dma->fifo. +* Arguments : none +* Return Value : uint32_t return Transfer Counter register(DMATCRn) value +* : regarding to the bus width. +*******************************************************************************/ +uint32_t Userdef_USB_usb1_host_stop_dma1 (void) +{ + uint32_t remain; + + /* ==== DMAC release ==== */ + usb1_host_DMAC4_Close(&remain); + + return remain; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_notice +* Description : Notice of USER +* Arguments : const char *format +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_notice (const char * format) +{ +// printf(format); + + return; +} + +/******************************************************************************* +* Function Name: Userdef_USB_usb1_host_user_rdy +* Description : This function notify a user and wait for trigger +* Arguments : const char *format +* : uint16_t data +* Return Value : none +*******************************************************************************/ +void Userdef_USB_usb1_host_user_rdy (const char * format, uint16_t data) +{ +// printf(format, data); + getchar(); + + return; +} + +/* End of File */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/TARGET_VK_RZ_A1H/usb_host_setting.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,100 @@ +/******************************************************************************* +* DISCLAIMER +* This software is supplied by Renesas Electronics Corporation and is only +* intended for use with Renesas products. No other uses are authorized. This +* software is owned by Renesas Electronics Corporation and is protected under +* all applicable laws, including copyright laws. +* THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING +* THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT +* LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE +* AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. +* TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS +* ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE +* FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR +* ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE +* BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. +* Renesas reserves the right, without notice, to make changes to this software +* and to discontinue the availability of this software. By using this software, +* you agree to the additional terms and conditions found by accessing the +* following link: +* http://www.renesas.com/disclaimer +* Copyright (C) 2014 - 2015 Renesas Electronics Corporation. All rights reserved. +*******************************************************************************/ + +#ifndef USB_HOST_SETTING_H +#define USB_HOST_SETTING_H + +#ifdef __cplusplus +extern "C" { +#endif + +#define USB_HOST_CH 0 +#define USB_HOST_HISPEED 1 + +#define INT_TRANS_MAX_NUM 4 /* min:1 max:4 */ +#define ISO_TRANS_MAX_NUM 0 /* min:0 max:2 */ + +#if (USB_HOST_CH == 0) +#include "usb0_host.h" +#define USB20X USB200 +#define USBIXUSBIX USBI0_IRQn +#define g_usbx_host_SupportUsbDeviceSpeed g_usb0_host_SupportUsbDeviceSpeed +#define g_usbx_host_UsbDeviceSpeed g_usb0_host_UsbDeviceSpeed +#define g_usbx_host_CmdStage g_usb0_host_CmdStage +#define g_usbx_host_pipe_status g_usb0_host_pipe_status +#define g_usbx_host_data_pointer g_usb0_host_data_pointer +#define g_usbx_host_data_count g_usb0_host_data_count +#define usbx_api_host_init usb0_api_host_init +#define usbx_host_UsbBusReset usb0_host_UsbBusReset +#define usbx_host_get_devadd usb0_host_get_devadd +#define usbx_host_set_devadd usb0_host_set_devadd +#define usbx_host_SetupStage usb0_host_SetupStage +#define usbx_host_CtrlWriteStart usb0_host_CtrlWriteStart +#define usbx_host_CtrlReadStart usb0_host_CtrlReadStart +#define usbx_api_host_SetEndpointTable usb0_api_host_SetEndpointTable +#define usbx_host_start_send_transfer usb0_host_start_send_transfer +#define usbx_host_start_receive_transfer usb0_host_start_receive_transfer +#define usbx_host_stop_transfer usb0_host_stop_transfer +#define usbx_host_set_sqclr usb0_host_set_sqclr +#define usbx_host_set_sqset usb0_host_set_sqset +#define usbx_host_CheckAttach usb0_host_CheckAttach +#define usbx_host_UsbDetach usb0_host_UsbDetach +#define usbx_host_UsbAttach usb0_host_UsbAttach +#define usbx_host_init_pipe_status usb0_host_init_pipe_status +#define usbx_host_get_sqmon usb0_host_get_sqmon +#else +#include "usb1_host.h" +#define USB20X USB201 +#define USBIXUSBIX USBI1_IRQn +#define g_usbx_host_SupportUsbDeviceSpeed g_usb1_host_SupportUsbDeviceSpeed +#define g_usbx_host_UsbDeviceSpeed g_usb1_host_UsbDeviceSpeed +#define g_usbx_host_CmdStage g_usb1_host_CmdStage +#define g_usbx_host_pipe_status g_usb1_host_pipe_status +#define g_usbx_host_data_pointer g_usb1_host_data_pointer +#define g_usbx_host_data_count g_usb1_host_data_count +#define usbx_api_host_init usb1_api_host_init +#define usbx_host_UsbBusReset usb1_host_UsbBusReset +#define usbx_host_get_devadd usb1_host_get_devadd +#define usbx_host_set_devadd usb1_host_set_devadd +#define usbx_host_SetupStage usb1_host_SetupStage +#define usbx_host_CtrlWriteStart usb1_host_CtrlWriteStart +#define usbx_host_CtrlReadStart usb1_host_CtrlReadStart +#define usbx_api_host_SetEndpointTable usb1_api_host_SetEndpointTable +#define usbx_host_start_send_transfer usb1_host_start_send_transfer +#define usbx_host_start_receive_transfer usb1_host_start_receive_transfer +#define usbx_host_stop_transfer usb1_host_stop_transfer +#define usbx_host_set_sqclr usb1_host_set_sqclr +#define usbx_host_set_sqset usb1_host_set_sqset +#define usbx_host_CheckAttach usb1_host_CheckAttach +#define usbx_host_UsbDetach usb1_host_UsbDetach +#define usbx_host_UsbAttach usb1_host_UsbAttach +#define usbx_host_init_pipe_status usb1_host_init_pipe_status +#define usbx_host_get_sqmon usb1_host_get_sqmon +#endif + + +#ifdef __cplusplus +} +#endif + +#endif /* USB_HOST_SETTING_H */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_RENESAS/USBHALHost_RZ_A1.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,282 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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(TARGET_RZ_A1H) || defined(TARGET_VK_RZ_A1H) + +#include "mbed.h" +#include "USBHALHost.h" +#include "dbg.h" + +#include "ohci_wrapp_RZ_A1.h" + + +#define HCCA_SIZE sizeof(HCCA) +#define ED_SIZE sizeof(HCED) +#define TD_SIZE sizeof(HCTD) + +#define TOTAL_SIZE (HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE) + (MAX_TD*TD_SIZE)) +#define ALIGNE_MSK (0x0000000F) + +static volatile uint8_t usb_buf[TOTAL_SIZE + ALIGNE_MSK]; //16 bytes aligned! + +USBHALHost * USBHALHost::instHost; + +USBHALHost::USBHALHost() { + instHost = this; + memInit(); + memset((void*)usb_hcca, 0, HCCA_SIZE); + for (int i = 0; i < MAX_ENDPOINT; i++) { + edBufAlloc[i] = false; + } + for (int i = 0; i < MAX_TD; i++) { + tdBufAlloc[i] = false; + } +} + +void USBHALHost::init() { + ohciwrapp_init(&_usbisr); + + ohciwrapp_reg_w(OHCI_REG_CONTROL, 1); // HARDWARE RESET + ohciwrapp_reg_w(OHCI_REG_CONTROLHEADED, 0); // Initialize Control list head to Zero + ohciwrapp_reg_w(OHCI_REG_BULKHEADED, 0); // Initialize Bulk list head to Zero + + // Wait 100 ms before apply reset + wait_ms(100); + + // software reset + ohciwrapp_reg_w(OHCI_REG_COMMANDSTATUS, OR_CMD_STATUS_HCR); + + // Write Fm Interval and Largest Data Packet Counter + ohciwrapp_reg_w(OHCI_REG_FMINTERVAL, DEFAULT_FMINTERVAL); + ohciwrapp_reg_w(OHCI_REG_PERIODICSTART, FI * 90 / 100); + + // Put HC in operational state + ohciwrapp_reg_w(OHCI_REG_CONTROL, (ohciwrapp_reg_r(OHCI_REG_CONTROL) & (~OR_CONTROL_HCFS)) | OR_CONTROL_HC_OPER); + // Set Global Power + ohciwrapp_reg_w(OHCI_REG_RHSTATUS, OR_RH_STATUS_LPSC); + + ohciwrapp_reg_w(OHCI_REG_HCCA, (uint32_t)(usb_hcca)); + + // Clear Interrrupt Status + ohciwrapp_reg_w(OHCI_REG_INTERRUPTSTATUS, ohciwrapp_reg_r(OHCI_REG_INTERRUPTSTATUS)); + + ohciwrapp_reg_w(OHCI_REG_INTERRUPTENABLE, OR_INTR_ENABLE_MIE | OR_INTR_ENABLE_WDH | OR_INTR_ENABLE_RHSC); + + // Enable the USB Interrupt + ohciwrapp_reg_w(OHCI_REG_RHPORTSTATUS1, OR_RH_PORT_CSC); + ohciwrapp_reg_w(OHCI_REG_RHPORTSTATUS1, OR_RH_PORT_PRSC); + + // Check for any connected devices + if (ohciwrapp_reg_r(OHCI_REG_RHPORTSTATUS1) & OR_RH_PORT_CCS) { + //Device connected + wait_ms(150); + USB_DBG("Device connected (%08x)\n\r", ohciwrapp_reg_r(OHCI_REG_RHPORTSTATUS1)); + deviceConnected(0, 1, ohciwrapp_reg_r(OHCI_REG_RHPORTSTATUS1) & OR_RH_PORT_LSDA); + } +} + +uint32_t USBHALHost::controlHeadED() { + return ohciwrapp_reg_r(OHCI_REG_CONTROLHEADED); +} + +uint32_t USBHALHost::bulkHeadED() { + return ohciwrapp_reg_r(OHCI_REG_BULKHEADED); +} + +uint32_t USBHALHost::interruptHeadED() { + return usb_hcca->IntTable[0]; +} + +void USBHALHost::updateBulkHeadED(uint32_t addr) { + ohciwrapp_reg_w(OHCI_REG_BULKHEADED, addr); +} + + +void USBHALHost::updateControlHeadED(uint32_t addr) { + ohciwrapp_reg_w(OHCI_REG_CONTROLHEADED, addr); +} + +void USBHALHost::updateInterruptHeadED(uint32_t addr) { + usb_hcca->IntTable[0] = addr; +} + + +void USBHALHost::enableList(ENDPOINT_TYPE type) { + uint32_t wk_data; + + switch(type) { + case CONTROL_ENDPOINT: + ohciwrapp_reg_w(OHCI_REG_COMMANDSTATUS, OR_CMD_STATUS_CLF); + wk_data = (ohciwrapp_reg_r(OHCI_REG_CONTROL) | OR_CONTROL_CLE); + ohciwrapp_reg_w(OHCI_REG_CONTROL, wk_data); + break; + case ISOCHRONOUS_ENDPOINT: + break; + case BULK_ENDPOINT: + ohciwrapp_reg_w(OHCI_REG_COMMANDSTATUS, OR_CMD_STATUS_BLF); + wk_data = (ohciwrapp_reg_r(OHCI_REG_CONTROL) | OR_CONTROL_BLE); + ohciwrapp_reg_w(OHCI_REG_CONTROL, wk_data); + break; + case INTERRUPT_ENDPOINT: + wk_data = (ohciwrapp_reg_r(OHCI_REG_CONTROL) | OR_CONTROL_PLE); + ohciwrapp_reg_w(OHCI_REG_CONTROL, wk_data); + break; + } +} + + +bool USBHALHost::disableList(ENDPOINT_TYPE type) { + uint32_t wk_data; + + switch(type) { + case CONTROL_ENDPOINT: + wk_data = ohciwrapp_reg_r(OHCI_REG_CONTROL); + if(wk_data & OR_CONTROL_CLE) { + wk_data &= ~OR_CONTROL_CLE; + ohciwrapp_reg_w(OHCI_REG_CONTROL, wk_data); + return true; + } + return false; + case ISOCHRONOUS_ENDPOINT: + return false; + case BULK_ENDPOINT: + wk_data = ohciwrapp_reg_r(OHCI_REG_CONTROL); + if(wk_data & OR_CONTROL_BLE) { + wk_data &= ~OR_CONTROL_BLE; + ohciwrapp_reg_w(OHCI_REG_CONTROL, wk_data); + return true; + } + return false; + case INTERRUPT_ENDPOINT: + wk_data = ohciwrapp_reg_r(OHCI_REG_CONTROL); + if(wk_data & OR_CONTROL_PLE) { + wk_data &= ~OR_CONTROL_PLE; + ohciwrapp_reg_w(OHCI_REG_CONTROL, wk_data); + return true; + } + return false; + } + return false; +} + + +void USBHALHost::memInit() { + volatile uint8_t *p_wk_buf = (uint8_t *)(((uint32_t)usb_buf + ALIGNE_MSK) & ~ALIGNE_MSK); + + usb_hcca = (volatile HCCA *)p_wk_buf; + usb_edBuf = (volatile uint8_t *)(p_wk_buf + HCCA_SIZE); + usb_tdBuf = (volatile uint8_t *)(p_wk_buf + HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE)); +} + +volatile uint8_t * USBHALHost::getED() { + for (int i = 0; i < MAX_ENDPOINT; i++) { + if ( !edBufAlloc[i] ) { + edBufAlloc[i] = true; + return (volatile uint8_t *)(usb_edBuf + i*ED_SIZE); + } + } + perror("Could not allocate ED\r\n"); + return NULL; //Could not alloc ED +} + +volatile uint8_t * USBHALHost::getTD() { + int i; + for (i = 0; i < MAX_TD; i++) { + if ( !tdBufAlloc[i] ) { + tdBufAlloc[i] = true; + return (volatile uint8_t *)(usb_tdBuf + i*TD_SIZE); + } + } + perror("Could not allocate TD\r\n"); + return NULL; //Could not alloc TD +} + + +void USBHALHost::freeED(volatile uint8_t * ed) { + int i; + i = (ed - usb_edBuf) / ED_SIZE; + edBufAlloc[i] = false; +} + +void USBHALHost::freeTD(volatile uint8_t * td) { + int i; + i = (td - usb_tdBuf) / TD_SIZE; + tdBufAlloc[i] = false; +} + + +void USBHALHost::resetRootHub() { + // Initiate port reset + ohciwrapp_reg_w(OHCI_REG_RHPORTSTATUS1, OR_RH_PORT_PRS); + + while (ohciwrapp_reg_r(OHCI_REG_RHPORTSTATUS1) & OR_RH_PORT_PRS); + + // ...and clear port reset signal + ohciwrapp_reg_w(OHCI_REG_RHPORTSTATUS1, OR_RH_PORT_PRSC); +} + + +void USBHALHost::_usbisr(void) { + if (instHost) { + instHost->UsbIrqhandler(); + } +} + +void USBHALHost::UsbIrqhandler() { + uint32_t int_status = ohciwrapp_reg_r(OHCI_REG_INTERRUPTSTATUS) & ohciwrapp_reg_r(OHCI_REG_INTERRUPTENABLE); + uint32_t data; + + if (int_status != 0) { //Is there something to actually process? + // Root hub status change interrupt + if (int_status & OR_INTR_STATUS_RHSC) { + if (ohciwrapp_reg_r(OHCI_REG_RHPORTSTATUS1) & OR_RH_PORT_CSC) { + if (ohciwrapp_reg_r(OHCI_REG_RHSTATUS) & OR_RH_STATUS_DRWE) { + // When DRWE is on, Connect Status Change + // means a remote wakeup event. + } else { + + //Root device connected + if (ohciwrapp_reg_r(OHCI_REG_RHPORTSTATUS1) & OR_RH_PORT_CCS) { + + // wait 150ms to avoid bounce + wait_ms(150); + + //Hub 0 (root hub), Port 1 (count starts at 1), Low or High speed + data = ohciwrapp_reg_r(OHCI_REG_RHPORTSTATUS1) & OR_RH_PORT_LSDA; + deviceConnected(0, 1, data); + } + + //Root device disconnected + else { + deviceDisconnected(0, 1, NULL, usb_hcca->DoneHead & 0xFFFFFFFE); + } + } + ohciwrapp_reg_w(OHCI_REG_RHPORTSTATUS1, OR_RH_PORT_CSC); + } + if (ohciwrapp_reg_r(OHCI_REG_RHPORTSTATUS1) & OR_RH_PORT_PRSC) { + ohciwrapp_reg_w(OHCI_REG_RHPORTSTATUS1, OR_RH_PORT_PRSC); + } + ohciwrapp_reg_w(OHCI_REG_INTERRUPTSTATUS, OR_INTR_STATUS_RHSC); + } + + // Writeback Done Head interrupt + if (int_status & OR_INTR_STATUS_WDH) { + transferCompleted(usb_hcca->DoneHead & 0xFFFFFFFE); + ohciwrapp_reg_w(OHCI_REG_INTERRUPTSTATUS, OR_INTR_STATUS_WDH); + } + } +} +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F2/TARGET_NUCLEO_F207ZG/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,19 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_STM_144_64pins.h" +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F4/TARGET_STM32F401xE/TARGET_NUCLEO_F401RE/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,20 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#define USBHALHOST_64pins +#include "USBHALHost_STM_144_64pins.h" +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F4/TARGET_STM32F411xE/TARGET_NUCLEO_F411RE/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,40 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +/* 144 pins boards */ +#if defined(TARGET_NUCLEO_F429ZI) || defined(TARGET_NUCLEO_F446ZE) || defined(TARGET_NUCLEO_F207ZG) \ +|| defined(TARGET_NUCLEO_F767ZI) || defined(TARGET_NUCLEO_F746ZG) || defined(TARGET_NUCLEO_F412ZG) \ +|| defined(TARGET_DISCO_F413ZH) +#include "USBHALHost_STM_144_64pins.h" +#endif + +/* 64 pins boards */ +#if defined(TARGET_NUCLEO_F401RE) || defined(TARGET_NUCLEO_L476RG) || defined(TARGET_NUCLEO_F411RE) +#define USBHALHOST_64pins +#include "USBHALHost_STM_144_64pins.h" +#endif + +/* DISCO board */ + +#ifdef TARGET_DISCO_F429ZI +#include "USBHALHost_DISCOF429ZI.h" +#endif + +#ifdef TARGET_DISCO_L476VG +#include "USBHALHost_DISCOL476VG.h" +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F4/TARGET_STM32F412xG/TARGET_NUCLEO_F412ZG/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,19 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_STM_144_64pins.h" +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F4/TARGET_STM32F429xI/TARGET_DISCO_F429ZI/USBHALHost_DISCOF429ZI.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,112 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBHALHOST_DISCOF429ZI +#define USBHALHOST_DISCOF429ZI + +#define USBHAL_IRQn OTG_HS_IRQn + +#define HCCA_SIZE sizeof(HCD_HandleTypeDef) +#define ED_SIZE sizeof(HCED) +#define TD_SIZE sizeof(HCTD) + +#define TOTAL_SIZE (HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE) + (MAX_TD*TD_SIZE)) +/* STM device FS have 11 channels (definition is for 60 channels) */ +static volatile uint8_t usb_buf[TOTAL_SIZE]; +typedef struct +{ + /* store the request ongoing on each endpoit */ + /* 1st field of structure avoid giving knowledge of all structure to + * endpoint */ + volatile uint32_t addr[MAX_ENDPOINT]; + USBHALHost *inst; + void (USBHALHost::*deviceConnected)(int hub, int port, bool lowSpeed, USBHostHub * hub_parent); + void (USBHALHost::*deviceDisconnected)(int hub, int port, USBHostHub * hub_parent, volatile uint32_t addr); + void (USBHALHost::*transferCompleted)(volatile uint32_t addr); +}USBHALHost_Private_t; +/* CONFIGURATION for USB_VBUS + * on 64 bits board PC_0 is used (0 VBUS on, 1 VBUS off) + * on 144 pins board PG_6 is used ( 1 VBUS on, 0 VBUS on) + */ +static gpio_t gpio_vbus; + +#define VBUS_OFF 1 +#define VBUS_ON 0 +#define USB_VBUS_CONFIG \ + do {__HAL_RCC_GPIOC_CLK_ENABLE();\ + gpio_init_out_ex(&gpio_vbus, PC_4, VBUS_OFF);\ + }while(0); + + +void usb_vbus( uint8_t state) +{ + if(state == 0) + { + gpio_write(&gpio_vbus, VBUS_OFF); + } + else + { + gpio_write(&gpio_vbus, VBUS_ON); + } + wait(0.2); +} + + +USBHALHost::USBHALHost() { + gpio_t pin_vbus; + instHost = this; + HCD_HandleTypeDef *hhcd; + USBHALHost_Private_t *HALPriv = new(USBHALHost_Private_t); + memset(HALPriv, 0, sizeof(USBHALHost_Private_t)); + memInit(); + memset((void*)usb_hcca, 0, HCCA_SIZE); + hhcd = (HCD_HandleTypeDef *)usb_hcca; + hhcd->Instance = USB_OTG_HS; + hhcd->pData = (void*)HALPriv; + hhcd->Init.Host_channels = 11; + /* for now failed with dma */ + hhcd->Init.dma_enable = 0; + hhcd->Init.speed = HCD_SPEED_HIGH; + hhcd->Init.phy_itface = HCD_PHY_EMBEDDED; + hhcd->Init.use_external_vbus = 1; + HALPriv->inst = this; + HALPriv->deviceConnected = &USBHALHost::deviceConnected; + HALPriv->deviceDisconnected = &USBHALHost::deviceDisconnected; + HALPriv->transferCompleted = &USBHALHost::transferCompleted; + for (int i = 0; i < MAX_ENDPOINT; i++) { + edBufAlloc[i] = false; + HALPriv->addr[i]=(uint32_t)-1; + } + for (int i = 0; i < MAX_TD; i++) { + tdBufAlloc[i] = false; + } + /* Configure USB HS GPIOs */ + __HAL_RCC_GPIOB_CLK_ENABLE(); + + /*USB DM and DP */ + pin_function(PB_14, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_NOPULL, GPIO_AF12_OTG_HS_FS)); + pin_function(PB_15, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_NOPULL, GPIO_AF12_OTG_HS_FS)); + /* Configure VBUS Pin */ + gpio_init_in(&pin_vbus, PB_13); + /* Configure POWER_SWITCH IO pin */ + USB_VBUS_CONFIG; + /* Enable USB HS Clocks */ + __HAL_RCC_USB_OTG_HS_CLK_ENABLE(); + + /* Set USBFS Interrupt priority */ + HAL_NVIC_SetPriority(USBHAL_IRQn, 5, 0); + NVIC_SetVector(USBHAL_IRQn, (uint32_t)&_usbisr); +} +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F4/TARGET_STM32F429xI/TARGET_DISCO_F429ZI/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,18 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_DISCOF429ZI.h"
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F4/TARGET_STM32F429xI/TARGET_NUCLEO_F429ZI/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,18 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_STM_144_64pins.h"
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F4/TARGET_STM32F439xI/TARGET_NUCLEO_F439ZI/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,18 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_STM_144_64pins.h"
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F4/TARGET_STM32F446xE/TARGET_NUCLEO_F446RE/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,18 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_STM_144_64pins.h"
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F4/TARGET_STM32F446xE/TARGET_NUCLEO_F446ZE/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,19 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_STM_144_64pins.h" +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F7/TARGET_STM32F746xG/TARGET_NUCLEO_F746ZG/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,18 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_STM_144_64pins.h"
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F7/TARGET_STM32F756xG/TARGET_NUCLEO_F756ZG/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,18 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_STM_144_64pins.h"
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32F7/TARGET_STM32F767xI/TARGET_NUCLEO_F767ZI/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,19 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_STM_144_64pins.h" +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32L4/TARGET_STM32L475xG/TARGET_DISCO_L475VG_IOT01A/USBHALHost_DISCO_L475VG_IOT01A.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,120 @@ +/* Copyright (c) 2017 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#ifndef USBHALHOST_DISCO_L475VG_IOT01A +#define USBHALHOST_DISCO_L475VG_IOT01A + +#define USBHAL_IRQn OTG_FS_IRQn + +#define HCCA_SIZE sizeof(HCD_HandleTypeDef) +#define ED_SIZE sizeof(HCED) +#define TD_SIZE sizeof(HCTD) + +#define TOTAL_SIZE (HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE) + (MAX_TD*TD_SIZE)) + +/* STM device FS have 11 channels (definition is for 60 channels) */ +static volatile uint8_t usb_buf[TOTAL_SIZE]; + +typedef struct { + /* store the request ongoing on each endpoit */ + /* 1st field of structure avoid giving knowledge of all structure to + * endpoint */ + volatile uint32_t addr[MAX_ENDPOINT]; + USBHALHost *inst; + void (USBHALHost::*deviceConnected)(int hub, int port, bool lowSpeed, USBHostHub * hub_parent); + void (USBHALHost::*deviceDisconnected)(int hub, int port, USBHostHub * hub_parent, volatile uint32_t addr); + void (USBHALHost::*transferCompleted)(volatile uint32_t addr); +} USBHALHost_Private_t; + +static gpio_t gpio_powerpin; + +#define USB_POWER_OFF 1 +#define USB_POWER_ON 0 +#define USB_POWERPIN_CONFIG {gpio_init_out_ex(&gpio_powerpin, PD_12, USB_POWER_OFF);} + + +void usb_vbus( uint8_t state) +{ + if (state == 0) { + gpio_write(&gpio_powerpin, USB_POWER_OFF); + } else { + gpio_write(&gpio_powerpin, USB_POWER_ON); + } + wait(0.2); +} + + +USBHALHost::USBHALHost() +{ + instHost = this; + HCD_HandleTypeDef *hhcd; + USBHALHost_Private_t *HALPriv = new(USBHALHost_Private_t); + + memset(HALPriv, 0, sizeof(USBHALHost_Private_t)); + memInit(); + memset((void*)usb_hcca, 0, HCCA_SIZE); + + hhcd = (HCD_HandleTypeDef *)usb_hcca; + hhcd->Instance = USB_OTG_FS; + hhcd->pData = (void*)HALPriv; + hhcd->Init.Host_channels = 11; + + /* for now failed with dma */ + hhcd->Init.dma_enable = 0; + hhcd->Init.speed = HCD_SPEED_FULL; + hhcd->Init.phy_itface = HCD_PHY_EMBEDDED; + hhcd->Init.use_external_vbus = 1; + + HALPriv->inst = this; + HALPriv->deviceConnected = &USBHALHost::deviceConnected; + HALPriv->deviceDisconnected = &USBHALHost::deviceDisconnected; + HALPriv->transferCompleted = &USBHALHost::transferCompleted; + + for (int i = 0; i < MAX_ENDPOINT; i++) { + edBufAlloc[i] = false; + HALPriv->addr[i]=(uint32_t)-1; + } + + for (int i = 0; i < MAX_TD; i++) { + tdBufAlloc[i] = false; + } + + __HAL_RCC_PWR_CLK_ENABLE(); + +#ifdef TARGET_STM32L4 + HAL_PWREx_EnableVddUSB(); +#endif + + /* Configure USB GPIOs */ + __HAL_RCC_GPIOA_CLK_ENABLE(); + pin_function(PA_11, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_NOPULL, GPIO_AF10_OTG_FS)); // DM pin + pin_function(PA_12, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_NOPULL, GPIO_AF10_OTG_FS)); // DP pin + pin_function(PA_9, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_NOPULL, GPIO_AF10_OTG_FS)); // VBUS pin + + /* Configure USB POWER pin */ + USB_POWERPIN_CONFIG; + + /* Enable USB FS Clocks */ + __HAL_RCC_SYSCFG_CLK_ENABLE(); + __HAL_RCC_USB_OTG_FS_CLK_ENABLE(); + + /* Set USBFS Interrupt priority */ + HAL_NVIC_SetPriority(USBHAL_IRQn, 5, 0); + NVIC_SetVector(USBHAL_IRQn, (uint32_t)&_usbisr); +} + +#endif // USBHALHOST_DISCO_L475VG_IOT01A
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32L4/TARGET_STM32L475xG/TARGET_DISCO_L475VG_IOT01A/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,18 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_DISCO_L475VG_IOT01A.h"
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32L4/TARGET_STM32L476xG/TARGET_DISCO_L476VG/USBHALHost_DISCOL476VG.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,118 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#ifndef USBHALHOST_DISCOL476VG +#define USBHALHOST_DISCOL476VG + +#define USBHAL_IRQn OTG_FS_IRQn + +#define HCCA_SIZE sizeof(HCD_HandleTypeDef) +#define ED_SIZE sizeof(HCED) +#define TD_SIZE sizeof(HCTD) + +#define TOTAL_SIZE (HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE) + (MAX_TD*TD_SIZE)) +/* STM device FS have 11 channels (definition is for 60 channels) */ +static volatile uint8_t usb_buf[TOTAL_SIZE]; +typedef struct +{ + /* store the request ongoing on each endpoit */ + /* 1st field of structure avoid giving knowledge of all structure to + * endpoint */ + volatile uint32_t addr[MAX_ENDPOINT]; + USBHALHost *inst; + void (USBHALHost::*deviceConnected)(int hub, int port, bool lowSpeed, USBHostHub * hub_parent); + void (USBHALHost::*deviceDisconnected)(int hub, int port, USBHostHub * hub_parent, volatile uint32_t addr); + void (USBHALHost::*transferCompleted)(volatile uint32_t addr); +}USBHALHost_Private_t; + +static gpio_t gpio_vbus; + +#define VBUS_OFF 1 +#define VBUS_ON 0 +#define USB_VBUS_CONFIG \ + do {\ + gpio_init_out_ex(&gpio_vbus, PC_9, VBUS_OFF);\ + }while(0); + + +void usb_vbus( uint8_t state) +{ + if(state == 0) + { + gpio_write(&gpio_vbus, VBUS_OFF); + } + else + { + gpio_write(&gpio_vbus, VBUS_ON); + } + wait(0.2); +} + + +USBHALHost::USBHALHost() { + instHost = this; + HCD_HandleTypeDef *hhcd; + USBHALHost_Private_t *HALPriv = new(USBHALHost_Private_t); + memset(HALPriv, 0, sizeof(USBHALHost_Private_t)); + memInit(); + memset((void*)usb_hcca, 0, HCCA_SIZE); + hhcd = (HCD_HandleTypeDef *)usb_hcca; + hhcd->Instance = USB_OTG_FS; + hhcd->pData = (void*)HALPriv; + hhcd->Init.Host_channels = 11; + /* for now failed with dma */ + hhcd->Init.dma_enable = 0; + hhcd->Init.speed = HCD_SPEED_FULL; + hhcd->Init.phy_itface = HCD_PHY_EMBEDDED; + hhcd->Init.use_external_vbus = 1; + HALPriv->inst = this; + HALPriv->deviceConnected = &USBHALHost::deviceConnected; + HALPriv->deviceDisconnected = &USBHALHost::deviceDisconnected; + HALPriv->transferCompleted = &USBHALHost::transferCompleted; + for (int i = 0; i < MAX_ENDPOINT; i++) { + edBufAlloc[i] = false; + HALPriv->addr[i]=(uint32_t)-1; + } + for (int i = 0; i < MAX_TD; i++) { + tdBufAlloc[i] = false; + } + __HAL_RCC_PWR_CLK_ENABLE(); +#ifdef TARGET_STM32L4 + HAL_PWREx_EnableVddUSB(); +#endif + + /* Configure USB HS GPIOs */ + __HAL_RCC_GPIOA_CLK_ENABLE(); + + /*USB DM and DP */ + pin_function(PA_11, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_NOPULL, GPIO_AF10_OTG_FS)); + pin_function(PA_12, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_NOPULL, GPIO_AF10_OTG_FS)); + + /* Configure VBUS Pin */ + __HAL_RCC_GPIOC_CLK_ENABLE(); + pin_function(PC_11, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_NOPULL, GPIO_AF10_OTG_FS)); + /* Configure POWER_SWITCH IO pin */ + USB_VBUS_CONFIG; + __HAL_RCC_SYSCFG_CLK_ENABLE(); + + /* Enable USB FS Clocks */ + __HAL_RCC_USB_OTG_FS_CLK_ENABLE(); + /* Set USBFS Interrupt priority */ + HAL_NVIC_SetPriority(USBHAL_IRQn, 5, 0); + NVIC_SetVector(USBHAL_IRQn, (uint32_t)&_usbisr); +} +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32L4/TARGET_STM32L476xG/TARGET_DISCO_L476VG/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,18 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#include "USBHALHost_DISCOL476VG.h"
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32L4/TARGET_STM32L476xG/TARGET_NUCLEO_L476RG/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,19 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#define USBHALHOST_64pins +#include "USBHALHost_STM_144_64pins.h"
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/TARGET_STM32L4/TARGET_STM32L486xG/TARGET_NUCLEO_L486RG/USBHALHost_STM_TARGET.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,19 @@ +/* Copyright (c) 2016 mbed.org, MIT License +* +* Permission is hereby granted, free of charge, to any person obtaining a copy of this software +* and associated documentation files (the "Software"), to deal in the Software without +* restriction, including without limitation the rights to use, copy, modify, merge, publish, +* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in all copies or +* substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING +* BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ +#define USBHALHOST_64pins +#include "USBHALHost_STM_144_64pins.h"
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/USBEndpoint_STM.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,182 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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(TARGET_STM) && defined(USBHOST_OTHER) + +#include "dbg.h" +#include "USBEndpoint.h" +extern uint32_t HAL_HCD_HC_GetMaxPacket(HCD_HandleTypeDef *hhcd, uint8_t chn_num); +extern uint32_t HAL_HCD_HC_GetType(HCD_HandleTypeDef *hhcd, uint8_t chn_num); +extern void HAL_HCD_DisableInt(HCD_HandleTypeDef* hhcd, uint8_t chn_num); +extern void HAL_HCD_EnableInt(HCD_HandleTypeDef* hhcd, uint8_t chn_num); + + + + +void USBEndpoint::init(HCED * hced_, ENDPOINT_TYPE type_, ENDPOINT_DIRECTION dir_, uint32_t size, uint8_t ep_number, HCTD* td_list_[2]) +{ + HCD_HandleTypeDef *hhcd; + uint32_t *addr; + + hced = hced_; + type = type_; + dir = dir_; + setup = (type == CONTROL_ENDPOINT) ? true : false; + + //TDs have been allocated by the host + memcpy((HCTD**)td_list, td_list_, sizeof(HCTD*)*2); //TODO: Maybe should add a param for td_list size... at least a define + memset(td_list_[0], 0, sizeof(HCTD)); + memset(td_list_[1], 0, sizeof(HCTD)); + + td_list[0]->ep = this; + td_list[1]->ep = this; + + address = (ep_number & 0x7F) | ((dir - 1) << 7); + this->size = size; + this->ep_number = ep_number; + transfer_len = 0; + transferred = 0; + buf_start = 0; + nextEp = NULL; + + td_current = td_list[0]; + td_next = td_list[1]; + /* remove potential post pending from previous endpoint */ + ep_queue.get(0); + intf_nb = 0; + hhcd = (HCD_HandleTypeDef*)hced->hhcd; + addr = &((uint32_t *)hhcd->pData)[hced->ch_num]; + *addr = 0; + state = USB_TYPE_IDLE; + speed =false; +} +void USBEndpoint::setSize(uint32_t size) +{ + this->size = size; +} + + +void USBEndpoint::setDeviceAddress(uint8_t addr) +{ + HCD_HandleTypeDef *hhcd; + uint8_t hcd_speed = HCD_SPEED_FULL; + /* fix me : small speed device with hub not supported + if (this->speed) hcd_speed = HCD_SPEED_LOW; */ + if (this->speed) { + USB_WARN("small speed device on hub not supported"); + } + MBED_ASSERT(HAL_HCD_HC_Init((HCD_HandleTypeDef*)hced->hhcd,hced->ch_num, address, addr, hcd_speed, type, size)!=HAL_BUSY); + this->device_address = addr; + +} + +void USBEndpoint::setSpeed(uint8_t speed) +{ + this->speed = speed; +} + + + +void USBEndpoint::setState(USB_TYPE st) +{ + /* modify this state is possible only with a plug */ + if (state == USB_TYPE_FREE) { + return; + } + + state = st; + if (st == USB_TYPE_FREE) { + HCD_HandleTypeDef *hhcd = (HCD_HandleTypeDef*)hced->hhcd; + uint32_t *addr = &((uint32_t *)hhcd->pData)[hced->ch_num]; + if ((*addr) && (type != INTERRUPT_ENDPOINT)) { + this->ep_queue.put((uint8_t*)1); + } + MBED_ASSERT(HAL_HCD_HC_Halt((HCD_HandleTypeDef*)hced->hhcd, hced->ch_num)!=HAL_BUSY); + HAL_HCD_DisableInt((HCD_HandleTypeDef*)hced->hhcd, hced->ch_num); + *addr = 0; + + } + if (st == USB_TYPE_ERROR) { + MBED_ASSERT(HAL_HCD_HC_Halt((HCD_HandleTypeDef*)hced->hhcd, hced->ch_num)!=HAL_BUSY); + HAL_HCD_DisableInt((HCD_HandleTypeDef*)hced->hhcd, hced->ch_num); + + } + if (st == USB_TYPE_ERROR) { + uint8_t hcd_speed = HCD_SPEED_FULL; + /* small speed device with hub not supported + if (this->speed) hcd_speed = HCD_SPEED_LOW;*/ + MBED_ASSERT(HAL_HCD_HC_Init((HCD_HandleTypeDef*)hced->hhcd,hced->ch_num, address, 0, hcd_speed, type, size)!=HAL_BUSY); + } +} + + +extern uint32_t HAL_HCD_HC_GetMaxPacket(HCD_HandleTypeDef *hhcd, uint8_t chn_num); +extern uint32_t HAL_HCD_HC_GetType(HCD_HandleTypeDef *hhcd, uint8_t chn_num); + + +USB_TYPE USBEndpoint::queueTransfer() +{ + HCD_HandleTypeDef *hhcd = (HCD_HandleTypeDef*)hced->hhcd; + uint32_t *addr = &((uint32_t *)hhcd->pData)[hced->ch_num]; + uint32_t type = HAL_HCD_HC_GetType(hhcd, hced->ch_num); + uint32_t max_size = HAL_HCD_HC_GetMaxPacket(hhcd, hced->ch_num); + /* if a packet is queue on disconnected ; no solution for now */ + if (state == USB_TYPE_FREE) { + td_current->state = USB_TYPE_FREE; + return USB_TYPE_FREE; + } + ep_queue.get(0); + MBED_ASSERT(*addr ==0); + transfer_len = td_current->size <= max_size ? td_current->size : max_size; + buf_start = (uint8_t *)td_current->currBufPtr; + + //Now add this free TD at this end of the queue + state = USB_TYPE_PROCESSING; + /* one request */ + td_current->nextTD = (hcTd*)0; +#if defined(MAX_NYET_RETRY) + td_current->retry = 0; +#endif + td_current->setup = setup; + *addr = (uint32_t)td_current; + /* dir /setup is inverted for ST */ + /* token is useful only ctrl endpoint */ + /* last parameter is ping ? */ + MBED_ASSERT(HAL_HCD_HC_SubmitRequest((HCD_HandleTypeDef*)hced->hhcd, hced->ch_num, dir-1, type,!setup,(uint8_t*) td_current->currBufPtr, transfer_len, 0)==HAL_OK); + HAL_HCD_EnableInt((HCD_HandleTypeDef*)hced->hhcd, hced->ch_num); + + return USB_TYPE_PROCESSING; +} + +void USBEndpoint::unqueueTransfer(volatile HCTD * td) +{ + if (state==USB_TYPE_FREE) { + return; + } + uint32_t *addr = &((uint32_t *)((HCD_HandleTypeDef*)hced->hhcd)->pData)[hced->ch_num]; + td->state=0; + td->currBufPtr=0; + td->size=0; + td->nextTD=0; + *addr = 0; + td_current = td_next; + td_next = td; +} + +void USBEndpoint::queueEndpoint(USBEndpoint * ed) +{ + nextEp = ed; +} +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/USBHALHost_STM.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,284 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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. + */ + +#ifdef TARGET_STM +#include "mbed.h" +#include "USBHALHost.h" +#include "dbg.h" +#include "pinmap.h" + +#include "USBHALHost_STM_TARGET.h" + +void HAL_HCD_Connect_Callback(HCD_HandleTypeDef *hhcd) +{ + USBHALHost_Private_t *priv=(USBHALHost_Private_t *)(hhcd->pData); + USBHALHost *obj= priv->inst; + void (USBHALHost::*func)(int hub, int port, bool lowSpeed, USBHostHub * hub_parent ) = priv->deviceConnected; + (obj->*func)(0,1,0,NULL); +} +void HAL_HCD_Disconnect_Callback(HCD_HandleTypeDef *hhcd) +{ + USBHALHost_Private_t *priv=(USBHALHost_Private_t *)(hhcd->pData); + USBHALHost *obj= priv->inst; + void (USBHALHost::*func1)(int hub, int port, USBHostHub * hub_parent, volatile uint32_t addr)= priv->deviceDisconnected; + (obj->*func1)(0,1,(USBHostHub *)NULL,0); +} +int HAL_HCD_HC_GetDirection(HCD_HandleTypeDef *hhcd,uint8_t chnum) +{ + /* useful for transmission */ + return hhcd->hc[chnum].ep_is_in; +} + +uint32_t HAL_HCD_HC_GetMaxPacket(HCD_HandleTypeDef *hhcd,uint8_t chnum) +{ + /* useful for transmission */ + return hhcd->hc[chnum].max_packet; +} + +void HAL_HCD_EnableInt(HCD_HandleTypeDef *hhcd,uint8_t chnum) +{ + USB_OTG_GlobalTypeDef *USBx = hhcd->Instance; + USBx_HOST->HAINTMSK |= (1 << chnum); +} + + +void HAL_HCD_DisableInt(HCD_HandleTypeDef *hhcd,uint8_t chnum) +{ + USB_OTG_GlobalTypeDef *USBx = hhcd->Instance; + USBx_HOST->HAINTMSK &= ~(1 << chnum); +} +uint32_t HAL_HCD_HC_GetType(HCD_HandleTypeDef *hhcd,uint8_t chnum) +{ + /* useful for transmission */ + return hhcd->hc[chnum].ep_type; +} + +void HAL_HCD_HC_NotifyURBChange_Callback(HCD_HandleTypeDef *hhcd,uint8_t chnum, HCD_URBStateTypeDef urb_state) +{ + USBHALHost_Private_t *priv=(USBHALHost_Private_t *)(hhcd->pData); + USBHALHost *obj= priv->inst; + void (USBHALHost::*func)(volatile uint32_t addr)= priv->transferCompleted; + + uint32_t addr = priv->addr[chnum]; + uint32_t max_size = HAL_HCD_HC_GetMaxPacket(hhcd, chnum); + uint32_t type = HAL_HCD_HC_GetType(hhcd, chnum); + uint32_t dir = HAL_HCD_HC_GetDirection(hhcd,chnum); + uint32_t length; + if ( (addr!=0)) { + HCTD *td = (HCTD *)addr; + + if ((type == EP_TYPE_BULK) || (type == EP_TYPE_CTRL )) { + switch (urb_state) { + case URB_DONE: +#if defined(MAX_NYET_RETRY) + td->retry = 0; +#endif + if (td->size > max_size) { + /* enqueue another request */ + td->currBufPtr += max_size; + td->size -= max_size; + length = td->size <= max_size ? td->size : max_size; + MBED_ASSERT(HAL_HCD_HC_SubmitRequest(hhcd, chnum, dir ,type , !td->setup,(uint8_t*) td->currBufPtr, length, 0)==HAL_OK); + HAL_HCD_EnableInt(hhcd, chnum); + return; + } + break; + case URB_NOTREADY: + /* try again */ + /* abritary limit , to avoid dead lock if other error than + * slow response is */ +#if defined(MAX_NYET_RETRY) + if (td->retry < MAX_NYET_RETRY) { + /* increment retry counter */ + td->retry++; +#endif + length = td->size <= max_size ? td->size : max_size; + MBED_ASSERT(HAL_HCD_HC_SubmitRequest(hhcd, chnum, dir ,type , !td->setup,(uint8_t*) td->currBufPtr, length, 0)==HAL_OK); + HAL_HCD_EnableInt(hhcd, chnum); + return; +#if defined(MAX_NYET_RETRY) + } else { + USB_ERR("urb_state != URB_NOTREADY"); + } +#endif + break; + } + } + if ((type == EP_TYPE_INTR) ) { + /* reply a packet of length NULL, this will be analyse in call back + * for mouse or hub */ + td->state =USB_TYPE_IDLE ; + HAL_HCD_DisableInt(hhcd, chnum); + + } else { + td->state = (urb_state == URB_DONE) ? USB_TYPE_IDLE : USB_TYPE_ERROR; + } + td->currBufPtr +=HAL_HCD_HC_GetXferCount(hhcd, chnum); + (obj->*func)(addr); + } else { + if (urb_state !=0) { + USB_DBG_EVENT("spurious %d %d",chnum, urb_state); + } + } +} + +USBHALHost * USBHALHost::instHost; + + +void USBHALHost::init() +{ + + NVIC_DisableIRQ(USBHAL_IRQn); + NVIC_SetVector(USBHAL_IRQn, (uint32_t)(_usbisr)); + HAL_HCD_Init((HCD_HandleTypeDef *) usb_hcca); + NVIC_EnableIRQ(USBHAL_IRQn); + control_disable = 0; + HAL_HCD_Start((HCD_HandleTypeDef *) usb_hcca); + usb_vbus(1); +} + +uint32_t USBHALHost::controlHeadED() +{ + return 0xffffffff; +} + +uint32_t USBHALHost::bulkHeadED() +{ + return 0xffffffff; +} + +uint32_t USBHALHost::interruptHeadED() +{ + return 0xffffffff; +} + +void USBHALHost::updateBulkHeadED(uint32_t addr) +{ +} + + +void USBHALHost::updateControlHeadED(uint32_t addr) +{ +} + +void USBHALHost::updateInterruptHeadED(uint32_t addr) +{ +} + + +void USBHALHost::enableList(ENDPOINT_TYPE type) +{ + /* react when the 3 lists are requested to be disabled */ + if (type == CONTROL_ENDPOINT) { + control_disable--; + if (control_disable == 0) { + NVIC_EnableIRQ(USBHAL_IRQn); + } else { + printf("reent\n"); + } + } +} + + +bool USBHALHost::disableList(ENDPOINT_TYPE type) +{ + if (type == CONTROL_ENDPOINT) { + NVIC_DisableIRQ(USBHAL_IRQn); + control_disable++; + if (control_disable > 1) { + printf("disable reentrance !!!\n"); + } + return true; + } + return false; +} + + +void USBHALHost::memInit() +{ + usb_hcca = (volatile HCD_HandleTypeDef *)usb_buf; + usb_edBuf = usb_buf + HCCA_SIZE; + usb_tdBuf = usb_buf + HCCA_SIZE +(MAX_ENDPOINT*ED_SIZE); + /* init channel */ + memset((void*)usb_buf,0, TOTAL_SIZE); + for (int i=0; i < MAX_ENDPOINT; i++) { + HCED *hced = (HCED*)(usb_edBuf + i*ED_SIZE); + hced->ch_num = i; + hced->hhcd = (HCCA *) usb_hcca; + } +} + +volatile uint8_t * USBHALHost::getED() +{ + for (int i = 0; i < MAX_ENDPOINT; i++) { + if ( !edBufAlloc[i] ) { + edBufAlloc[i] = true; + return (volatile uint8_t *)(usb_edBuf + i*ED_SIZE); + } + } + perror("Could not allocate ED\r\n"); + return NULL; //Could not alloc ED +} + +volatile uint8_t * USBHALHost::getTD() +{ + int i; + for (i = 0; i < MAX_TD; i++) { + if ( !tdBufAlloc[i] ) { + tdBufAlloc[i] = true; + return (volatile uint8_t *)(usb_tdBuf + i*TD_SIZE); + } + } + perror("Could not allocate TD\r\n"); + return NULL; //Could not alloc TD +} + + +void USBHALHost::freeED(volatile uint8_t * ed) +{ + int i; + i = (ed - usb_edBuf) / ED_SIZE; + edBufAlloc[i] = false; +} + +void USBHALHost::freeTD(volatile uint8_t * td) +{ + int i; + i = (td - usb_tdBuf) / TD_SIZE; + tdBufAlloc[i] = false; +} + + +void USBHALHost::resetRootHub() +{ + // Initiate port reset + wait(0.2); + HAL_HCD_ResetPort((HCD_HandleTypeDef *)usb_hcca); +} + + +void USBHALHost::_usbisr(void) +{ + if (instHost) { + instHost->UsbIrqhandler(); + } +} + +void USBHALHost::UsbIrqhandler() +{ + HAL_HCD_IRQHandler((HCD_HandleTypeDef *)usb_hcca); +} +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/USBHost/targets/TARGET_STM/USBHALHost_STM_144_64pins.h Wed Jun 05 04:54:37 2019 +0000 @@ -0,0 +1,121 @@ +/* mbed USBHost Library + * Copyright (c) 2006-2013 ARM Limited + * + * 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 USBHALHOST_STM32_144_64 +#define USBHALHOST_STM32_144_64 + +#define USBHAL_IRQn OTG_FS_IRQn + +#define HCCA_SIZE sizeof(HCD_HandleTypeDef) +#define ED_SIZE sizeof(HCED) +#define TD_SIZE sizeof(HCTD) + +#define TOTAL_SIZE (HCCA_SIZE + (MAX_ENDPOINT*ED_SIZE) + (MAX_TD*TD_SIZE)) +/* STM device FS have 11 channels (definition is for 60 channels) */ +static volatile uint8_t usb_buf[TOTAL_SIZE]; +typedef struct +{ + /* store the request ongoing on each endpoit */ + /* 1st field of structure avoid giving knowledge of all structure to + * endpoint */ + volatile uint32_t addr[MAX_ENDPOINT]; + USBHALHost *inst; + void (USBHALHost::*deviceConnected)(int hub, int port, bool lowSpeed, USBHostHub * hub_parent); + void (USBHALHost::*deviceDisconnected)(int hub, int port, USBHostHub * hub_parent, volatile uint32_t addr); + void (USBHALHost::*transferCompleted)(volatile uint32_t addr); +}USBHALHost_Private_t; + +/* CONFIGURATION for USB_VBUS + * on 64 bits board PC_0 is used (0 VBUS on, 1 VBUS off) + * on 144 pins board PG_6 is used ( 1 VBUS on, 0 VBUS on) + */ +static gpio_t gpio_vbus; + +#if defined(USBHALHOST_64pins) +#define VBUS_OFF 1 +#define VBUS_ON 0 +#define USB_VBUS_CONFIG \ + do {__HAL_RCC_GPIOC_CLK_ENABLE();\ + gpio_init_out_ex(&gpio_vbus, PC_0, VBUS_OFF);\ + }while(0); +#else +#define VBUS_OFF 0 +#define VBUS_ON 1 +#define USB_VBUS_CONFIG \ + do {__HAL_RCC_GPIOG_CLK_ENABLE();\ + gpio_init_out_ex(&gpio_vbus, PG_6, VBUS_OFF);\ + }while(0); +#endif + +void usb_vbus( uint8_t state) +{ + if(state == 0) + { + gpio_write(&gpio_vbus, VBUS_OFF); + } + else + { + gpio_write(&gpio_vbus, VBUS_ON); + } + wait(0.2); +} + +USBHALHost::USBHALHost() { + instHost = this; + HCD_HandleTypeDef *hhcd; + USBHALHost_Private_t *HALPriv = new(USBHALHost_Private_t); + memset(HALPriv, 0, sizeof(USBHALHost_Private_t)); + memInit(); + memset((void*)usb_hcca, 0, HCCA_SIZE); + hhcd = (HCD_HandleTypeDef *)usb_hcca; + hhcd->Instance = USB_OTG_FS; + hhcd->pData = (void*)HALPriv; + hhcd->Init.Host_channels = 11; + hhcd->Init.speed = HCD_SPEED_FULL; + hhcd->Init.phy_itface = HCD_PHY_EMBEDDED; + HALPriv->inst = this; + HALPriv->deviceConnected = &USBHALHost::deviceConnected; + HALPriv->deviceDisconnected = &USBHALHost::deviceDisconnected; + HALPriv->transferCompleted = &USBHALHost::transferCompleted; + for (int i = 0; i < MAX_ENDPOINT; i++) { + edBufAlloc[i] = false; + HALPriv->addr[i]=(uint32_t)-1; + } + for (int i = 0; i < MAX_TD; i++) { + tdBufAlloc[i] = false; + } + __HAL_RCC_PWR_CLK_ENABLE(); +#ifdef TARGET_STM32L4 + HAL_PWREx_EnableVddUSB(); +#endif + /* Configure USB FS GPIOs */ + __HAL_RCC_GPIOA_CLK_ENABLE(); + + /*USB DM and DP */ + pin_function(PA_11, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_NOPULL, GPIO_AF10_OTG_FS)); + pin_function(PA_12, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_NOPULL, GPIO_AF10_OTG_FS)); + /*USB ID */ + pin_function(PA_10, STM_PIN_DATA(STM_MODE_AF_OD, GPIO_PULLUP, GPIO_AF10_OTG_FS)); + + __HAL_RCC_SYSCFG_CLK_ENABLE(); + /* Configure POWER_SWITCH IO pin */ + USB_VBUS_CONFIG; + /* Enable USB FS Clocks */ + __HAL_RCC_USB_OTG_FS_CLK_ENABLE(); + + /* Set USBFS Interrupt priority */ + HAL_NVIC_SetPriority(OTG_FS_IRQn, 6, 0); +} +#endif
--- a/main.cpp Wed Jan 03 08:07:31 2018 +0000 +++ b/main.cpp Wed Jun 05 04:54:37 2019 +0000 @@ -1,91 +1,194 @@ +/* + * BEHRINGER X-TOUCH to DJAY bridge + * for mbed LPC1768 + * + * X-TOUCH (MC/USB) <---USB---> LPC1768 <---UART MIDI---> MD-BT01 (YAMAHA, BLE MIDI) + */ + #include "mbed.h" +#include "USBHostHub.h" #include "USBHostMIDI.h" +#include "MIDI.h" +#include "CBuffer.h" Serial pc(USBTX, USBRX); DigitalOut led1(LED1); PwmOut led2(LED2), led3(LED3), led4(LED4); +USBHostHub hub; USBHostMIDI midi; +MIDI midi2(p28, p27); -volatile int sendNoteOn = -1, sendNoteOff = -1, sendControlChange = -1; +CircBuffer <uint32_t>midi_out(20); + +void systemExclusive (uint8_t *buffer, uint16_t length, bool flag) { + midi2.sendSysEx(length, buffer, flag); +} void noteOn(uint8_t channel, uint8_t note, uint8_t velocity) { - pc.printf("noteOn %02x %02x %02x\r\n", channel, note, velocity); - switch (note) { - case 0: - led2 = (float)velocity / 127.0; - break; - case 1: - led3 = (float)velocity / 127.0; - break; - case 2: - led4 = (float)velocity / 127.0; - break; - } - sendNoteOn = (channel << 16) | (note << 8) | velocity; + midi_out.queue(((uint32_t)NoteOn << 24) | ((uint32_t)channel << 16) | (note << 8) | velocity); +} +void noteOff(uint8_t channel, uint8_t note, uint8_t velocity) { + midi_out.queue(((uint32_t)NoteOff << 24) | ((uint32_t)channel << 16) | (note << 8) | velocity); +} +void controlChange(uint8_t channel, uint8_t key, uint8_t value) { + midi_out.queue(((uint32_t)ControlChange << 24) | ((uint32_t)channel << 16) | (key << 8) | value); +} +void programChange (uint8_t channel, uint8_t progra) { + midi_out.queue(((uint32_t)ProgramChange << 24) | ((uint32_t)channel << 16) | (progra << 8)); +} +void pitchBend (uint8_t channel, uint16_t value) { + midi_out.queue(((uint32_t)PitchBend << 24) | ((uint32_t)channel << 16) | value); } -void noteOff(uint8_t channel, uint8_t note, uint8_t velocity) { - pc.printf("noteOff %02x %02x %02x\r\n", channel, note, velocity); - sendNoteOff = (channel << 16) | (note << 8) | velocity; -} + +void printLcd (int x, int y, char *buf) { + int i, len; + uint8_t msg[40] = {0xf0, 0x00, 0x00, 0x66, 0x14, 0x12, 0x00}; -void controlChange(uint8_t channel, uint8_t key, uint8_t value) { - pc.printf("controlChange %02x %02x %02x\r\n", channel, key, value); - switch (key) { - case 0: - case 0x4d: - led2 = (float)value / 127.0; - break; - case 1: - case 0x4e: - led3 = (float)value / 127.0; - break; - case 2: - case 0x4f: - led4 = (float)value / 127.0; - break; + msg[6] = (7 * x) + (0x38 * y); + len = 7; + for (i = 0; i < strlen(buf); i ++) { + msg[len ++] = buf[i]; } - sendControlChange = (channel << 16) | (key << 8) | value; + msg[len ++] = 0xf7; + midi.sendSystemExclusive(msg, len); } void midi_task(void const*) { int i; - USBHostMIDI midi; - + +// hub = new USBHostHub; +// midi = new USBHostMIDI; + // attach midi event callbacks + midi.attachSystemExclusive(systemExclusive); midi.attachNoteOn(noteOn); midi.attachNoteOff(noteOff); midi.attachControlChange(controlChange); + midi.attachProgramChange(programChange); + midi.attachPitchBend(pitchBend); + pc.printf("begin\r\n"); + uint32_t m; + int channel, data1, data2; for (;;) { // try to connect a midi device while(!midi.connect()) { Thread::wait(500); led1 = !led1; } - Thread::wait(1000); - midi.sendControlChange(0, 41, 127); // LED on (nanoKONTROL2) - midi.sendNoteOn(0, 0x29, 127); // LED on (Launch Control XL) + Thread::wait(500); + + pc.printf("detected\r\n"); + for (i = 0; i < 9; i ++) { + midi.sendPitchBend(i, 0); // fader 0 + } + for (i = 0; i < 0x7f; i ++) { + midi.sendNoteOn(0, i, 0); // led off + } + + // LCD + printLcd(0, 0, " High"); + printLcd(1, 0, " Mid"); + printLcd(2, 0, " Low"); + printLcd(3, 0, " Gain"); + printLcd(4, 0, " Gain"); + printLcd(5, 0, " Low"); + printLcd(6, 0, " Mid"); + printLcd(7, 0, " High"); + printLcd(2, 1, " Speed"); + printLcd(3, 1, " 1 <"); + printLcd(4, 1, "> 2 "); + printLcd(5, 1, " Speed"); + // 7segment LED + midi.sendControlChange(0, 0x43, 'D' & 0x1f); + midi.sendControlChange(0, 0x42, 'J' & 0x1f); + midi.sendControlChange(0, 0x41, 'A' & 0x1f); + midi.sendControlChange(0, 0x40, 'Y' & 0x1f); + led1 = 1; - for (;;) { if (!midi.connected()) { pc.printf("disconnected\r\n"); break; } - if (sendNoteOn != -1) { - midi.sendNoteOn(sendNoteOn >> 16, sendNoteOn >> 8, sendNoteOn); - sendNoteOn = -1; + if (!midi_out.isEmpty()) { + // USB -> uart + midi_out.dequeue(&m); + channel = (m >> 16) & 0x7f; + data1 = (m >> 8) & 0x7f; + data2 = m & 0x7f; + + switch (m >> 24) { + case NoteOn: + midi2.sendNoteOn(data1, data2, channel); +// pc.printf("noteOn %02x %02x %02x\r\n", channel, data1, data2); + break; + case NoteOff: + midi2.sendNoteOff(data1, data2, channel); +// pc.printf("noteOff %02x %02x %02x\r\n", channel, data1, data2); + break; + case ControlChange: + if ((data1 >= 0x10 && data1 <= 0x17) || data1 == 0x3c) { + midi2.sendControlChange(data1, data2 < 0x40 ? data2 : 0x80 - (data2 - 0x40), channel); + } else { + midi2.sendControlChange(data1, data2, channel); + } +// pc.printf("controlChange %02x %02x %02x\r\n", channel, data1, data2); + break; + case ProgramChange: + midi2.sendProgramChange(data1, channel); +// pc.printf("programChange %02x %02x\r\n", channel, data1); + break; + case PitchBend: + data1 = m & 0x3fff; + midi.sendPitchBend(channel, data1); + midi2.sendControlChange(channel, data1 >> 7, 0); +// pc.printf("pitchBend %02x %04x\r\n", channel, data1); + break; + } } - if (sendNoteOff != -1) { - midi.sendNoteOff(sendNoteOff >> 16, sendNoteOff >> 8, sendNoteOff); - sendNoteOff = -1; - } - if (sendControlChange != -1) { - midi.sendControlChange(sendControlChange >> 16, sendControlChange >> 8, sendControlChange); - sendControlChange = -1; + + if (midi2.read()) { + // uart -> USB + channel = midi2.getChannel(); + data1 = midi2.getData1(); + data2 = midi2.getData2(); + + switch (midi2.getType()) { + case NoteOn: + midi.sendNoteOn(channel, data1, data2); +// pc.printf(" noteOn %02x %02x %02x\r\n", channel, data1, data2); + break; + case NoteOff: + midi.sendNoteOff(channel, data1, data2); +// pc.printf(" noteOff %02x %02x %02x\r\n", channel, data1, data2); + break; + case ControlChange: + if (data1 < 0x10) { + midi.sendPitchBend(data1, (data2 << 7) | data2); + } else + if (data1 >= 0x10 && data1 <= 0x17) { + midi.sendControlChange(channel, 0x30 | (data1 & 0x0f), (data2 * 0x0c) / 0x7f); + } else { + midi.sendControlChange(channel, data1, data2); + } +// pc.printf(" controlChange %02x %02x %02x\r\n", channel, data1, data2); + break; + case ProgramChange: + midi.sendProgramChange(channel, data1); +// pc.printf(" programChange %02x %02x\r\n", channel, data1); + break; + case PitchBend: +// pc.printf(" pitchBend %02x %04x\r\n", channel, data1); + break; + case SystemExclusive: + midi.sendSystemExclusive((uint8_t *)midi2.getSysExArray(), midi2.getSysExArrayLength()); +// pc.printf(" SystemExclusive\r\n"); + break; + } } } } @@ -95,8 +198,12 @@ pc.baud(115200); pc.printf("*** USB Host MIDI\r\n"); - Thread midiTask(midi_task); + midi2.begin(MIDI_CHANNEL_OMNI); + midi2.turnThruOff(); + +// Thread midiTask(midi_task, NULL, osPriorityNormal, 5120); for (;;) { - Thread::wait(100); + midi_task(NULL); +// Thread::wait(100); } }