/* * Realtek Otto MIPS platform watchdog * * Watchdog timer that will reset the system after timeout, using the selected * reset mode. * * Counter scaling and timeouts: * - Base prescale of (2 << 25), providing tick duration T_0: 168ms @ 200MHz * - PRESCALE: logarithmic prescaler adding a factor of {1, 2, 4, 8} * - Phase 1: Times out after (PHASE1 + 1) × PRESCALE × T_0 * Generates an interrupt, WDT cannot be stopped after phase 1 * - Phase 2: starts after phase 1, times out after (PHASE2 + 1) × PRESCALE × T_0 * Resets the system according to RST_MODE
*/
/* * One higher than the max values contained in PHASE{1,2}, since a value of 0 * corresponds to one tick.
*/ #define OTTO_WDT_PHASE_TICKS_MAX 32
/* * The maximum reset delay is actually 2×32 ticks, but that would require large * pretimeout values for timeouts longer than 32 ticks. Limit the maximum timeout * to 32 + 1 to ensure small pretimeout values can be configured as expected.
*/ #define OTTO_WDT_TIMEOUT_TICKS_MAX (OTTO_WDT_PHASE_TICKS_MAX + 1)
/* * The timer asserts the PHASE1/PHASE2 IRQs when the number of ticks exceeds * the value stored in those fields. This means each phase will run for at least * one tick, so small values need to be clamped to correctly reflect the timeout.
*/ staticinlineunsignedint div_round_ticks(unsignedint val, unsignedint tick_duration, unsignedint min_ticks)
{ return max(min_ticks, DIV_ROUND_UP(val, tick_duration));
}
/* Configure for shortest timeout and wait for reset to occur */
v = FIELD_PREP(OTTO_WDT_CTRL_RST_MODE, reset_mode) | OTTO_WDT_CTRL_ENABLE;
iowrite32(v, ctrl->base + OTTO_WDT_REG_CTRL);
/* Clear any old interrupts and reset initial state */
iowrite32(OTTO_WDT_INTR_PHASE_1 | OTTO_WDT_INTR_PHASE_2,
ctrl->base + OTTO_WDT_REG_INTR);
iowrite32(OTTO_WDT_CTRL_DEFAULT, ctrl->base + OTTO_WDT_REG_CTRL);
ret = otto_wdt_probe_clk(ctrl); if (ret) return ret;
ctrl->irq_phase1 = platform_get_irq_byname(pdev, "phase1"); if (ctrl->irq_phase1 < 0) return ctrl->irq_phase1;
ret = devm_request_irq(dev, ctrl->irq_phase1, otto_wdt_phase1_isr, 0, "realtek-otto-wdt", ctrl); if (ret) return dev_err_probe(dev, ret, "Failed to get IRQ for phase1\n");
ret = otto_wdt_probe_reset_mode(ctrl); if (ret) return dev_err_probe(dev, ret, "Invalid reset mode specified\n");
/* * Since pretimeout cannot be disabled, min. timeout is twice the * subsystem resolution. Max. timeout is ca. 43s at a bus clock of 200MHz.
*/
ctrl->wdev.min_timeout = 2;
max_tick_ms = otto_wdt_tick_ms(ctrl, OTTO_WDT_PRESCALE_MAX);
ctrl->wdev.max_hw_heartbeat_ms = max_tick_ms * OTTO_WDT_TIMEOUT_TICKS_MAX;
ctrl->wdev.timeout = min(30U, ctrl->wdev.max_hw_heartbeat_ms / 1000);
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.