xemac_polled.c 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482
  1. /******************************************************************************
  2. *
  3. * Author: Xilinx, Inc.
  4. *
  5. *
  6. * This program is free software; you can redistribute it and/or modify it
  7. * under the terms of the GNU General Public License as published by the
  8. * Free Software Foundation; either version 2 of the License, or (at your
  9. * option) any later version.
  10. *
  11. *
  12. * XILINX IS PROVIDING THIS DESIGN, CODE, OR INFORMATION "AS IS" AS A
  13. * COURTESY TO YOU. BY PROVIDING THIS DESIGN, CODE, OR INFORMATION AS
  14. * ONE POSSIBLE IMPLEMENTATION OF THIS FEATURE, APPLICATION OR STANDARD,
  15. * XILINX IS MAKING NO REPRESENTATION THAT THIS IMPLEMENTATION IS FREE
  16. * FROM ANY CLAIMS OF INFRINGEMENT, AND YOU ARE RESPONSIBLE FOR OBTAINING
  17. * ANY THIRD PARTY RIGHTS YOU MAY REQUIRE FOR YOUR IMPLEMENTATION.
  18. * XILINX EXPRESSLY DISCLAIMS ANY WARRANTY WHATSOEVER WITH RESPECT TO
  19. * THE ADEQUACY OF THE IMPLEMENTATION, INCLUDING BUT NOT LIMITED TO ANY
  20. * WARRANTIES OR REPRESENTATIONS THAT THIS IMPLEMENTATION IS FREE FROM
  21. * CLAIMS OF INFRINGEMENT, IMPLIED WARRANTIES OF MERCHANTABILITY AND
  22. * FITNESS FOR A PARTICULAR PURPOSE.
  23. *
  24. *
  25. * Xilinx hardware products are not intended for use in life support
  26. * appliances, devices, or systems. Use in such applications is
  27. * expressly prohibited.
  28. *
  29. *
  30. * (c) Copyright 2002-2004 Xilinx Inc.
  31. * All rights reserved.
  32. *
  33. *
  34. * You should have received a copy of the GNU General Public License along
  35. * with this program; if not, write to the Free Software Foundation, Inc.,
  36. * 675 Mass Ave, Cambridge, MA 02139, USA.
  37. *
  38. ******************************************************************************/
  39. /*****************************************************************************/
  40. /**
  41. *
  42. * @file xemac_polled.c
  43. *
  44. * Contains functions used when the driver is in polled mode. Use the
  45. * XEmac_SetOptions() function to put the driver into polled mode.
  46. *
  47. * <pre>
  48. * MODIFICATION HISTORY:
  49. *
  50. * Ver Who Date Changes
  51. * ----- ---- -------- -----------------------------------------------
  52. * 1.00a rpm 07/31/01 First release
  53. * 1.00b rpm 02/20/02 Repartitioned files and functions
  54. * 1.00c rpm 12/05/02 New version includes support for simple DMA
  55. * </pre>
  56. *
  57. ******************************************************************************/
  58. /***************************** Include Files *********************************/
  59. #include "xbasic_types.h"
  60. #include "xemac_i.h"
  61. #include "xio.h"
  62. #include "xipif_v1_23_b.h" /* Uses v1.23b of the IPIF */
  63. /************************** Constant Definitions *****************************/
  64. /**************************** Type Definitions *******************************/
  65. /***************** Macros (Inline Functions) Definitions *********************/
  66. /************************** Variable Definitions *****************************/
  67. /************************** Function Prototypes ******************************/
  68. /*****************************************************************************/
  69. /**
  70. *
  71. * Send an Ethernet frame in polled mode. The device/driver must be in polled
  72. * mode before calling this function. The driver writes the frame directly to
  73. * the MAC's packet FIFO, then enters a loop checking the device status for
  74. * completion or error. Statistics are updated if an error occurs. The buffer
  75. * to be sent must be word-aligned.
  76. *
  77. * It is assumed that the upper layer software supplies a correctly formatted
  78. * Ethernet frame, including the destination and source addresses, the
  79. * type/length field, and the data field. It is also assumed that upper layer
  80. * software does not append FCS at the end of the frame.
  81. *
  82. * @param InstancePtr is a pointer to the XEmac instance to be worked on.
  83. * @param BufPtr is a pointer to a word-aligned buffer containing the Ethernet
  84. * frame to be sent.
  85. * @param ByteCount is the size of the Ethernet frame.
  86. *
  87. * @return
  88. *
  89. * - XST_SUCCESS if the frame was sent successfully
  90. * - XST_DEVICE_IS_STOPPED if the device has not yet been started
  91. * - XST_NOT_POLLED if the device is not in polled mode
  92. * - XST_FIFO_NO_ROOM if there is no room in the EMAC's length FIFO for this frame
  93. * - XST_FIFO_ERROR if the FIFO was overrun or underrun. This error is critical
  94. * and requires the caller to reset the device.
  95. * - XST_EMAC_COLLISION if the send failed due to excess deferral or late
  96. * collision
  97. *
  98. * @note
  99. *
  100. * There is the possibility that this function will not return if the hardware
  101. * is broken (i.e., it never sets the status bit indicating that transmission is
  102. * done). If this is of concern to the user, the user should provide protection
  103. * from this problem - perhaps by using a different timer thread to monitor the
  104. * PollSend thread. On a 10Mbps MAC, it takes about 1.21 msecs to transmit a
  105. * maximum size Ethernet frame (1518 bytes). On a 100Mbps MAC, it takes about
  106. * 121 usecs to transmit a maximum size Ethernet frame.
  107. *
  108. * @internal
  109. *
  110. * The EMAC uses FIFOs behind its length and status registers. For this reason,
  111. * it is important to keep the length, status, and data FIFOs in sync when
  112. * reading or writing to them.
  113. *
  114. ******************************************************************************/
  115. XStatus
  116. XEmac_PollSend(XEmac * InstancePtr, u8 * BufPtr, u32 ByteCount)
  117. {
  118. u32 IntrStatus;
  119. u32 XmitStatus;
  120. XStatus Result;
  121. XASSERT_NONVOID(InstancePtr != NULL);
  122. XASSERT_NONVOID(BufPtr != NULL);
  123. XASSERT_NONVOID(ByteCount > XEM_HDR_SIZE); /* send at least 1 byte */
  124. XASSERT_NONVOID(InstancePtr->IsReady == XCOMPONENT_IS_READY);
  125. /*
  126. * Be sure the device is configured for polled mode and it is started
  127. */
  128. if (!InstancePtr->IsPolled) {
  129. return XST_NOT_POLLED;
  130. }
  131. if (InstancePtr->IsStarted != XCOMPONENT_IS_STARTED) {
  132. return XST_DEVICE_IS_STOPPED;
  133. }
  134. /*
  135. * Check for overruns and underruns for the transmit status and length
  136. * FIFOs and make sure the send packet FIFO is not deadlocked. Any of these
  137. * conditions is bad enough that we do not want to continue. The upper layer
  138. * software should reset the device to resolve the error.
  139. */
  140. IntrStatus = XIIF_V123B_READ_IISR(InstancePtr->BaseAddress);
  141. /*
  142. * Overrun errors
  143. */
  144. if (IntrStatus & (XEM_EIR_XMIT_SFIFO_OVER_MASK |
  145. XEM_EIR_XMIT_LFIFO_OVER_MASK)) {
  146. InstancePtr->Stats.XmitOverrunErrors++;
  147. InstancePtr->Stats.FifoErrors++;
  148. return XST_FIFO_ERROR;
  149. }
  150. /*
  151. * Underrun errors
  152. */
  153. if (IntrStatus & (XEM_EIR_XMIT_SFIFO_UNDER_MASK |
  154. XEM_EIR_XMIT_LFIFO_UNDER_MASK)) {
  155. InstancePtr->Stats.XmitUnderrunErrors++;
  156. InstancePtr->Stats.FifoErrors++;
  157. return XST_FIFO_ERROR;
  158. }
  159. if (XPF_V100B_IS_DEADLOCKED(&InstancePtr->SendFifo)) {
  160. InstancePtr->Stats.FifoErrors++;
  161. return XST_FIFO_ERROR;
  162. }
  163. /*
  164. * Before writing to the data FIFO, make sure the length FIFO is not
  165. * full. The data FIFO might not be full yet even though the length FIFO
  166. * is. This avoids an overrun condition on the length FIFO and keeps the
  167. * FIFOs in sync.
  168. */
  169. if (IntrStatus & XEM_EIR_XMIT_LFIFO_FULL_MASK) {
  170. /*
  171. * Clear the latched LFIFO_FULL bit so next time around the most
  172. * current status is represented
  173. */
  174. XIIF_V123B_WRITE_IISR(InstancePtr->BaseAddress,
  175. XEM_EIR_XMIT_LFIFO_FULL_MASK);
  176. return XST_FIFO_NO_ROOM;
  177. }
  178. /*
  179. * This is a non-blocking write. The packet FIFO returns an error if there
  180. * is not enough room in the FIFO for this frame.
  181. */
  182. Result =
  183. XPacketFifoV100b_Write(&InstancePtr->SendFifo, BufPtr, ByteCount);
  184. if (Result != XST_SUCCESS) {
  185. return Result;
  186. }
  187. /*
  188. * Loop on the MAC's status to wait for any pause to complete.
  189. */
  190. IntrStatus = XIIF_V123B_READ_IISR(InstancePtr->BaseAddress);
  191. while ((IntrStatus & XEM_EIR_XMIT_PAUSE_MASK) != 0) {
  192. IntrStatus = XIIF_V123B_READ_IISR(InstancePtr->BaseAddress);
  193. /*
  194. * Clear the pause status from the transmit status register
  195. */
  196. XIIF_V123B_WRITE_IISR(InstancePtr->BaseAddress,
  197. IntrStatus & XEM_EIR_XMIT_PAUSE_MASK);
  198. }
  199. /*
  200. * Set the MAC's transmit packet length register to tell it to transmit
  201. */
  202. XIo_Out32(InstancePtr->BaseAddress + XEM_TPLR_OFFSET, ByteCount);
  203. /*
  204. * Loop on the MAC's status to wait for the transmit to complete. The
  205. * transmit status is in the FIFO when the XMIT_DONE bit is set.
  206. */
  207. do {
  208. IntrStatus = XIIF_V123B_READ_IISR(InstancePtr->BaseAddress);
  209. }
  210. while ((IntrStatus & XEM_EIR_XMIT_DONE_MASK) == 0);
  211. XmitStatus = XIo_In32(InstancePtr->BaseAddress + XEM_TSR_OFFSET);
  212. InstancePtr->Stats.XmitFrames++;
  213. InstancePtr->Stats.XmitBytes += ByteCount;
  214. /*
  215. * Check for various errors, bump statistics, and return an error status.
  216. */
  217. /*
  218. * Overrun errors
  219. */
  220. if (IntrStatus & (XEM_EIR_XMIT_SFIFO_OVER_MASK |
  221. XEM_EIR_XMIT_LFIFO_OVER_MASK)) {
  222. InstancePtr->Stats.XmitOverrunErrors++;
  223. InstancePtr->Stats.FifoErrors++;
  224. return XST_FIFO_ERROR;
  225. }
  226. /*
  227. * Underrun errors
  228. */
  229. if (IntrStatus & (XEM_EIR_XMIT_SFIFO_UNDER_MASK |
  230. XEM_EIR_XMIT_LFIFO_UNDER_MASK)) {
  231. InstancePtr->Stats.XmitUnderrunErrors++;
  232. InstancePtr->Stats.FifoErrors++;
  233. return XST_FIFO_ERROR;
  234. }
  235. /*
  236. * Clear the interrupt status register of transmit statuses
  237. */
  238. XIIF_V123B_WRITE_IISR(InstancePtr->BaseAddress,
  239. IntrStatus & XEM_EIR_XMIT_ALL_MASK);
  240. /*
  241. * Collision errors are stored in the transmit status register
  242. * instead of the interrupt status register
  243. */
  244. if (XmitStatus & XEM_TSR_EXCESS_DEFERRAL_MASK) {
  245. InstancePtr->Stats.XmitExcessDeferral++;
  246. return XST_EMAC_COLLISION_ERROR;
  247. }
  248. if (XmitStatus & XEM_TSR_LATE_COLLISION_MASK) {
  249. InstancePtr->Stats.XmitLateCollisionErrors++;
  250. return XST_EMAC_COLLISION_ERROR;
  251. }
  252. return XST_SUCCESS;
  253. }
  254. /*****************************************************************************/
  255. /**
  256. *
  257. * Receive an Ethernet frame in polled mode. The device/driver must be in polled
  258. * mode before calling this function. The driver receives the frame directly
  259. * from the MAC's packet FIFO. This is a non-blocking receive, in that if there
  260. * is no frame ready to be received at the device, the function returns with an
  261. * error. The MAC's error status is not checked, so statistics are not updated
  262. * for polled receive. The buffer into which the frame will be received must be
  263. * word-aligned.
  264. *
  265. * @param InstancePtr is a pointer to the XEmac instance to be worked on.
  266. * @param BufPtr is a pointer to a word-aligned buffer into which the received
  267. * Ethernet frame will be copied.
  268. * @param ByteCountPtr is both an input and an output parameter. It is a pointer
  269. * to a 32-bit word that contains the size of the buffer on entry into the
  270. * function and the size the received frame on return from the function.
  271. *
  272. * @return
  273. *
  274. * - XST_SUCCESS if the frame was sent successfully
  275. * - XST_DEVICE_IS_STOPPED if the device has not yet been started
  276. * - XST_NOT_POLLED if the device is not in polled mode
  277. * - XST_NO_DATA if there is no frame to be received from the FIFO
  278. * - XST_BUFFER_TOO_SMALL if the buffer to receive the frame is too small for
  279. * the frame waiting in the FIFO.
  280. *
  281. * @note
  282. *
  283. * Input buffer must be big enough to hold the largest Ethernet frame. Buffer
  284. * must also be 32-bit aligned.
  285. *
  286. * @internal
  287. *
  288. * The EMAC uses FIFOs behind its length and status registers. For this reason,
  289. * it is important to keep the length, status, and data FIFOs in sync when
  290. * reading or writing to them.
  291. *
  292. ******************************************************************************/
  293. XStatus
  294. XEmac_PollRecv(XEmac * InstancePtr, u8 * BufPtr, u32 * ByteCountPtr)
  295. {
  296. XStatus Result;
  297. u32 PktLength;
  298. u32 IntrStatus;
  299. XASSERT_NONVOID(InstancePtr != NULL);
  300. XASSERT_NONVOID(BufPtr != NULL);
  301. XASSERT_NONVOID(ByteCountPtr != NULL);
  302. XASSERT_NONVOID(InstancePtr->IsReady == XCOMPONENT_IS_READY);
  303. /*
  304. * Be sure the device is configured for polled mode and it is started
  305. */
  306. if (!InstancePtr->IsPolled) {
  307. return XST_NOT_POLLED;
  308. }
  309. if (InstancePtr->IsStarted != XCOMPONENT_IS_STARTED) {
  310. return XST_DEVICE_IS_STOPPED;
  311. }
  312. /*
  313. * Make sure the buffer is big enough to hold the maximum frame size.
  314. * We need to do this because as soon as we read the MAC's packet length
  315. * register, which is actually a FIFO, we remove that length from the
  316. * FIFO. We do not want to read the length FIFO without also reading the
  317. * data FIFO since this would get the FIFOs out of sync. So we have to
  318. * make this restriction.
  319. */
  320. if (*ByteCountPtr < XEM_MAX_FRAME_SIZE) {
  321. return XST_BUFFER_TOO_SMALL;
  322. }
  323. /*
  324. * First check for packet FIFO deadlock and return an error if it has
  325. * occurred. A reset by the caller is necessary to correct this problem.
  326. */
  327. if (XPF_V100B_IS_DEADLOCKED(&InstancePtr->RecvFifo)) {
  328. InstancePtr->Stats.FifoErrors++;
  329. return XST_FIFO_ERROR;
  330. }
  331. /*
  332. * Get the interrupt status to know what happened (whether an error occurred
  333. * and/or whether frames have been received successfully). When clearing the
  334. * intr status register, clear only statuses that pertain to receive.
  335. */
  336. IntrStatus = XIIF_V123B_READ_IISR(InstancePtr->BaseAddress);
  337. XIIF_V123B_WRITE_IISR(InstancePtr->BaseAddress,
  338. IntrStatus & XEM_EIR_RECV_ALL_MASK);
  339. /*
  340. * Check receive errors and bump statistics so the caller will have a clue
  341. * as to why data may not have been received. We continue on if an error
  342. * occurred since there still may be frames that were received successfully.
  343. */
  344. if (IntrStatus & (XEM_EIR_RECV_LFIFO_OVER_MASK |
  345. XEM_EIR_RECV_DFIFO_OVER_MASK)) {
  346. InstancePtr->Stats.RecvOverrunErrors++;
  347. InstancePtr->Stats.FifoErrors++;
  348. }
  349. if (IntrStatus & XEM_EIR_RECV_LFIFO_UNDER_MASK) {
  350. InstancePtr->Stats.RecvUnderrunErrors++;
  351. InstancePtr->Stats.FifoErrors++;
  352. }
  353. /*
  354. * General receive errors
  355. */
  356. if (IntrStatus & XEM_EIR_RECV_ERROR_MASK) {
  357. if (IntrStatus & XEM_EIR_RECV_MISSED_FRAME_MASK) {
  358. InstancePtr->Stats.RecvMissedFrameErrors =
  359. XIo_In32(InstancePtr->BaseAddress +
  360. XEM_RMFC_OFFSET);
  361. }
  362. if (IntrStatus & XEM_EIR_RECV_COLLISION_MASK) {
  363. InstancePtr->Stats.RecvCollisionErrors =
  364. XIo_In32(InstancePtr->BaseAddress + XEM_RCC_OFFSET);
  365. }
  366. if (IntrStatus & XEM_EIR_RECV_FCS_ERROR_MASK) {
  367. InstancePtr->Stats.RecvFcsErrors =
  368. XIo_In32(InstancePtr->BaseAddress +
  369. XEM_RFCSEC_OFFSET);
  370. }
  371. if (IntrStatus & XEM_EIR_RECV_LEN_ERROR_MASK) {
  372. InstancePtr->Stats.RecvLengthFieldErrors++;
  373. }
  374. if (IntrStatus & XEM_EIR_RECV_SHORT_ERROR_MASK) {
  375. InstancePtr->Stats.RecvShortErrors++;
  376. }
  377. if (IntrStatus & XEM_EIR_RECV_LONG_ERROR_MASK) {
  378. InstancePtr->Stats.RecvLongErrors++;
  379. }
  380. if (IntrStatus & XEM_EIR_RECV_ALIGN_ERROR_MASK) {
  381. InstancePtr->Stats.RecvAlignmentErrors =
  382. XIo_In32(InstancePtr->BaseAddress +
  383. XEM_RAEC_OFFSET);
  384. }
  385. }
  386. /*
  387. * Before reading from the length FIFO, make sure the length FIFO is not
  388. * empty. We could cause an underrun error if we try to read from an
  389. * empty FIFO.
  390. */
  391. if ((IntrStatus & XEM_EIR_RECV_DONE_MASK) == 0) {
  392. return XST_NO_DATA;
  393. }
  394. /*
  395. * Determine, from the MAC, the length of the next packet available
  396. * in the data FIFO (there should be a non-zero length here)
  397. */
  398. PktLength = XIo_In32(InstancePtr->BaseAddress + XEM_RPLR_OFFSET);
  399. if (PktLength == 0) {
  400. return XST_NO_DATA;
  401. }
  402. /*
  403. * Write the RECV_DONE bit in the status register to clear it. This bit
  404. * indicates the RPLR is non-empty, and we know it's set at this point.
  405. * We clear it so that subsequent entry into this routine will reflect the
  406. * current status. This is done because the non-empty bit is latched in the
  407. * IPIF, which means it may indicate a non-empty condition even though
  408. * there is something in the FIFO.
  409. */
  410. XIIF_V123B_WRITE_IISR(InstancePtr->BaseAddress, XEM_EIR_RECV_DONE_MASK);
  411. /*
  412. * We assume that the MAC never has a length bigger than the largest
  413. * Ethernet frame, so no need to make another check here.
  414. */
  415. /*
  416. * This is a non-blocking read. The FIFO returns an error if there is
  417. * not at least the requested amount of data in the FIFO.
  418. */
  419. Result =
  420. XPacketFifoV100b_Read(&InstancePtr->RecvFifo, BufPtr, PktLength);
  421. if (Result != XST_SUCCESS) {
  422. return Result;
  423. }
  424. InstancePtr->Stats.RecvFrames++;
  425. InstancePtr->Stats.RecvBytes += PktLength;
  426. *ByteCountPtr = PktLength;
  427. return XST_SUCCESS;
  428. }