[U-Boot,12/22] x86: Add an early CMOS access library

Message ID 1489674408-17498-13-git-send-email-bmeng.cn@gmail.com
State Accepted
Commit 9f1fad1e365f413e4f6f5a608a70be0e6ba95dc8
Delegated to: Bin Meng
Headers show

Commit Message

Bin Meng March 16, 2017, 2:26 p.m.
This adds a library that provides CMOS (inside RTC SRAM) access
at a very early stage when driver model is not available yet.

Signed-off-by: Bin Meng <bmeng.cn@gmail.com>
---

 arch/x86/include/asm/early_cmos.h | 43 +++++++++++++++++++++++++++++++++
 arch/x86/lib/Makefile             |  1 +
 arch/x86/lib/early_cmos.c         | 51 +++++++++++++++++++++++++++++++++++++++
 3 files changed, 95 insertions(+)
 create mode 100644 arch/x86/include/asm/early_cmos.h
 create mode 100644 arch/x86/lib/early_cmos.c

Comments

Simon Glass March 21, 2017, 8:06 p.m. | #1
Hi Bin,

On 16 March 2017 at 08:26, Bin Meng <bmeng.cn@gmail.com> wrote:
> This adds a library that provides CMOS (inside RTC SRAM) access
> at a very early stage when driver model is not available yet.
>
> Signed-off-by: Bin Meng <bmeng.cn@gmail.com>
> ---
>
>  arch/x86/include/asm/early_cmos.h | 43 +++++++++++++++++++++++++++++++++
>  arch/x86/lib/Makefile             |  1 +
>  arch/x86/lib/early_cmos.c         | 51 +++++++++++++++++++++++++++++++++++++++
>  3 files changed, 95 insertions(+)
>  create mode 100644 arch/x86/include/asm/early_cmos.h
>  create mode 100644 arch/x86/lib/early_cmos.c

Is it possible to share code with the existing driver, like we do with
DEBUG_UART?

Regards,
Simon
Bin Meng April 18, 2017, 9:46 a.m. | #2
Hi Simon,

On Wed, Mar 22, 2017 at 4:06 AM, Simon Glass <sjg@chromium.org> wrote:
> Hi Bin,
>
> On 16 March 2017 at 08:26, Bin Meng <bmeng.cn@gmail.com> wrote:
>> This adds a library that provides CMOS (inside RTC SRAM) access
>> at a very early stage when driver model is not available yet.
>>
>> Signed-off-by: Bin Meng <bmeng.cn@gmail.com>
>> ---
>>
>>  arch/x86/include/asm/early_cmos.h | 43 +++++++++++++++++++++++++++++++++
>>  arch/x86/lib/Makefile             |  1 +
>>  arch/x86/lib/early_cmos.c         | 51 +++++++++++++++++++++++++++++++++++++++
>>  3 files changed, 95 insertions(+)
>>  create mode 100644 arch/x86/include/asm/early_cmos.h
>>  create mode 100644 arch/x86/lib/early_cmos.c
>
> Is it possible to share code with the existing driver, like we do with
> DEBUG_UART?

DEBUG_UART requires every serial driver provides APIs like
_debug_uart_putc(), while this early cmos library wants to share codes
with rtc-uclass.c. Looks not possible to get rid of the udevice
parameter.

Regards,
Bin
Simon Glass April 19, 2017, 12:12 a.m. | #3
On 18 April 2017 at 03:46, Bin Meng <bmeng.cn@gmail.com> wrote:
> Hi Simon,
>
> On Wed, Mar 22, 2017 at 4:06 AM, Simon Glass <sjg@chromium.org> wrote:
>> Hi Bin,
>>
>> On 16 March 2017 at 08:26, Bin Meng <bmeng.cn@gmail.com> wrote:
>>> This adds a library that provides CMOS (inside RTC SRAM) access
>>> at a very early stage when driver model is not available yet.
>>>
>>> Signed-off-by: Bin Meng <bmeng.cn@gmail.com>
>>> ---
>>>
>>>  arch/x86/include/asm/early_cmos.h | 43 +++++++++++++++++++++++++++++++++
>>>  arch/x86/lib/Makefile             |  1 +
>>>  arch/x86/lib/early_cmos.c         | 51 +++++++++++++++++++++++++++++++++++++++
>>>  3 files changed, 95 insertions(+)
>>>  create mode 100644 arch/x86/include/asm/early_cmos.h
>>>  create mode 100644 arch/x86/lib/early_cmos.c
>>
>> Is it possible to share code with the existing driver, like we do with
>> DEBUG_UART?
>
> DEBUG_UART requires every serial driver provides APIs like
> _debug_uart_putc(), while this early cmos library wants to share codes
> with rtc-uclass.c. Looks not possible to get rid of the udevice
> parameter.
>
> Regards,
> Bin

