drivers/rtc/rtc-armada38x.c
Source file repositories/reference/linux-study-clean/drivers/rtc/rtc-armada38x.c
File Facts
- System
- Linux kernel
- Corpus path
drivers/rtc/rtc-armada38x.c- Extension
.c- Size
- 15492 bytes
- Lines
- 581
- Domain
- Driver Families
- Bucket
- drivers/rtc
- Inferred role
- Driver Families: implementation source
- Status
- source implementation candidate
Why This File Exists
Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Uses kernel synchronization; read lock ordering, sleepability, and interrupt context assumptions before translating.
- Touches IRQ or DMA behavior; this matters for the representative real-device path.
- Allocates kernel memory; connect allocation flags and lifetime to context constraints.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/delay.hlinux/io.hlinux/module.hlinux/of.hlinux/platform_device.hlinux/rtc.h
Detected Declarations
struct value_to_freqstruct armada38x_rtcstruct armada38x_rtc_datafunction rtc_delayed_writefunction rtc_update_38x_mbus_timing_paramsfunction rtc_update_8k_mbus_timing_paramsfunction read_rtc_registerfunction read_rtc_register_38x_wafunction armada38x_clear_isrfunction armada38x_unmask_interruptfunction armada8k_clear_isrfunction armada8k_unmask_interruptfunction armada38x_rtc_read_timefunction armada38x_rtc_resetfunction armada38x_rtc_set_timefunction armada38x_rtc_read_alarmfunction armada38x_rtc_set_alarmfunction armada38x_rtc_alarm_irq_enablefunction armada38x_rtc_alarm_irqfunction tofunction armada38x_rtc_read_offsetfunction armada38x_rtc_set_offsetfunction armada38x_rtc_probefunction armada38x_rtc_suspendfunction armada38x_rtc_resume
Annotated Snippet
struct value_to_freq {
u32 value;
u8 freq;
};
struct armada38x_rtc {
struct rtc_device *rtc_dev;
void __iomem *regs;
void __iomem *regs_soc;
spinlock_t lock;
int irq;
bool initialized;
const struct armada38x_rtc_data *data;
struct value_to_freq val_to_freq[];
};
#define ALARM1 0
#define ALARM2 1
#define ALARM_REG(base, alarm) ((base) + (alarm) * sizeof(u32))
struct armada38x_rtc_data {
/* Initialize the RTC-MBUS bridge timing */
void (*update_mbus_timing)(struct armada38x_rtc *rtc);
u32 (*read_rtc_reg)(struct armada38x_rtc *rtc, u8 rtc_reg);
void (*clear_isr)(struct armada38x_rtc *rtc);
void (*unmask_interrupt)(struct armada38x_rtc *rtc);
u32 alarm;
};
/*
* According to the datasheet, the OS should wait 5us after every
* register write to the RTC hard macro so that the required update
* can occur without holding off the system bus
* According to errata RES-3124064, Write to any RTC register
* may fail. As a workaround, before writing to RTC
* register, issue a dummy write of 0x0 twice to RTC Status
* register.
*/
static void rtc_delayed_write(u32 val, struct armada38x_rtc *rtc, int offset)
{
writel(0, rtc->regs + RTC_STATUS);
writel(0, rtc->regs + RTC_STATUS);
writel(val, rtc->regs + offset);
udelay(5);
}
/* Update RTC-MBUS bridge timing parameters */
static void rtc_update_38x_mbus_timing_params(struct armada38x_rtc *rtc)
{
u32 reg;
reg = readl(rtc->regs_soc + RTC_38X_BRIDGE_TIMING_CTL);
reg &= ~RTC_38X_PERIOD_MASK;
reg |= 0x3FF << RTC_38X_PERIOD_OFFS; /* Maximum value */
reg &= ~RTC_38X_READ_DELAY_MASK;
reg |= 0x1F << RTC_38X_READ_DELAY_OFFS; /* Maximum value */
writel(reg, rtc->regs_soc + RTC_38X_BRIDGE_TIMING_CTL);
}
static void rtc_update_8k_mbus_timing_params(struct armada38x_rtc *rtc)
{
u32 reg;
reg = readl(rtc->regs_soc + RTC_8K_BRIDGE_TIMING_CTL0);
reg &= ~RTC_8K_WRCLK_PERIOD_MASK;
reg |= 0x3FF << RTC_8K_WRCLK_PERIOD_OFFS;
reg &= ~RTC_8K_WRCLK_SETUP_MASK;
reg |= 0x29 << RTC_8K_WRCLK_SETUP_OFFS;
writel(reg, rtc->regs_soc + RTC_8K_BRIDGE_TIMING_CTL0);
reg = readl(rtc->regs_soc + RTC_8K_BRIDGE_TIMING_CTL1);
reg &= ~RTC_8K_READ_DELAY_MASK;
reg |= 0x3F << RTC_8K_READ_DELAY_OFFS;
writel(reg, rtc->regs_soc + RTC_8K_BRIDGE_TIMING_CTL1);
}
static u32 read_rtc_register(struct armada38x_rtc *rtc, u8 rtc_reg)
{
return readl(rtc->regs + rtc_reg);
}
static u32 read_rtc_register_38x_wa(struct armada38x_rtc *rtc, u8 rtc_reg)
{
int i, index_max = 0, max = 0;
for (i = 0; i < SAMPLE_NR; i++) {
rtc->val_to_freq[i].value = readl(rtc->regs + rtc_reg);
rtc->val_to_freq[i].freq = 0;
Annotation
- Immediate include surface: `linux/delay.h`, `linux/io.h`, `linux/module.h`, `linux/of.h`, `linux/platform_device.h`, `linux/rtc.h`.
- Detected declarations: `struct value_to_freq`, `struct armada38x_rtc`, `struct armada38x_rtc_data`, `function rtc_delayed_write`, `function rtc_update_38x_mbus_timing_params`, `function rtc_update_8k_mbus_timing_params`, `function read_rtc_register`, `function read_rtc_register_38x_wa`, `function armada38x_clear_isr`, `function armada38x_unmask_interrupt`.
- Atlas domain: Driver Families / drivers/rtc.
- Implementation status: source implementation candidate.
- Synchronization appears in or near this file; preserve lock ordering, sleepability, and interrupt-context constraints.
- IRQ or DMA behavior appears here, which is relevant to the selected PCIe/NVMe device path.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.