drivers/rtc/rtc-rx8025.c

Source file repositories/reference/linux-study-clean/drivers/rtc/rtc-rx8025.c

File Facts

System
Linux kernel
Corpus path
drivers/rtc/rtc-rx8025.c
Extension
.c
Size
14701 bytes
Lines
589
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.

Dependency Surface

Detected Declarations

Annotated Snippet

struct rx8025_data {
	struct rtc_device *rtc;
	enum rx_model model;
	u8 ctrl1;
	int is_24;
};

static s32 rx8025_read_reg(const struct i2c_client *client, u8 number)
{
	return i2c_smbus_read_byte_data(client, number << 4);
}

static int rx8025_read_regs(const struct i2c_client *client,
			    u8 number, u8 length, u8 *values)
{
	int ret = i2c_smbus_read_i2c_block_data(client, number << 4, length,
						values);
	if (ret != length)
		return ret < 0 ? ret : -EIO;

	return 0;
}

static s32 rx8025_write_reg(const struct i2c_client *client, u8 number,
			    u8 value)
{
	return i2c_smbus_write_byte_data(client, number << 4, value);
}

static s32 rx8025_write_regs(const struct i2c_client *client,
			     u8 number, u8 length, const u8 *values)
{
	return i2c_smbus_write_i2c_block_data(client, number << 4,
					      length, values);
}

static int rx8025_is_osc_stopped(enum rx_model model, int ctrl2)
{
	int xstp = ctrl2 & RX8025_BIT_CTRL2_XST;
	/* XSTP bit has different polarity on RX-8025 vs RX-8035.
	 * RX-8025: 0 == oscillator stopped
	 * RX-8035: 1 == oscillator stopped
	 */

	if (model == model_rx_8025)
		xstp = !xstp;

	return xstp;
}

static int rx8025_check_validity(struct device *dev)
{
	struct i2c_client *client = to_i2c_client(dev);
	struct rx8025_data *drvdata = dev_get_drvdata(dev);
	int ctrl2;
	int xstp;

	ctrl2 = rx8025_read_reg(client, RX8025_REG_CTRL2);
	if (ctrl2 < 0)
		return ctrl2;

	if (ctrl2 & RX8025_BIT_CTRL2_VDET)
		dev_warn(dev, "power voltage drop detected\n");

	if (ctrl2 & RX8025_BIT_CTRL2_PON) {
		dev_warn(dev, "power-on reset detected, date is invalid\n");
		return -EINVAL;
	}

	xstp = rx8025_is_osc_stopped(drvdata->model, ctrl2);
	if (xstp) {
		dev_warn(dev, "crystal stopped, date is invalid\n");
		return -EINVAL;
	}

	return 0;
}

static int rx8025_reset_validity(struct i2c_client *client)
{
	struct rx8025_data *drvdata = i2c_get_clientdata(client);
	int ctrl2 = rx8025_read_reg(client, RX8025_REG_CTRL2);

	if (ctrl2 < 0)
		return ctrl2;

	ctrl2 &= ~(RX8025_BIT_CTRL2_PON | RX8025_BIT_CTRL2_VDET);

	if (drvdata->model == model_rx_8025)
		ctrl2 |= RX8025_BIT_CTRL2_XST;

Annotation

Implementation Notes