Reviewed-by: Simon Glass <sjg@chromium.org>

Patch

diff --git a/arch/x86/include/asm/early_cmos.h b/arch/x86/include/asm/early_cmos.h
new file mode 100644
index 0000000..cd2634d
--- /dev/null
+++ b/arch/x86/include/asm/early_cmos.h
@@ -0,0 +1,43 @@ 
+/*
+ * Copyright (C) 2017, Bin Meng <bmeng.cn@gmail.com>
+ *
+ * SPDX-License-Identifier:	GPL-2.0+
+ */
+
+#ifndef __EARLY_CMOS_H
+#define __EARLY_CMOS_H
+
+/* CMOS actually resides in the RTC SRAM */
+#define CMOS_IO_PORT	0x70
+
+/**
+ * cmos_read8() - Get 8-bit data stored at the given address
+ *
+ * This reads from CMOS for the 8-bit data stored at the given address.
+ *
+ * @addr:	RTC SRAM address
+ * @return:	8-bit data stored at the given address
+ */
+u8 cmos_read8(u8 addr);
+
+/**
+ * cmos_read16() - Get 16-bit data stored at the given address
+ *
+ * This reads from CMOS for the 16-bit data stored at the given address.
+ *
+ * @addr:	RTC SRAM address
+ * @return:	16-bit data stored at the given address
+ */
+u16 cmos_read16(u8 addr);
+
+/**
+ * cmos_read32() - Get 32-bit data stored at the given address
+ *
+ * This reads from CMOS for the 32-bit data stored at the given address.
+ *
+ * @addr:	RTC SRAM address
+ * @return:	32-bit data stored at the given address
+ */
+u32 cmos_read32(u8 addr);
+
+#endif /* __EARLY_CMOS_H */
diff --git a/arch/x86/lib/Makefile b/arch/x86/lib/Makefile
index c61f931..cd4e976 100644
--- a/arch/x86/lib/Makefile
+++ b/arch/x86/lib/Makefile
@@ -15,6 +15,7 @@  obj-$(CONFIG_CMD_BOOTM) += bootm.o
 endif
 obj-y	+= cmd_boot.o
 obj-$(CONFIG_SEABIOS) += coreboot_table.o
+obj-y	+= early_cmos.o
 obj-$(CONFIG_EFI) += efi/
 obj-y	+= e820.o
 obj-y	+= gcc.o
diff --git a/arch/x86/lib/early_cmos.c b/arch/x86/lib/early_cmos.c
new file mode 100644
index 0000000..fa0b327
--- /dev/null
+++ b/arch/x86/lib/early_cmos.c
@@ -0,0 +1,51 @@ 
+/*
+ * Copyright (C) 2017, Bin Meng <bmeng.cn@gmail.com>
+ *
+ * SPDX-License-Identifier:	GPL-2.0+
+ */
+
+/*
+ * This library provides CMOS (inside RTC SRAM) access routines at a very
+ * early stage when driver model is not available yet. Only read access is
+ * provided. The 16-bit/32-bit read are compatible with driver model RTC
+ * uclass write ops, that data is stored in little-endian mode.
+ */
+
+#include <common.h>
+#include <asm/early_cmos.h>
+#include <asm/io.h>
+
+u8 cmos_read8(u8 addr)
+{
+	outb(addr, CMOS_IO_PORT);
+
+	return inb(CMOS_IO_PORT + 1);
+}
+
+u16 cmos_read16(u8 addr)
+{
+	u16 value = 0;
+	u16 data;
+	int i;
+
+	for (i = 0; i < sizeof(value); i++) {
+		data = cmos_read8(addr + i);
+		value |= data << (i << 3);
+	}
+
+	return value;
+}
+
+u32 cmos_read32(u8 addr)
+{
+	u32 value = 0;
+	u32 data;
+	int i;
+
+	for (i = 0; i < sizeof(value); i++) {
+		data = cmos_read8(addr + i);
+		value |= data << (i << 3);
+	}
+
+	return value;
+}