Commit 64da3a91 authored by Wesley W. Terpstra's avatar Wesley W. Terpstra

minic: fix race condition => softpll hang

The minic driver reads the TX timestamp from the device after sending.
Unfortunately, it only waited for the data to be enqueued to be sent.
Sometimes this lead to a race condition where the old TX stamp was read.

As a result, the PTP calculation goes wrong by as much as an entire second.
When in track_phase, this manifests as a bad phase offset sent to softpll.
The softpll takes years to reach that phase offset, so it is always busy.
Thus the clock drifts further and further away, never correcting.
parent db67ddf1
......@@ -320,25 +320,33 @@ int minic_tx_frame(uint8_t * hdr, uint8_t * payload, uint32_t size,
mcr = minic_readl(MINIC_REG_MCR);
minic_writel(MINIC_REG_MCR, mcr | MINIC_MCR_TX_START);
i = 0;
do {
/* wait for the DMA to finish */
for (i = 0; i < 1000; ++i) {
mcr = minic_readl(MINIC_REG_MCR);
if (i > 0)
if ((mcr & MINIC_MCR_TX_IDLE) != 0) break;
timer_delay(1);
i++;
} while (((mcr & MINIC_MCR_TX_IDLE) == 0) && (i < 1000));
}
if (i == 1000)
mprintf("Warning: tx not terminated infinite mcr=0x%x\n",mcr);
if (hwts) { /* wait for the timestamp */
if (hwts) {
uint32_t raw_ts;
uint16_t fid;
uint32_t counter_r, counter_f;
uint64_t sec;
uint32_t nsec;
/* wait for the timestamp */
for (i = 0; i < 1000; ++i) {
mcr = minic_readl(MINIC_REG_MCR);
if ((mcr & MINIC_MCR_TX_TS_READY) != 0) break;
timer_delay(1);
}
if (i == 1000)
mprintf("Warning: tx timestamp never became available\n");
ts_valid = (uint8_t)(minic_readl(MINIC_REG_TSR0)
& MINIC_TSR0_VALID);
......@@ -360,11 +368,11 @@ int minic_tx_frame(uint8_t * hdr, uint8_t * payload, uint32_t size,
hwts->sec = sec;
hwts->ahead = 0;
hwts->nsec = counter_r * 8;
// TRACE_DEV("minic_tx_frame [%d bytes] TS: %d.%d valid %d\n", size, hwts->utc, hwts->nsec, hwts->valid);
minic.tx_count++;
}
}
return size;
}
......
......@@ -3,7 +3,7 @@
* File : minic_regs.h
* Author : auto-generated by wbgen2 from mini_nic.wb
* Created : Tue May 29 15:57:15 2012
* Created : Thu Mar 7 14:45:52 2013
* Standard : ANSI C
THIS FILE WAS GENERATED BY wbgen2 FROM SOURCE FILE mini_nic.wb
......@@ -51,6 +51,9 @@
/* definitions for field: RX DMA enable in reg: miNIC Control Register */
#define MINIC_MCR_RX_EN WBGEN2_GEN_MASK(10, 1)
/* definitions for field: TX TS ready in reg: miNIC Control Register */
#define MINIC_MCR_TX_TS_READY WBGEN2_GEN_MASK(11, 1)
/* definitions for field: RX Accepted Packet Classes in reg: miNIC Control Register */
#define MINIC_MCR_RX_CLASS_MASK WBGEN2_GEN_MASK(16, 8)
#define MINIC_MCR_RX_CLASS_SHIFT 16
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment