\r
Pipe_Unfreeze();\r
\r
- PacketWaiting = Pipe_IsINReceived();\r
+ PacketWaiting = (Pipe_IsINReceived() && Pipe_BytesInPipe());\r
\r
Pipe_Freeze();\r
\r
\r
if (!(Pipe_IsReadWriteAllowed()))\r
{\r
+ if (Pipe_IsINReceived())\r
+ Pipe_ClearIN();\r
+ \r
*PacketLength = 0;\r
Pipe_Freeze();\r
return PIPE_RWSTREAM_NoError;\r
\r
RNDIS_Packet_Message_t DeviceMessage;\r
\r
+ if (Pipe_BytesInPipe() < sizeof(RNDIS_Packet_Message_t))\r
+ {\r
+ printf("*SIZE YARG: %d*\r\n", Pipe_BytesInPipe());\r
+ *PacketLength = 0;\r
+ Pipe_ClearIN();\r
+ return RNDIS_COMMAND_FAILED; \r
+ }\r
+ \r
if ((ErrorCode = Pipe_Read_Stream_LE(&DeviceMessage, sizeof(RNDIS_Packet_Message_t),\r
NO_STREAM_CALLBACK)) != PIPE_RWSTREAM_NoError)\r
{\r
return ErrorCode;\r
}\r
+ \r
+ if (DeviceMessage.MessageType != REMOTE_NDIS_PACKET_MSG)\r
+ {\r
+ printf("****YARG****\r\n");\r
+ *PacketLength = 0;\r
+ Pipe_ClearIN();\r
+ return RNDIS_COMMAND_FAILED;\r
+ }\r
\r
*PacketLength = (uint16_t)DeviceMessage.DataLength;\r
\r
NO_STREAM_CALLBACK);\r
\r
Pipe_Read_Stream_LE(Buffer, *PacketLength, NO_STREAM_CALLBACK);\r
- Pipe_ClearIN();\r
+ \r
+ if (!(Pipe_BytesInPipe()))\r
+ Pipe_ClearIN();\r
\r
Pipe_Freeze();\r
\r
Pipe_SelectPipe(RNDISInterfaceInfo->Config.DataOUTPipeNumber); \r
}\r
\r
- Pipe_Unfreeze();\r
-\r
RNDIS_Packet_Message_t DeviceMessage;\r
- \r
- DeviceMessage.MessageType = REMOTE_NDIS_PACKET_MSG;\r
+\r
+ memset(&DeviceMessage, 0, sizeof(RNDIS_Packet_Message_t));\r
+ DeviceMessage.MessageType = REMOTE_NDIS_PACKET_MSG;\r
DeviceMessage.MessageLength = (sizeof(RNDIS_Packet_Message_t) + PacketLength);\r
- DeviceMessage.DataOffset = (sizeof(RNDIS_Packet_Message_t) - sizeof(RNDIS_Message_Header_t));\r
- DeviceMessage.DataLength = PacketLength;\r
+ DeviceMessage.DataOffset = (sizeof(RNDIS_Packet_Message_t) - sizeof(RNDIS_Message_Header_t));\r
+ DeviceMessage.DataLength = PacketLength;\r
\r
+ Pipe_Unfreeze();\r
+\r
if ((ErrorCode = Pipe_Write_Stream_LE(&DeviceMessage, sizeof(RNDIS_Packet_Message_t),\r
NO_STREAM_CALLBACK)) != PIPE_RWSTREAM_NoError)\r
{\r
+ if (RNDISInterfaceInfo->State.BidirectionalDataEndpoints)\r
+ Pipe_SetPipeToken(PIPE_TOKEN_IN);\r
+\r
return ErrorCode;\r
}\r
- \r
+\r
Pipe_Write_Stream_LE(Buffer, PacketLength, NO_STREAM_CALLBACK);\r
Pipe_ClearOUT();\r
\r
#warning TPI Protocol support is currently incomplete and is not suitable for general use.\r
\r
/** Sends the given pointer address to the target's TPI pointer register */\r
-void TINYNVM_SendPointerAddress(const uint16_t AbsoluteAddress)\r
+static void TINYNVM_SendPointerAddress(const uint16_t AbsoluteAddress)\r
{\r
/* Send the given 16-bit address to the target, LSB first */\r
XPROGTarget_SendByte(TPI_CMD_SSTPR | 0);\r
XPROGTarget_SendByte(((uint8_t*)&AbsoluteAddress)[1]);\r
}\r
\r
+/** Sends a SIN command to the target with the specified I/O address, ready for the data byte to be written.\r
+ *\r
+ * \param Address 6-bit I/O address to write to in the target's I/O memory space\r
+ */\r
+static void TINYNVM_SendReadNVMRegister(uint8_t Address)\r
+{\r
+ /* The TPI command for reading from the I/O space uses wierd addressing, where the I/O address's upper\r
+ * two bits of the 6-bit address are shifted left once */\r
+ XPROGTarget_SendByte(TPI_CMD_SIN | ((Address & 0x30) << 1) | (Address & 0x0F));\r
+}\r
+\r
+/** Sends a SOUT command to the target with the specified I/O address, ready for the data byte to be read.\r
+ *\r
+ * \param Address 6-bit I/O address to read from in the target's I/O memory space\r
+ */\r
+static void TINYNVM_SendWriteNVMRegister(uint8_t Address)\r
+{\r
+ /* The TPI command for writing to the I/O space uses wierd addressing, where the I/O address's upper\r
+ * two bits of the 6-bit address are shifted left once */\r
+ XPROGTarget_SendByte(TPI_CMD_SOUT | ((Address & 0x30) << 1) | (Address & 0x0F));\r
+}\r
+\r
/** Busy-waits while the NVM controller is busy performing a NVM operation, such as a FLASH page read.\r
*\r
* \return Boolean true if the NVM controller became ready within the timeout period, false otherwise\r
while (TimeoutMSRemaining)\r
{\r
/* Send the SIN command to read the TPI STATUS register to see the NVM bus is active */\r
- XPROGTarget_SendByte(TPI_CMD_SIN | XPROG_Param_NVMCSRRegAddr);\r
+ TINYNVM_SendReadNVMRegister(XPROG_Param_NVMCSRRegAddr);\r
if (XPROGTarget_ReceiveByte() & (1 << 7))\r
return true;\r
}\r
return false;\r
\r
/* Set the NVM control register to the NO OP command for memory reading */\r
- XPROGTarget_SendByte(TPI_CMD_SOUT | XPROG_Param_NVMCMDRegAddr);\r
+ TINYNVM_SendWriteNVMRegister(XPROG_Param_NVMCMDRegAddr);\r
XPROGTarget_SendByte(TINY_NVM_CMD_NOOP);\r
\r
/* Send the address of the location to read from */\r
return false;\r
\r
/* Set the NVM control register to the WORD WRITE command for memory reading */\r
- XPROGTarget_SendByte(TPI_CMD_SOUT | XPROG_Param_NVMCMDRegAddr);\r
+ TINYNVM_SendWriteNVMRegister(XPROG_Param_NVMCMDRegAddr);\r
XPROGTarget_SendByte(TINY_NVM_CMD_WORDWRITE);\r
\r
/* Send the address of the location to write to */\r
return false;\r
\r
/* Set the NVM control register to the CHIP ERASE command to erase the target */\r
- XPROGTarget_SendByte(TPI_CMD_SOUT | XPROG_Param_NVMCMDRegAddr);\r
+ TINYNVM_SendWriteNVMRegister(XPROG_Param_NVMCMDRegAddr);\r
XPROGTarget_SendByte(TINY_NVM_CMD_CHIPERASE); \r
\r
/* Wait until the NVM bus is ready again */\r
#define TINY_NVM_CMD_SECTIONERASE 0x14\r
#define TINY_NVM_CMD_WORDWRITE 0x1D\r
\r
- /* Function Prototypes: */\r
- void TINYNVM_SendPointerAddress(const uint16_t AbsoluteAddress);\r
+ /* Function Prototypes: */ \r
bool TINYNVM_WaitWhileNVMBusBusy(void);\r
bool TINYNVM_ReadMemory(const uint32_t ReadAddress, uint8_t* ReadBuffer, uint16_t ReadLength);\r
bool TINYNVM_WriteMemory(const uint32_t WriteAddress, const uint8_t* WriteBuffer, uint16_t WriteLength);\r
bool TINYNVM_EraseMemory(void);\r
\r
+ #if defined(INCLUDE_FROM_TINYNVM_C)\r
+ static void TINYNVM_SendReadNVMRegister(uint8_t Address);\r
+ static void TINYNVM_SendWriteNVMRegister(uint8_t Address);\r
+ static void TINYNVM_SendPointerAddress(const uint16_t AbsoluteAddress);\r
+ #endif\r
+\r
#endif\r
\r
#if defined(ENABLE_XPROG_PROTOCOL) || defined(__DOXYGEN__)\r
\r
-/** Sends the given NVM register address to the target.\r
- *\r
- * \param[in] Register NVM register whose absolute address is to be sent\r
- */\r
-void XMEGANVM_SendNVMRegAddress(const uint8_t Register)\r
-{\r
- /* Determine the absolute register address from the NVM base memory address and the NVM register address */\r
- uint32_t Address = XPROG_Param_NVMBase | Register;\r
-\r
- /* Send the calculated 32-bit address to the target, LSB first */\r
- XMEGANVM_SendAddress(Address);\r
-}\r
-\r
/** Sends the given 32-bit absolute address to the target.\r
*\r
* \param[in] AbsoluteAddress Absolute address to send to the target\r
*/\r
-void XMEGANVM_SendAddress(const uint32_t AbsoluteAddress)\r
+static void XMEGANVM_SendAddress(const uint32_t AbsoluteAddress)\r
{\r
/* Send the given 32-bit address to the target, LSB first */\r
XPROGTarget_SendByte(((uint8_t*)&AbsoluteAddress)[0]);\r
XPROGTarget_SendByte(((uint8_t*)&AbsoluteAddress)[3]);\r
}\r
\r
+/** Sends the given NVM register address to the target.\r
+ *\r
+ * \param[in] Register NVM register whose absolute address is to be sent\r
+ */\r
+static void XMEGANVM_SendNVMRegAddress(const uint8_t Register)\r
+{\r
+ /* Determine the absolute register address from the NVM base memory address and the NVM register address */\r
+ uint32_t Address = XPROG_Param_NVMBase | Register;\r
+\r
+ /* Send the calculated 32-bit address to the target, LSB first */\r
+ XMEGANVM_SendAddress(Address);\r
+}\r
+\r
/** Busy-waits while the NVM controller is busy performing a NVM operation, such as a FLASH page read or CRC\r
* calculation.\r
*\r
#define XMEGA_NVM_CMD_READEEPROM 0x06\r
\r
/* Function Prototypes: */\r
- void XMEGANVM_SendNVMRegAddress(const uint8_t Register);\r
- void XMEGANVM_SendAddress(const uint32_t AbsoluteAddress);\r
bool XMEGANVM_WaitWhileNVMBusBusy(void);\r
bool XMEGANVM_WaitWhileNVMControllerBusy(void);\r
bool XMEGANVM_GetMemoryCRC(const uint8_t CRCCommand, uint32_t* const CRCDest);\r
const uint8_t* WriteBuffer, uint16_t WriteSize);\r
bool XMEGANVM_EraseMemory(const uint8_t EraseCommand, const uint32_t Address);\r
\r
+ #if defined(INCLUDE_FROM_XMEGANVM_C)\r
+ static void XMEGANVM_SendNVMRegAddress(const uint8_t Register);\r
+ static void XMEGANVM_SendAddress(const uint32_t AbsoluteAddress); \r
+ #endif\r
+\r
#endif\r