Skip to contentSkip to conversation

EXYNOS5: FDT: Add I2C device node data

PATCH Superseded Rajeshwari Shinde 5 participants 27 messages Dec 14, 2012 – Dec 26, 2012

Subsystems (5)

v1 of 2 Superseded Latest is v2 →

lore
Share & tools
lore
#0 lore raw

PATCH 1/16 EXYNOS5: FDT: Add I2C device node data

Add I2C device node data for exynos

---
Changes in V1:
-Rebased on latest u-boot-samsung

 arch/arm/dts/exynos5250.dtsi |   64 ++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 64 insertions(+), 0 deletions(-)
arch/arm/dts/exynos5250.dtsi +64 -0
index fa4d498..7a50b2e 100644
@@ -28,4 +28,68 @@
 		#address-cells = <1>;
 		#size-cells = <0>;
 	};
+
+	i2c at 12c60000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,s3c2440-i2c";
+		reg = <0x12C60000 0x100>;
+		interrupts = <0 56 0>;
+	};
+
+	i2c at 12c70000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,s3c2440-i2c";
+		reg = <0x12C70000 0x100>;
+		interrupts = <0 57 0>;
+	};
+
+	i2c at 12c80000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,s3c2440-i2c";
+		reg = <0x12C80000 0x100>;
+		interrupts = <0 58 0>;
+	};
+
+	i2c at 12c90000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,s3c2440-i2c";
+		reg = <0x12C90000 0x100>;
+		interrupts = <0 59 0>;
+	};
+
+	i2c at 12ca0000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,s3c2440-i2c";
+		reg = <0x12CA0000 0x100>;
+		interrupts = <0 60 0>;
+	};
+
+	i2c at 12cb0000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,s3c2440-i2c";
+		reg = <0x12CB0000 0x100>;
+		interrupts = <0 61 0>;
+	};
+
+	i2c at 12cc0000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,s3c2440-i2c";
+		reg = <0x12CC0000 0x100>;
+		interrupts = <0 62 0>;
+	};
+
+	i2c at 12cd0000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,s3c2440-i2c";
+		reg = <0x12CD0000 0x100>;
+		interrupts = <0 63 0>;
+	};
 };
Signature · 1 line
1.7.4.4
#1 lore raw

PATCH 2/16 EXYNOS5 : FDT: Add Aliases for I2C device

This patch adds aliases for I2C.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 board/samsung/dts/exynos5250-smdk5250.dts |   11 +++++++++++
 1 files changed, 11 insertions(+), 0 deletions(-)
board/samsung/dts/exynos5250-smdk5250.dts +11 -0
index b6fbb67..0f971c0 100644
@@ -16,6 +16,17 @@
 	model = "SAMSUNG SMDK5250 board based on EXYNOS5250";
 	compatible = "samsung,smdk5250", "samsung,exynos5250";
 
+	aliases {
+		i2c0 = "/i2c at 12c60000";
+		i2c1 = "/i2c at 12c70000";
+		i2c2 = "/i2c at 12c80000";
+		i2c3 = "/i2c at 12c90000";
+		i2c4 = "/i2c at 12ca0000";
+		i2c5 = "/i2c at 12cb0000";
+		i2c6 = "/i2c at 12cc0000";
+		i2c7 = "/i2c at 12cd0000";
+	};
+
 	sromc at 12250000 {
 		bank = <1>;
 		srom-timing = <1 9 12 1 6 1 1>;
Signature · 1 line
1.7.4.4
#2 lore raw

PATCH 3/16 FDT: Add compatible string for I2C

In reply to Rajeshwari Shinde

Add required compatible information for I2C driver.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 include/fdtdec.h |    1 +
 lib/fdtdec.c     |    1 +
 2 files changed, 2 insertions(+), 0 deletions(-)
include/fdtdec.h +1 -0
index da2054a..567ad13 100644
@@ -70,6 +70,7 @@ enum fdt_compat_id {
 	COMPAT_NVIDIA_TEGRA20_DC,	/* Tegra 2 Display controller */
 	COMPAT_SMSC_LAN9215,		/* SMSC 10/100 Ethernet LAN9215 */
 	COMPAT_SAMSUNG_EXYNOS5_SROMC,	/* Exynos5 SROMC */
+	COMPAT_SAMSUNG_S3C2440_I2C,	/* Exynos I2C Controller */
 
 	COMPAT_COUNT,
 };
lib/fdtdec.c +1 -0
index f10ef5a..6ae2dd0 100644
@@ -47,6 +47,7 @@ static const char * const compat_names[COMPAT_COUNT] = {
 	COMPAT(NVIDIA_TEGRA20_DC, "nvidia,tegra20-dc"),
 	COMPAT(SMSC_LAN9215, "smsc,lan9215"),
 	COMPAT(SAMSUNG_EXYNOS5_SROMC, "samsung,exynos-sromc"),
+	COMPAT(SAMSUNG_S3C2440_I2C, "samsung,s3c2440-i2c"),
 };
 
 const char *fdtdec_get_compatible(enum fdt_compat_id id)
Signature · 1 line
1.7.4.4
#3 lore raw

PATCH 4/16 EXYNOS5: FDT : Decode peripheral id

In reply to Rajeshwari Shinde

Api is added to decode peripheral id based on the interrupt number of the peripheral.

Acked-by; Simon Glass <[email protected]>
---
Changes in V1:
-Rebased on latest u-boot-samsung

 arch/arm/cpu/armv7/exynos/pinmux.c        |   28 ++++++++++++++++++++++++++
 arch/arm/include/asm/arch-exynos/periph.h |   31 ++++++++++++++++------------
 arch/arm/include/asm/arch-exynos/pinmux.h |    8 +++++++
 3 files changed, 54 insertions(+), 13 deletions(-)
arch/arm/cpu/armv7/exynos/pinmux.c +28 -0
index f02f441..f9f6911 100644
@@ -22,6 +22,7 @@
  */
 
 #include <common.h>
+#include <fdtdec.h>
 #include <asm/arch/gpio.h>
 #include <asm/arch/pinmux.h>
 #include <asm/arch/sromc.h>
@@ -396,3 +397,30 @@ int exynos_pinmux_config(int peripheral, int flags)
 		return -1;
 	}
 }
+
+#ifdef CONFIG_OF_CONTROL
+static int exynos5_pinmux_decode_periph_id(const void *blob, int node)
+{
+	int err;
+	u32 cell[3];
+
+	err = fdtdec_get_int_array(blob, node, "interrupts", cell,
+					ARRAY_SIZE(cell));
+	if (err)
+		return PERIPH_ID_NONE;
+
+	if ((131 > cell[1]) || (cell[1] < 31))
+		return cell[1];
+
+	debug(" invalid peripheral id\n");
+	return PERIPH_ID_NONE;
+}
+
+int pinmux_decode_periph_id(const void *blob, int node)
+{
+	if (cpu_is_exynos5())
+		return  exynos5_pinmux_decode_periph_id(blob, node);
+	else
+		return PERIPH_ID_NONE;
+}
+#endif
arch/arm/include/asm/arch-exynos/periph.h +18 -13
index 13abd2d..783b77c 100644
@@ -25,12 +25,17 @@
 #define __ASM_ARM_ARCH_PERIPH_H
 
 /*
- * Peripherals requiring clock/pinmux configuration. List will
+ * Peripherals requiring pinmux configuration0. List will
  * grow with support for more devices getting added.
+ * Numbering based on interrupt table.
  *
  */
 enum periph_id {
-	PERIPH_ID_I2C0,
+	PERIPH_ID_UART0 = 51,
+	PERIPH_ID_UART1,
+	PERIPH_ID_UART2,
+	PERIPH_ID_UART3,
+	PERIPH_ID_I2C0 = 56,
 	PERIPH_ID_I2C1,
 	PERIPH_ID_I2C2,
 	PERIPH_ID_I2C3,
@@ -38,22 +43,22 @@ enum periph_id {
 	PERIPH_ID_I2C5,
 	PERIPH_ID_I2C6,
 	PERIPH_ID_I2C7,
-	PERIPH_ID_I2S1,
-	PERIPH_ID_SDMMC0,
+	PERIPH_ID_SPI0 = 68,
+	PERIPH_ID_SPI1,
+	PERIPH_ID_SPI2,
+	PERIPH_ID_SDMMC0 = 75,
 	PERIPH_ID_SDMMC1,
 	PERIPH_ID_SDMMC2,
 	PERIPH_ID_SDMMC3,
-	PERIPH_ID_SDMMC4,
-	PERIPH_ID_SROMC,
-	PERIPH_ID_SPI0,
-	PERIPH_ID_SPI1,
-	PERIPH_ID_SPI2,
+	PERIPH_ID_I2S1 = 99,
+
+/* Since following peripherals do not have shared peripheral interrupts (SPIs)
+ * they are numbered arbitiraly after the maximum SPIs Exynos has (128)
+ */
+	PERIPH_ID_SROMC = 128,
 	PERIPH_ID_SPI3,
 	PERIPH_ID_SPI4,
-	PERIPH_ID_UART0,
-	PERIPH_ID_UART1,
-	PERIPH_ID_UART2,
-	PERIPH_ID_UART3,
+	PERIPH_ID_SDMMC4,
 
 	PERIPH_ID_COUNT,
 	PERIPH_ID_NONE = -1,
arch/arm/include/asm/arch-exynos/pinmux.h +8 -0
index 10ea736..00cbb0d 100644
@@ -55,4 +55,12 @@ enum {
  */
 int exynos_pinmux_config(int peripheral, int flags);
 
+/**
+ * Decode the peripheral id using the interrpt numbers.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return peripheral id if ok, PERIPH_ID_NONE on error
+ */
+int pinmux_decode_periph_id(const void *blob, int node);
 #endif
Signature · 1 line
1.7.4.4
#4 lore raw

PATCH 4/16 EXYNOS5: FDT : Decode peripheral id

Dear Rajeshwari Shinde,

Quoted 32 lines · Rajeshwari Shinde

Api is added to decode peripheral id based on the interrupt number of the peripheral.

Acked-by; Simon Glass <[email protected]>
---
Changes in V1:
-Rebased on latest u-boot-samsung

 arch/arm/cpu/armv7/exynos/pinmux.c        |   28 ++++++++++++++++++++++++++
 arch/arm/include/asm/arch-exynos/periph.h |   31 ++++++++++++++++------------
 arch/arm/include/asm/arch-exynos/pinmux.h |    8 +++++++
 3 files changed, 54 insertions(+), 13 deletions(-)
arch/arm/cpu/armv7/exynos/pinmux.c +4 -0
index f02f441..f9f6911 100644
@@ -22,6 +22,7 @@
  */
 
 #include <common.h>
+#include <fdtdec.h>
 #include <asm/arch/gpio.h>
 #include <asm/arch/pinmux.h>
 #include <asm/arch/sromc.h>
@@ -396,3 +397,30 @@ int exynos_pinmux_config(int peripheral, int flags)
 		return -1;
 	}
 }
+
+#ifdef CONFIG_OF_CONTROL
+static int exynos5_pinmux_decode_periph_id(const void *blob, int node)

arch/arm/cpu/armv7/exynos/pinmux.c int exynos_pinmux_config(int peripheral, int flags) · line 412

Quoted 10 lines
arch/arm/cpu/armv7/exynos/pinmux.c +10 -0
+{
+	int err;
+	u32 cell[3];
+
+	err = fdtdec_get_int_array(blob, node, "interrupts", cell,
+					ARRAY_SIZE(cell));
+	if (err)
+		return PERIPH_ID_NONE;
+
+	if ((131 > cell[1]) || (cell[1] < 31))

What means 131 and 31?

Quoted 19 lines
arch/arm/cpu/armv7/exynos/pinmux.c +14 -0
+		return cell[1];
+
+	debug(" invalid peripheral id\n");
+	return PERIPH_ID_NONE;
+}
+
+int pinmux_decode_periph_id(const void *blob, int node)
+{
+	if (cpu_is_exynos5())
+		return  exynos5_pinmux_decode_periph_id(blob, node);
+	else
+		return PERIPH_ID_NONE;
+}
+#endif
arch/arm/include/asm/arch-exynos/periph.h +0 -0
index 13abd2d..783b77c 100644

arch/arm/include/asm/arch-exynos/periph.h line 28

Quoted 5 lines
arch/arm/include/asm/arch-exynos/periph.h +1 -1
@@ -25,12 +25,17 @@
 #define __ASM_ARM_ARCH_PERIPH_H
 
 /*
- * Peripherals requiring clock/pinmux configuration. List will
+ * Peripherals requiring pinmux configuration0. List will

configuration0?

Quoted 25 lines
arch/arm/include/asm/arch-exynos/periph.h +10 -3
  * grow with support for more devices getting added.
+ * Numbering based on interrupt table.
  *
  */
 enum periph_id {
-	PERIPH_ID_I2C0,
+	PERIPH_ID_UART0 = 51,
+	PERIPH_ID_UART1,
+	PERIPH_ID_UART2,
+	PERIPH_ID_UART3,
+	PERIPH_ID_I2C0 = 56,
 	PERIPH_ID_I2C1,
 	PERIPH_ID_I2C2,
 	PERIPH_ID_I2C3,
@@ -38,22 +43,22 @@ enum periph_id {
 	PERIPH_ID_I2C5,
 	PERIPH_ID_I2C6,
 	PERIPH_ID_I2C7,
-	PERIPH_ID_I2S1,
-	PERIPH_ID_SDMMC0,
+	PERIPH_ID_SPI0 = 68,
+	PERIPH_ID_SPI1,
+	PERIPH_ID_SPI2,
+	PERIPH_ID_SDMMC0 = 75,
 	PERIPH_ID_SDMMC1,

arch/arm/include/asm/arch-exynos/periph.h enum periph_id { · line 55

Quoted 10 lines
arch/arm/include/asm/arch-exynos/periph.h +3 -5
 	PERIPH_ID_SDMMC2,
 	PERIPH_ID_SDMMC3,
-	PERIPH_ID_SDMMC4,
-	PERIPH_ID_SROMC,
-	PERIPH_ID_SPI0,
-	PERIPH_ID_SPI1,
-	PERIPH_ID_SPI2,
+	PERIPH_ID_I2S1 = 99,
+
+/* Since following peripherals do not have shared peripheral interrupts (SPIs)

Please check multi line comment rule.

Quoted 18 lines
arch/arm/include/asm/arch-exynos/periph.h +4 -4
+ * they are numbered arbitiraly after the maximum SPIs Exynos has (128)
+ */
+	PERIPH_ID_SROMC = 128,
 	PERIPH_ID_SPI3,
 	PERIPH_ID_SPI4,
-	PERIPH_ID_UART0,
-	PERIPH_ID_UART1,
-	PERIPH_ID_UART2,
-	PERIPH_ID_UART3,
+	PERIPH_ID_SDMMC4,
 
 	PERIPH_ID_COUNT,
 	PERIPH_ID_NONE = -1,
arch/arm/include/asm/arch-exynos/pinmux.h +0 -0
index 10ea736..00cbb0d 100644

arch/arm/include/asm/arch-exynos/pinmux.h enum { · line 58

Quoted 4 lines
arch/arm/include/asm/arch-exynos/pinmux.h +1 -0
@@ -55,4 +55,12 @@ enum {
  */
 int exynos_pinmux_config(int peripheral, int flags);
 
+/**

please remove "*".

arch/arm/include/asm/arch-exynos/pinmux.h enum { · line 66

Quoted 9 lines
arch/arm/include/asm/arch-exynos/pinmux.h +7 -0
+ * Decode the peripheral id using the interrpt numbers.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return peripheral id if ok, PERIPH_ID_NONE on error
+ */
+int pinmux_decode_periph_id(const void *blob, int node);
 #endif

--
Thanks,
Minkyu Kang.

#5 lore raw

PATCH 4/16 EXYNOS5: FDT : Decode peripheral id

Hi Minkyu Kang,

Thank you for comments

Quoted 42 lines · Minkyu Kang

Dear Rajeshwari Shinde,

Quoted 9 lines · Rajeshwari Shinde

Api is added to decode peripheral id based on the interrupt number of the peripheral.

Acked-by; Simon Glass <[email protected]>
---
Changes in V1:
-Rebased on latest u-boot-samsung

 arch/arm/cpu/armv7/exynos/pinmux.c        |   28

++++++++++++++++++++++++++

Quoted 1 line
 arch/arm/include/asm/arch-exynos/periph.h |   31

++++++++++++++++------------

Review

Quoted 4 lines
 arch/arm/include/asm/arch-exynos/pinmux.h |    8 +++++++
 3 files changed, 54 insertions(+), 13 deletions(-)
(quoted diff) +0 -0

b/arch/arm/cpu/armv7/exynos/pinmux.c

Quoted 22 lines

index f02f441..f9f6911 100644

arch/arm/cpu/armv7/exynos/pinmux.c +8 -0
@@ -22,6 +22,7 @@
  */
 
 #include <common.h>
+#include <fdtdec.h>
 #include <asm/arch/gpio.h>
 #include <asm/arch/pinmux.h>
 #include <asm/arch/sromc.h>
@@ -396,3 +397,30 @@ int exynos_pinmux_config(int peripheral, int flags)
              return -1;
      }
 }
+
+#ifdef CONFIG_OF_CONTROL
+static int exynos5_pinmux_decode_periph_id(const void *blob, int node)
+{
+     int err;
+     u32 cell[3];
+
Quoted 9 lines

arch/arm/cpu/armv7/exynos/pinmux.c int exynos_pinmux_config(int peripheral, int flags) · line 412

Quoted 6 lines
arch/arm/cpu/armv7/exynos/pinmux.c +6 -0
+     err = fdtdec_get_int_array(blob, node, "interrupts", cell,
+                                     ARRAY_SIZE(cell));
+     if (err)
+             return PERIPH_ID_NONE;
+
+     if ((131 > cell[1]) || (cell[1] < 31))

What means 131 and 31?

will correct and remove magic numbers.
They were the high and lowest interrupt numbers.

Quoted 23 lines

Review

Quoted 16 lines
arch/arm/cpu/armv7/exynos/pinmux.c +14 -0
+             return cell[1];
+
+     debug(" invalid peripheral id\n");
+     return PERIPH_ID_NONE;
+}
+
+int pinmux_decode_periph_id(const void *blob, int node)
+{
+     if (cpu_is_exynos5())
+             return  exynos5_pinmux_decode_periph_id(blob, node);
+     else
+             return PERIPH_ID_NONE;
+}
+#endif
(quoted diff) +0 -0

b/arch/arm/include/asm/arch-exynos/periph.h

Quoted 6 lines

index 13abd2d..783b77c 100644

arch/arm/include/asm/arch-exynos/periph.h +0 -0
@@ -25,12 +25,17 @@
 #define __ASM_ARM_ARCH_PERIPH_H
 
Quoted 6 lines

arch/arm/include/asm/arch-exynos/periph.h line 28

Quoted 3 lines
arch/arm/include/asm/arch-exynos/periph.h +1 -1
 /*
- * Peripherals requiring clock/pinmux configuration. List will
+ * Peripherals requiring pinmux configuration0. List will

configuration0?

- Will correct this

Quoted 38 lines
Quoted 26 lines
arch/arm/include/asm/arch-exynos/periph.h +10 -3
  * grow with support for more devices getting added.
+ * Numbering based on interrupt table.
  *
  */
 enum periph_id {
-     PERIPH_ID_I2C0,
+     PERIPH_ID_UART0 = 51,
+     PERIPH_ID_UART1,
+     PERIPH_ID_UART2,
+     PERIPH_ID_UART3,
+     PERIPH_ID_I2C0 = 56,
      PERIPH_ID_I2C1,
      PERIPH_ID_I2C2,
      PERIPH_ID_I2C3,
@@ -38,22 +43,22 @@ enum periph_id {
      PERIPH_ID_I2C5,
      PERIPH_ID_I2C6,
      PERIPH_ID_I2C7,
-     PERIPH_ID_I2S1,
-     PERIPH_ID_SDMMC0,
+     PERIPH_ID_SPI0 = 68,
+     PERIPH_ID_SPI1,
+     PERIPH_ID_SPI2,
+     PERIPH_ID_SDMMC0 = 75,
      PERIPH_ID_SDMMC1,

arch/arm/include/asm/arch-exynos/periph.h enum periph_id { · line 55

Quoted 10 lines
arch/arm/include/asm/arch-exynos/periph.h +3 -5
      PERIPH_ID_SDMMC2,
      PERIPH_ID_SDMMC3,
-     PERIPH_ID_SDMMC4,
-     PERIPH_ID_SROMC,
-     PERIPH_ID_SPI0,
-     PERIPH_ID_SPI1,
-     PERIPH_ID_SPI2,
+     PERIPH_ID_I2S1 = 99,
+
+/* Since following peripherals do not have shared peripheral interrupts

(SPIs)

Quoted 2 lines

Please check multi line comment rule.

- Will correct this

Quoted 23 lines

Review

Quoted 15 lines
arch/arm/include/asm/arch-exynos/periph.h +4 -4
+ * they are numbered arbitiraly after the maximum SPIs Exynos has (128)
+ */
+     PERIPH_ID_SROMC = 128,
      PERIPH_ID_SPI3,
      PERIPH_ID_SPI4,
-     PERIPH_ID_UART0,
-     PERIPH_ID_UART1,
-     PERIPH_ID_UART2,
-     PERIPH_ID_UART3,
+     PERIPH_ID_SDMMC4,
 
      PERIPH_ID_COUNT,
      PERIPH_ID_NONE = -1,
(quoted diff) +0 -0

b/arch/arm/include/asm/arch-exynos/pinmux.h

Quoted 7 lines

index 10ea736..00cbb0d 100644

arch/arm/include/asm/arch-exynos/pinmux.h +0 -0
@@ -55,4 +55,12 @@ enum {
  */
 int exynos_pinmux_config(int peripheral, int flags);
 
Quoted 4 lines

arch/arm/include/asm/arch-exynos/pinmux.h enum { · line 58

Quoted 1 line
arch/arm/include/asm/arch-exynos/pinmux.h +1 -0
+/**

please remove "*".

- Will correct this

Quoted 20 lines

arch/arm/include/asm/arch-exynos/pinmux.h enum { · line 66

Quoted 10 lines
arch/arm/include/asm/arch-exynos/pinmux.h +7 -0
+ * Decode the peripheral id using the interrpt numbers.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return peripheral id if ok, PERIPH_ID_NONE on error
+ */
+int pinmux_decode_periph_id(const void *blob, int node);
 #endif

--
Thanks,
Minkyu Kang.

_______________________________________________
U-Boot mailing list
U-Boot at lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot

Signature · 2 lines
Regards,
Rajeshwari Shinde
#6 lore raw

PATCH 4/16 EXYNOS5: FDT : Decode peripheral id

Hi,

Quoted 156 lines · Rajeshwari Birje

Hi Minkyu Kang,

Thank you for comments

Quoted 42 lines · Minkyu Kang

Dear Rajeshwari Shinde,

Quoted 9 lines · Rajeshwari Shinde

Api is added to decode peripheral id based on the interrupt number of the peripheral.

Acked-by; Simon Glass <[email protected]>
---
Changes in V1:
-Rebased on latest u-boot-samsung

 arch/arm/cpu/armv7/exynos/pinmux.c        |   28

++++++++++++++++++++++++++

Quoted 1 line
 arch/arm/include/asm/arch-exynos/periph.h |   31

++++++++++++++++------------

Review

Quoted 4 lines
 arch/arm/include/asm/arch-exynos/pinmux.h |    8 +++++++
 3 files changed, 54 insertions(+), 13 deletions(-)
(quoted diff) +0 -0

b/arch/arm/cpu/armv7/exynos/pinmux.c

Quoted 22 lines

index f02f441..f9f6911 100644

arch/arm/cpu/armv7/exynos/pinmux.c +8 -0
@@ -22,6 +22,7 @@
  */
 
 #include <common.h>
+#include <fdtdec.h>
 #include <asm/arch/gpio.h>
 #include <asm/arch/pinmux.h>
 #include <asm/arch/sromc.h>
@@ -396,3 +397,30 @@ int exynos_pinmux_config(int peripheral, int flags)
              return -1;
      }
 }
+
+#ifdef CONFIG_OF_CONTROL
+static int exynos5_pinmux_decode_periph_id(const void *blob, int node)
+{
+     int err;
+     u32 cell[3];
+
Quoted 9 lines

arch/arm/cpu/armv7/exynos/pinmux.c int exynos_pinmux_config(int peripheral, int flags) · line 412

Quoted 6 lines
arch/arm/cpu/armv7/exynos/pinmux.c +6 -0
+     err = fdtdec_get_int_array(blob, node, "interrupts", cell,
+                                     ARRAY_SIZE(cell));
+     if (err)
+             return PERIPH_ID_NONE;
+
+     if ((131 > cell[1]) || (cell[1] < 31))

What means 131 and 31?

will correct and remove magic numbers.
They were the high and lowest interrupt numbers.

Quoted 23 lines

Review

Quoted 16 lines
arch/arm/cpu/armv7/exynos/pinmux.c +14 -0
+             return cell[1];
+
+     debug(" invalid peripheral id\n");
+     return PERIPH_ID_NONE;
+}
+
+int pinmux_decode_periph_id(const void *blob, int node)
+{
+     if (cpu_is_exynos5())
+             return  exynos5_pinmux_decode_periph_id(blob, node);
+     else
+             return PERIPH_ID_NONE;
+}
+#endif
(quoted diff) +0 -0

b/arch/arm/include/asm/arch-exynos/periph.h

Quoted 6 lines

index 13abd2d..783b77c 100644

arch/arm/include/asm/arch-exynos/periph.h +0 -0
@@ -25,12 +25,17 @@
 #define __ASM_ARM_ARCH_PERIPH_H
 
Quoted 6 lines

arch/arm/include/asm/arch-exynos/periph.h line 28

Quoted 3 lines
arch/arm/include/asm/arch-exynos/periph.h +1 -1
 /*
- * Peripherals requiring clock/pinmux configuration. List will
+ * Peripherals requiring pinmux configuration0. List will

configuration0?

- Will correct this

Quoted 38 lines
Quoted 26 lines
arch/arm/include/asm/arch-exynos/periph.h +10 -3
  * grow with support for more devices getting added.
+ * Numbering based on interrupt table.
  *
  */
 enum periph_id {
-     PERIPH_ID_I2C0,
+     PERIPH_ID_UART0 = 51,
+     PERIPH_ID_UART1,
+     PERIPH_ID_UART2,
+     PERIPH_ID_UART3,
+     PERIPH_ID_I2C0 = 56,
      PERIPH_ID_I2C1,
      PERIPH_ID_I2C2,
      PERIPH_ID_I2C3,
@@ -38,22 +43,22 @@ enum periph_id {
      PERIPH_ID_I2C5,
      PERIPH_ID_I2C6,
      PERIPH_ID_I2C7,
-     PERIPH_ID_I2S1,
-     PERIPH_ID_SDMMC0,
+     PERIPH_ID_SPI0 = 68,
+     PERIPH_ID_SPI1,
+     PERIPH_ID_SPI2,
+     PERIPH_ID_SDMMC0 = 75,
      PERIPH_ID_SDMMC1,

arch/arm/include/asm/arch-exynos/periph.h enum periph_id { · line 55

Quoted 10 lines
arch/arm/include/asm/arch-exynos/periph.h +3 -5
      PERIPH_ID_SDMMC2,
      PERIPH_ID_SDMMC3,
-     PERIPH_ID_SDMMC4,
-     PERIPH_ID_SROMC,
-     PERIPH_ID_SPI0,
-     PERIPH_ID_SPI1,
-     PERIPH_ID_SPI2,
+     PERIPH_ID_I2S1 = 99,
+
+/* Since following peripherals do not have shared peripheral interrupts

(SPIs)

Quoted 2 lines

Please check multi line comment rule.

- Will correct this

Quoted 23 lines

Review

Quoted 15 lines
arch/arm/include/asm/arch-exynos/periph.h +4 -4
+ * they are numbered arbitiraly after the maximum SPIs Exynos has (128)
+ */
+     PERIPH_ID_SROMC = 128,
      PERIPH_ID_SPI3,
      PERIPH_ID_SPI4,
-     PERIPH_ID_UART0,
-     PERIPH_ID_UART1,
-     PERIPH_ID_UART2,
-     PERIPH_ID_UART3,
+     PERIPH_ID_SDMMC4,
 
      PERIPH_ID_COUNT,
      PERIPH_ID_NONE = -1,
(quoted diff) +0 -0

b/arch/arm/include/asm/arch-exynos/pinmux.h

Quoted 7 lines

index 10ea736..00cbb0d 100644

arch/arm/include/asm/arch-exynos/pinmux.h +0 -0
@@ -55,4 +55,12 @@ enum {
  */
 int exynos_pinmux_config(int peripheral, int flags);
 
Quoted 5 lines
Quoted 4 lines

arch/arm/include/asm/arch-exynos/pinmux.h enum { · line 58

Quoted 1 line
arch/arm/include/asm/arch-exynos/pinmux.h +1 -0
+/**

please remove "*".

- Will correct this

The extra * indicates a comment with doxygen / DocBook comments, so I think we should keep this if we can. There is a bit of a push in U-Boot to use DocBook now (like include/cbfs.h). The format is slightly different from doxygen but it's probably putting to run a converter to switch over at one point.

Quoted 11 lines
Quoted 11 lines

arch/arm/include/asm/arch-exynos/pinmux.h enum { · line 66

Quoted 11 lines
arch/arm/include/asm/arch-exynos/pinmux.h +7 -0
+ * Decode the peripheral id using the interrpt numbers.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return peripheral id if ok, PERIPH_ID_NONE on error
+ */
+int pinmux_decode_periph_id(const void *blob, int node);
 #endif

Regards,
Simon

#7 lore raw

PATCH 5/16 I2C: Driver changes for FDT support

In reply to Rajeshwari Shinde

Functions added to get the I2C bus number and reset I2C bus using FDT node.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/i2c/s3c24x0_i2c.c |   83 ++++++++++++++++++++++++++++++++++++++++++++-
 drivers/i2c/s3c24x0_i2c.h |    8 ++++
 include/i2c.h             |   26 ++++++++++++++
 3 files changed, 116 insertions(+), 1 deletions(-)
drivers/i2c/s3c24x0_i2c.c +82 -1
index 9bc4c7f..94a093e 100644
@@ -27,9 +27,11 @@
  */
 
 #include <common.h>
+#include <fdtdec.h>
 #ifdef CONFIG_EXYNOS5
 #include <asm/arch/clk.h>
 #include <asm/arch/cpu.h>
+#include <asm/arch/pinmux.h>
 #else
 #include <asm/arch/s3c24x0_cpu.h>
 #endif
@@ -60,7 +62,14 @@
 #define I2C_TIMEOUT 1		/* 1 second */
 
 
-static unsigned int g_current_bus;	/* Stores Current I2C Bus */
+/*
+ * For SPL boot some boards need i2c before SDRAM is initialised so force
+ * variables to live in SRAM
+ */
+static unsigned int g_current_bus __attribute__((section(".data")));
+static struct s3c24x0_i2c_bus i2c_bus[CONFIG_MAX_I2C_NUM]
+			__attribute__((section(".data")));
+static int i2c_busses __attribute__((section(".data")));
 
 #ifndef CONFIG_EXYNOS5
 static int GetI2CSDA(void)
@@ -507,4 +516,76 @@ int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len)
 		(i2c, I2C_WRITE, chip << 1, &xaddr[4 - alen], alen, buffer,
 		 len) != 0);
 }
+
+#ifdef CONFIG_OF_CONTROL
+void board_i2c_init(const void *blob)
+{
+
+	int node_list[CONFIG_MAX_I2C_NUM];
+	int count, i;
+
+	count = fdtdec_find_aliases_for_id(blob, "i2c",
+		COMPAT_SAMSUNG_S3C2440_I2C, node_list,
+		CONFIG_MAX_I2C_NUM);
+	for (i = 0; i < count; i++) {
+		struct s3c24x0_i2c_bus *bus;
+		int node = node_list[i];
+
+		if (node <= 0)
+			continue;
+		bus = &i2c_bus[i];
+		bus->regs = (struct s3c24x0_i2c *)
+			fdtdec_get_addr(blob, node, "reg");
+		bus->id = pinmux_decode_periph_id(blob, node);
+		bus->node = node;
+		bus->bus_num = i2c_busses++;
+		exynos_pinmux_config(bus->id, 0);
+	}
+
+}
+
+static struct s3c24x0_i2c_bus *get_bus(unsigned int bus_idx)
+{
+	if (bus_idx < i2c_busses)
+		return &i2c_bus[bus_idx];
+	debug("Undefined bus: %d\n", bus_idx);
+	return NULL;
+}
+
+int i2c_get_bus_num_fdt(int node)
+{
+	int i;
+
+	for (i = 0; i < i2c_busses; i++) {
+		if (node == i2c_bus[i].node)
+			return i;
+	}
+
+	debug("%s: Can't find any matched I2C bus\n", __func__);
+	return -1;
+}
+
+int i2c_reset_port_fdt(const void *blob, int node)
+{
+	struct s3c24x0_i2c_bus *i2c;
+
+	int bus;
+
+	bus = i2c_get_bus_num_fdt(node);
+	if (bus < 0) {
+		debug("could not get bus for node %d\n", node);
+		return -1;
+	}
+	i2c = get_bus(bus);
+	if (!i2c) {
+		debug("get_bus() failed for node node %d\n", node);
+		return -1;
+	}
+
+	i2c_ch_init(i2c->regs, CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
+
+	return 0;
+}
+#endif
+
 #endif /* CONFIG_HARD_I2C */
drivers/i2c/s3c24x0_i2c.h +8 -0
index 2dd4b06..1243bf1 100644
@@ -30,4 +30,12 @@ struct s3c24x0_i2c {
 	u32	iicds;
 	u32	iiclc;
 };
+
+struct s3c24x0_i2c_bus {
+	int node;	/* device tree node */
+	int bus_num;	/* i2c bus number */
+	struct s3c24x0_i2c *regs;
+	enum periph_id id;
+};
+
 #endif /* _S3C24X0_I2C_H */
include/i2c.h +26 -0
index 16f099d..c60d075 100644
@@ -262,4 +262,30 @@ extern int get_multi_scl_pin(void);
 extern int get_multi_sda_pin(void);
 extern int multi_i2c_init(void);
 #endif
+
+/**
+ * Get FDT values for i2c bus.
+ *
+ * @param blob  Device tree blbo
+ * @return the number of I2C bus
+ */
+void board_i2c_init(const void *blob);
+
+/**
+ * Find the I2C bus number by given a FDT I2C node.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return the number of I2C bus (zero based), or -1 on error
+ */
+int i2c_get_bus_num_fdt(int node);
+
+/**
+ * Reset the I2C bus represented by the given a FDT I2C node.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return 0 if port was reset, -1 if not found
+ */
+int i2c_reset_port_fdt(const void *blob, int node);
 #endif	/* _I2C_H_ */
Signature · 1 line
1.7.4.4
#8 lore raw

PATCH 5/16 I2C: Driver changes for FDT support

Dear Rajeshwari Shinde,

Quoted 47 lines · Rajeshwari Shinde

Functions added to get the I2C bus number and reset I2C bus using FDT node.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/i2c/s3c24x0_i2c.c |   83 ++++++++++++++++++++++++++++++++++++++++++++-
 drivers/i2c/s3c24x0_i2c.h |    8 ++++
 include/i2c.h             |   26 ++++++++++++++
 3 files changed, 116 insertions(+), 1 deletions(-)
drivers/i2c/s3c24x0_i2c.c +10 -1
index 9bc4c7f..94a093e 100644
@@ -27,9 +27,11 @@
  */
 
 #include <common.h>
+#include <fdtdec.h>
 #ifdef CONFIG_EXYNOS5
 #include <asm/arch/clk.h>
 #include <asm/arch/cpu.h>
+#include <asm/arch/pinmux.h>
 #else
 #include <asm/arch/s3c24x0_cpu.h>
 #endif
@@ -60,7 +62,14 @@
 #define I2C_TIMEOUT 1		/* 1 second */
 
 
-static unsigned int g_current_bus;	/* Stores Current I2C Bus */
+/*
+ * For SPL boot some boards need i2c before SDRAM is initialised so force
+ * variables to live in SRAM
+ */
+static unsigned int g_current_bus __attribute__((section(".data")));
+static struct s3c24x0_i2c_bus i2c_bus[CONFIG_MAX_I2C_NUM]
+			__attribute__((section(".data")));
+static int i2c_busses __attribute__((section(".data")));
 
 #ifndef CONFIG_EXYNOS5
 static int GetI2CSDA(void)

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 523

Quoted 8 lines
drivers/i2c/s3c24x0_i2c.c +5 -0
@@ -507,4 +516,76 @@ int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len)
 		(i2c, I2C_WRITE, chip << 1, &xaddr[4 - alen], alen, buffer,
 		 len) != 0);
 }
+
+#ifdef CONFIG_OF_CONTROL
+void board_i2c_init(const void *blob)
+{
+

please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 529

Quoted 6 lines
drivers/i2c/s3c24x0_i2c.c +6 -0
+	int node_list[CONFIG_MAX_I2C_NUM];
+	int count, i;
+
+	count = fdtdec_find_aliases_for_id(blob, "i2c",
+		COMPAT_SAMSUNG_S3C2440_I2C, node_list,
+		CONFIG_MAX_I2C_NUM);

need blank line here.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 532

Quoted 3 lines
drivers/i2c/s3c24x0_i2c.c +3 -0
+	for (i = 0; i < count; i++) {
+		struct s3c24x0_i2c_bus *bus;
+		int node = node_list[i];

How handle if the value of count is bigger than CONFIG_MAX_I2C_NUM?

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 544

Quoted 12 lines
drivers/i2c/s3c24x0_i2c.c +12 -0
+
+		if (node <= 0)
+			continue;
+		bus = &i2c_bus[i];
+		bus->regs = (struct s3c24x0_i2c *)
+			fdtdec_get_addr(blob, node, "reg");
+		bus->id = pinmux_decode_periph_id(blob, node);
+		bus->node = node;
+		bus->bus_num = i2c_busses++;
+		exynos_pinmux_config(bus->id, 0);
+	}
+

please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 550

Quoted 6 lines
drivers/i2c/s3c24x0_i2c.c +6 -0
+}
+
+static struct s3c24x0_i2c_bus *get_bus(unsigned int bus_idx)
+{
+	if (bus_idx < i2c_busses)
+		return &i2c_bus[bus_idx];

need blank line here.

Quoted 11 lines
drivers/i2c/s3c24x0_i2c.c +11 -0
+	debug("Undefined bus: %d\n", bus_idx);
+	return NULL;
+}
+
+int i2c_get_bus_num_fdt(int node)
+{
+	int i;
+
+	for (i = 0; i < i2c_busses; i++) {
+		if (node == i2c_bus[i].node)
+			return i;

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 571

Quoted 10 lines
drivers/i2c/s3c24x0_i2c.c +10 -0
+	}
+
+	debug("%s: Can't find any matched I2C bus\n", __func__);
+	return -1;
+}
+
+int i2c_reset_port_fdt(const void *blob, int node)
+{
+	struct s3c24x0_i2c_bus *i2c;
+

Please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 578

Quoted 7 lines
drivers/i2c/s3c24x0_i2c.c +7 -0
+	int bus;
+
+	bus = i2c_get_bus_num_fdt(node);
+	if (bus < 0) {
+		debug("could not get bus for node %d\n", node);
+		return -1;
+	}

need blank line here.

Quoted 56 lines
drivers/i2c/s3c24x0_i2c.c +12 -0
+	i2c = get_bus(bus);
+	if (!i2c) {
+		debug("get_bus() failed for node node %d\n", node);
+		return -1;
+	}
+
+	i2c_ch_init(i2c->regs, CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
+
+	return 0;
+}
+#endif
+
 #endif /* CONFIG_HARD_I2C */
drivers/i2c/s3c24x0_i2c.h +8 -0
index 2dd4b06..1243bf1 100644
@@ -30,4 +30,12 @@ struct s3c24x0_i2c {
 	u32	iicds;
 	u32	iiclc;
 };
+
+struct s3c24x0_i2c_bus {
+	int node;	/* device tree node */
+	int bus_num;	/* i2c bus number */
+	struct s3c24x0_i2c *regs;
+	enum periph_id id;
+};
+
 #endif /* _S3C24X0_I2C_H */
include/i2c.h +17 -0
index 16f099d..c60d075 100644
@@ -262,4 +262,30 @@ extern int get_multi_scl_pin(void);
 extern int get_multi_sda_pin(void);
 extern int multi_i2c_init(void);
 #endif
+
+/**
+ * Get FDT values for i2c bus.
+ *
+ * @param blob  Device tree blbo
+ * @return the number of I2C bus
+ */
+void board_i2c_init(const void *blob);
+
+/**
+ * Find the I2C bus number by given a FDT I2C node.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return the number of I2C bus (zero based), or -1 on error
+ */
+int i2c_get_bus_num_fdt(int node);

include/i2c.h extern int get_multi_scl_pin(void); · line 291

Quoted 10 lines
include/i2c.h +9 -0
+
+/**
+ * Reset the I2C bus represented by the given a FDT I2C node.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return 0 if port was reset, -1 if not found
+ */
+int i2c_reset_port_fdt(const void *blob, int node);
 #endif	/* _I2C_H_ */

--
Thanks,
Minkyu Kang.

#9 lore raw

PATCH 5/16 I2C: Driver changes for FDT support

Hi Minkyu Kang,

Thank you for comments.Will correct them

Quoted 212 lines · Minkyu Kang

Dear Rajeshwari Shinde,

Quoted 10 lines · Rajeshwari Shinde

Functions added to get the I2C bus number and reset I2C bus using FDT node.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/i2c/s3c24x0_i2c.c |   83

++++++++++++++++++++++++++++++++++++++++++++-

Quoted 21 lines
 drivers/i2c/s3c24x0_i2c.h |    8 ++++
 include/i2c.h             |   26 ++++++++++++++
 3 files changed, 116 insertions(+), 1 deletions(-)
drivers/i2c/s3c24x0_i2c.c +2 -0
index 9bc4c7f..94a093e 100644
@@ -27,9 +27,11 @@
  */
 
 #include <common.h>
+#include <fdtdec.h>
 #ifdef CONFIG_EXYNOS5
 #include <asm/arch/clk.h>
 #include <asm/arch/cpu.h>
+#include <asm/arch/pinmux.h>
 #else
 #include <asm/arch/s3c24x0_cpu.h>
 #endif

drivers/i2c/s3c24x0_i2c.c line 66

Quoted 6 lines
drivers/i2c/s3c24x0_i2c.c +2 -1
@@ -60,7 +62,14 @@
 #define I2C_TIMEOUT 1                /* 1 second */
 
 
-static unsigned int g_current_bus;   /* Stores Current I2C Bus */
+/*
+ * For SPL boot some boards need i2c before SDRAM is initialised so

force

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen,

Quoted 10 lines
drivers/i2c/s3c24x0_i2c.c +6 -0
+ * variables to live in SRAM
+ */
+static unsigned int g_current_bus __attribute__((section(".data")));
+static struct s3c24x0_i2c_bus i2c_bus[CONFIG_MAX_I2C_NUM]
+                     __attribute__((section(".data")));
+static int i2c_busses __attribute__((section(".data")));
 
 #ifndef CONFIG_EXYNOS5
 static int GetI2CSDA(void)
@@ -507,4 +516,76 @@ int i2c_write(uchar chip, uint addr, int alen,

uchar *buffer, int len)

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 523

Quoted 8 lines
drivers/i2c/s3c24x0_i2c.c +5 -0
              (i2c, I2C_WRITE, chip << 1, &xaddr[4 - alen], alen, buffer,
               len) != 0);
 }
+
+#ifdef CONFIG_OF_CONTROL
+void board_i2c_init(const void *blob)
+{
+

please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 529

Quoted 6 lines
drivers/i2c/s3c24x0_i2c.c +6 -0
+     int node_list[CONFIG_MAX_I2C_NUM];
+     int count, i;
+
+     count = fdtdec_find_aliases_for_id(blob, "i2c",
+             COMPAT_SAMSUNG_S3C2440_I2C, node_list,
+             CONFIG_MAX_I2C_NUM);

need blank line here.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 532

Quoted 3 lines
drivers/i2c/s3c24x0_i2c.c +3 -0
+     for (i = 0; i < count; i++) {
+             struct s3c24x0_i2c_bus *bus;
+             int node = node_list[i];

How handle if the value of count is bigger than CONFIG_MAX_I2C_NUM?

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 544

Quoted 12 lines
drivers/i2c/s3c24x0_i2c.c +12 -0
+
+             if (node <= 0)
+                     continue;
+             bus = &i2c_bus[i];
+             bus->regs = (struct s3c24x0_i2c *)
+                     fdtdec_get_addr(blob, node, "reg");
+             bus->id = pinmux_decode_periph_id(blob, node);
+             bus->node = node;
+             bus->bus_num = i2c_busses++;
+             exynos_pinmux_config(bus->id, 0);
+     }
+

please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 550

Quoted 6 lines
drivers/i2c/s3c24x0_i2c.c +6 -0
+}
+
+static struct s3c24x0_i2c_bus *get_bus(unsigned int bus_idx)
+{
+     if (bus_idx < i2c_busses)
+             return &i2c_bus[bus_idx];

need blank line here.

Quoted 11 lines
drivers/i2c/s3c24x0_i2c.c +11 -0
+     debug("Undefined bus: %d\n", bus_idx);
+     return NULL;
+}
+
+int i2c_get_bus_num_fdt(int node)
+{
+     int i;
+
+     for (i = 0; i < i2c_busses; i++) {
+             if (node == i2c_bus[i].node)
+                     return i;

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 571

Quoted 10 lines
drivers/i2c/s3c24x0_i2c.c +10 -0
+     }
+
+     debug("%s: Can't find any matched I2C bus\n", __func__);
+     return -1;
+}
+
+int i2c_reset_port_fdt(const void *blob, int node)
+{
+     struct s3c24x0_i2c_bus *i2c;
+

Please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 578

Quoted 7 lines
drivers/i2c/s3c24x0_i2c.c +7 -0
+     int bus;
+
+     bus = i2c_get_bus_num_fdt(node);
+     if (bus < 0) {
+             debug("could not get bus for node %d\n", node);
+             return -1;
+     }

need blank line here.

Quoted 56 lines
drivers/i2c/s3c24x0_i2c.c +12 -0
+     i2c = get_bus(bus);
+     if (!i2c) {
+             debug("get_bus() failed for node node %d\n", node);
+             return -1;
+     }
+
+     i2c_ch_init(i2c->regs, CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
+
+     return 0;
+}
+#endif
+
 #endif /* CONFIG_HARD_I2C */
drivers/i2c/s3c24x0_i2c.h +8 -0
index 2dd4b06..1243bf1 100644
@@ -30,4 +30,12 @@ struct s3c24x0_i2c {
      u32     iicds;
      u32     iiclc;
 };
+
+struct s3c24x0_i2c_bus {
+     int node;       /* device tree node */
+     int bus_num;    /* i2c bus number */
+     struct s3c24x0_i2c *regs;
+     enum periph_id id;
+};
+
 #endif /* _S3C24X0_I2C_H */
include/i2c.h +17 -0
index 16f099d..c60d075 100644
@@ -262,4 +262,30 @@ extern int get_multi_scl_pin(void);
 extern int get_multi_sda_pin(void);
 extern int multi_i2c_init(void);
 #endif
+
+/**
+ * Get FDT values for i2c bus.
+ *
+ * @param blob  Device tree blbo
+ * @return the number of I2C bus
+ */
+void board_i2c_init(const void *blob);
+
+/**
+ * Find the I2C bus number by given a FDT I2C node.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return the number of I2C bus (zero based), or -1 on error
+ */
+int i2c_get_bus_num_fdt(int node);

include/i2c.h extern int get_multi_scl_pin(void); · line 291

Quoted 10 lines
include/i2c.h +9 -0
+
+/**
+ * Reset the I2C bus represented by the given a FDT I2C node.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return 0 if port was reset, -1 if not found
+ */
+int i2c_reset_port_fdt(const void *blob, int node);
 #endif       /* _I2C_H_ */

--
Thanks,
Minkyu Kang.
_______________________________________________
U-Boot mailing list
U-Boot at lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot

Signature · 2 lines
Regards,
Rajeshwari Shinde
#10 lore raw

PATCH 5/16 I2C: Driver changes for FDT support

In reply to Minkyu Kang

Hi Minkyu Kang,

Quoted 71 lines · Minkyu Kang

Dear Rajeshwari Shinde,

Quoted 10 lines · Rajeshwari Shinde

Functions added to get the I2C bus number and reset I2C bus using FDT node.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/i2c/s3c24x0_i2c.c |   83

++++++++++++++++++++++++++++++++++++++++++++-

Quoted 21 lines
 drivers/i2c/s3c24x0_i2c.h |    8 ++++
 include/i2c.h             |   26 ++++++++++++++
 3 files changed, 116 insertions(+), 1 deletions(-)
drivers/i2c/s3c24x0_i2c.c +2 -0
index 9bc4c7f..94a093e 100644
@@ -27,9 +27,11 @@
  */
 
 #include <common.h>
+#include <fdtdec.h>
 #ifdef CONFIG_EXYNOS5
 #include <asm/arch/clk.h>
 #include <asm/arch/cpu.h>
+#include <asm/arch/pinmux.h>
 #else
 #include <asm/arch/s3c24x0_cpu.h>
 #endif

drivers/i2c/s3c24x0_i2c.c line 66

Quoted 6 lines
drivers/i2c/s3c24x0_i2c.c +2 -1
@@ -60,7 +62,14 @@
 #define I2C_TIMEOUT 1                /* 1 second */
 
 
-static unsigned int g_current_bus;   /* Stores Current I2C Bus */
+/*
+ * For SPL boot some boards need i2c before SDRAM is initialised so

force

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen,

Quoted 10 lines
drivers/i2c/s3c24x0_i2c.c +6 -0
+ * variables to live in SRAM
+ */
+static unsigned int g_current_bus __attribute__((section(".data")));
+static struct s3c24x0_i2c_bus i2c_bus[CONFIG_MAX_I2C_NUM]
+                     __attribute__((section(".data")));
+static int i2c_busses __attribute__((section(".data")));
 
 #ifndef CONFIG_EXYNOS5
 static int GetI2CSDA(void)
@@ -507,4 +516,76 @@ int i2c_write(uchar chip, uint addr, int alen,

uchar *buffer, int len)

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 523

Quoted 8 lines
drivers/i2c/s3c24x0_i2c.c +5 -0
              (i2c, I2C_WRITE, chip << 1, &xaddr[4 - alen], alen, buffer,
               len) != 0);
 }
+
+#ifdef CONFIG_OF_CONTROL
+void board_i2c_init(const void *blob)
+{
+

please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 529

Quoted 6 lines
drivers/i2c/s3c24x0_i2c.c +6 -0
+     int node_list[CONFIG_MAX_I2C_NUM];
+     int count, i;
+
+     count = fdtdec_find_aliases_for_id(blob, "i2c",
+             COMPAT_SAMSUNG_S3C2440_I2C, node_list,
+             CONFIG_MAX_I2C_NUM);
Quoted 8 lines

need blank line here.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 532

Quoted 3 lines
drivers/i2c/s3c24x0_i2c.c +3 -0
+     for (i = 0; i < count; i++) {
+             struct s3c24x0_i2c_bus *bus;
+             int node = node_list[i];

How handle if the value of count is bigger than CONFIG_MAX_I2C_NUM?

CONFIG_MAX_I2C_NUM is maximum number of I2C lines supported.
if count bigger than CONFIG_MAX_I2C_NUM then it is error. So you want me to add a check here?

Quoted 134 lines

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 544

Quoted 13 lines
drivers/i2c/s3c24x0_i2c.c +12 -0
+
+             if (node <= 0)
+                     continue;
+             bus = &i2c_bus[i];
+             bus->regs = (struct s3c24x0_i2c *)
+                     fdtdec_get_addr(blob, node, "reg");
+             bus->id = pinmux_decode_periph_id(blob, node);
+             bus->node = node;
+             bus->bus_num = i2c_busses++;
+             exynos_pinmux_config(bus->id, 0);
+     }
+

please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 550

Quoted 6 lines
drivers/i2c/s3c24x0_i2c.c +6 -0
+}
+
+static struct s3c24x0_i2c_bus *get_bus(unsigned int bus_idx)
+{
+     if (bus_idx < i2c_busses)
+             return &i2c_bus[bus_idx];

need blank line here.

Quoted 11 lines
drivers/i2c/s3c24x0_i2c.c +11 -0
+     debug("Undefined bus: %d\n", bus_idx);
+     return NULL;
+}
+
+int i2c_get_bus_num_fdt(int node)
+{
+     int i;
+
+     for (i = 0; i < i2c_busses; i++) {
+             if (node == i2c_bus[i].node)
+                     return i;

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 571

Quoted 10 lines
drivers/i2c/s3c24x0_i2c.c +10 -0
+     }
+
+     debug("%s: Can't find any matched I2C bus\n", __func__);
+     return -1;
+}
+
+int i2c_reset_port_fdt(const void *blob, int node)
+{
+     struct s3c24x0_i2c_bus *i2c;
+

Please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 578

Quoted 7 lines
drivers/i2c/s3c24x0_i2c.c +7 -0
+     int bus;
+
+     bus = i2c_get_bus_num_fdt(node);
+     if (bus < 0) {
+             debug("could not get bus for node %d\n", node);
+             return -1;
+     }

need blank line here.

Quoted 56 lines
drivers/i2c/s3c24x0_i2c.c +12 -0
+     i2c = get_bus(bus);
+     if (!i2c) {
+             debug("get_bus() failed for node node %d\n", node);
+             return -1;
+     }
+
+     i2c_ch_init(i2c->regs, CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
+
+     return 0;
+}
+#endif
+
 #endif /* CONFIG_HARD_I2C */
drivers/i2c/s3c24x0_i2c.h +8 -0
index 2dd4b06..1243bf1 100644
@@ -30,4 +30,12 @@ struct s3c24x0_i2c {
      u32     iicds;
      u32     iiclc;
 };
+
+struct s3c24x0_i2c_bus {
+     int node;       /* device tree node */
+     int bus_num;    /* i2c bus number */
+     struct s3c24x0_i2c *regs;
+     enum periph_id id;
+};
+
 #endif /* _S3C24X0_I2C_H */
include/i2c.h +17 -0
index 16f099d..c60d075 100644
@@ -262,4 +262,30 @@ extern int get_multi_scl_pin(void);
 extern int get_multi_sda_pin(void);
 extern int multi_i2c_init(void);
 #endif
+
+/**
+ * Get FDT values for i2c bus.
+ *
+ * @param blob  Device tree blbo
+ * @return the number of I2C bus
+ */
+void board_i2c_init(const void *blob);
+
+/**
+ * Find the I2C bus number by given a FDT I2C node.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return the number of I2C bus (zero based), or -1 on error
+ */
+int i2c_get_bus_num_fdt(int node);

include/i2c.h extern int get_multi_scl_pin(void); · line 291

Quoted 10 lines
include/i2c.h +9 -0
+
+/**
+ * Reset the I2C bus represented by the given a FDT I2C node.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return 0 if port was reset, -1 if not found
+ */
+int i2c_reset_port_fdt(const void *blob, int node);
 #endif       /* _I2C_H_ */

--
Thanks,
Minkyu Kang.
_______________________________________________
U-Boot mailing list
U-Boot at lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot

Signature · 2 lines
Regards,
Rajeshwari Shinde
#11 lore raw

PATCH 5/16 I2C: Driver changes for FDT support

Quoted 82 lines · Rajeshwari Birje

Hi Minkyu Kang,

Quoted 49 lines · Minkyu Kang

Dear Rajeshwari Shinde,

Quoted 10 lines · Rajeshwari Shinde

Functions added to get the I2C bus number and reset I2C bus using FDT node.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/i2c/s3c24x0_i2c.c |   83

++++++++++++++++++++++++++++++++++++++++++++-

Quoted 21 lines
 drivers/i2c/s3c24x0_i2c.h |    8 ++++
 include/i2c.h             |   26 ++++++++++++++
 3 files changed, 116 insertions(+), 1 deletions(-)
drivers/i2c/s3c24x0_i2c.c +2 -0
index 9bc4c7f..94a093e 100644
@@ -27,9 +27,11 @@
  */
 
 #include <common.h>
+#include <fdtdec.h>
 #ifdef CONFIG_EXYNOS5
 #include <asm/arch/clk.h>
 #include <asm/arch/cpu.h>
+#include <asm/arch/pinmux.h>
 #else
 #include <asm/arch/s3c24x0_cpu.h>
 #endif

drivers/i2c/s3c24x0_i2c.c line 66

Quoted 6 lines
drivers/i2c/s3c24x0_i2c.c +2 -1
@@ -60,7 +62,14 @@
 #define I2C_TIMEOUT 1                /* 1 second */
 
 
-static unsigned int g_current_bus;   /* Stores Current I2C Bus */
+/*
+ * For SPL boot some boards need i2c before SDRAM is initialised so

force

Quoted 7 lines
drivers/i2c/s3c24x0_i2c.c +6 -0
+ * variables to live in SRAM
+ */
+static unsigned int g_current_bus __attribute__((section(".data")));
+static struct s3c24x0_i2c_bus i2c_bus[CONFIG_MAX_I2C_NUM]
+                     __attribute__((section(".data")));
+static int i2c_busses __attribute__((section(".data")));
 
Quoted 5 lines

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen,

Quoted 3 lines
drivers/i2c/s3c24x0_i2c.c +0 -0
 #ifndef CONFIG_EXYNOS5
 static int GetI2CSDA(void)
@@ -507,4 +516,76 @@ int i2c_write(uchar chip, uint addr, int alen,

uchar *buffer, int len)

Quoted 1 line
drivers/i2c/s3c24x0_i2c.c +0 -0
              (i2c, I2C_WRITE, chip << 1, &xaddr[4 - alen], alen,

buffer,

Quoted 23 lines

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 523

Quoted 7 lines
drivers/i2c/s3c24x0_i2c.c +5 -0
               len) != 0);
 }
+
+#ifdef CONFIG_OF_CONTROL
+void board_i2c_init(const void *blob)
+{
+

please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 529

Quoted 6 lines
drivers/i2c/s3c24x0_i2c.c +6 -0
+     int node_list[CONFIG_MAX_I2C_NUM];
+     int count, i;
+
+     count = fdtdec_find_aliases_for_id(blob, "i2c",
+             COMPAT_SAMSUNG_S3C2440_I2C, node_list,
+             CONFIG_MAX_I2C_NUM);

need blank line here.

Quoted 3 lines
drivers/i2c/s3c24x0_i2c.c +3 -0
+     for (i = 0; i < count; i++) {
+             struct s3c24x0_i2c_bus *bus;
+             int node = node_list[i];
Quoted 6 lines
Quoted 2 lines

How handle if the value of count is bigger than CONFIG_MAX_I2C_NUM?

CONFIG_MAX_I2C_NUM is maximum number of I2C lines supported.
if count bigger than CONFIG_MAX_I2C_NUM then it is error. So you want me to add a check here?

It seems to check at fdtdec_find_aliases_fo_id function. Then OK, enough.

Quoted 149 lines
Quoted 58 lines
Quoted 4 lines
drivers/i2c/s3c24x0_i2c.c +2 -0
+
+             if (node <= 0)

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 544

Quoted 10 lines
drivers/i2c/s3c24x0_i2c.c +10 -0
+                     continue;
+             bus = &i2c_bus[i];
+             bus->regs = (struct s3c24x0_i2c *)
+                     fdtdec_get_addr(blob, node, "reg");
+             bus->id = pinmux_decode_periph_id(blob, node);
+             bus->node = node;
+             bus->bus_num = i2c_busses++;
+             exynos_pinmux_config(bus->id, 0);
+     }
+

please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 550

Quoted 6 lines
drivers/i2c/s3c24x0_i2c.c +6 -0
+}
+
+static struct s3c24x0_i2c_bus *get_bus(unsigned int bus_idx)
+{
+     if (bus_idx < i2c_busses)
+             return &i2c_bus[bus_idx];

need blank line here.

Quoted 11 lines
drivers/i2c/s3c24x0_i2c.c +11 -0
+     debug("Undefined bus: %d\n", bus_idx);
+     return NULL;
+}
+
+int i2c_get_bus_num_fdt(int node)
+{
+     int i;
+
+     for (i = 0; i < i2c_busses; i++) {
+             if (node == i2c_bus[i].node)
+                     return i;

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 571

Quoted 10 lines
drivers/i2c/s3c24x0_i2c.c +10 -0
+     }
+
+     debug("%s: Can't find any matched I2C bus\n", __func__);
+     return -1;
+}
+
+int i2c_reset_port_fdt(const void *blob, int node)
+{
+     struct s3c24x0_i2c_bus *i2c;
+

Please remove this blank line.

drivers/i2c/s3c24x0_i2c.c int i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len) · line 578

Quoted 7 lines
drivers/i2c/s3c24x0_i2c.c +7 -0
+     int bus;
+
+     bus = i2c_get_bus_num_fdt(node);
+     if (bus < 0) {
+             debug("could not get bus for node %d\n", node);
+             return -1;
+     }
Quoted 9 lines

need blank line here.

Quoted 7 lines
drivers/i2c/s3c24x0_i2c.c +7 -0
+     i2c = get_bus(bus);
+     if (!i2c) {
+             debug("get_bus() failed for node node %d\n", node);
+             return -1;
+     }
+
+     i2c_ch_init(i2c->regs, CONFIG_SYS_I2C_SPEED,

CONFIG_SYS_I2C_SLAVE);

Quoted 60 lines
Quoted 49 lines
drivers/i2c/s3c24x0_i2c.c +5 -0
+
+     return 0;
+}
+#endif
+
 #endif /* CONFIG_HARD_I2C */
drivers/i2c/s3c24x0_i2c.h +8 -0
index 2dd4b06..1243bf1 100644
@@ -30,4 +30,12 @@ struct s3c24x0_i2c {
      u32     iicds;
      u32     iiclc;
 };
+
+struct s3c24x0_i2c_bus {
+     int node;       /* device tree node */
+     int bus_num;    /* i2c bus number */
+     struct s3c24x0_i2c *regs;
+     enum periph_id id;
+};
+
 #endif /* _S3C24X0_I2C_H */
include/i2c.h +17 -0
index 16f099d..c60d075 100644
@@ -262,4 +262,30 @@ extern int get_multi_scl_pin(void);
 extern int get_multi_sda_pin(void);
 extern int multi_i2c_init(void);
 #endif
+
+/**
+ * Get FDT values for i2c bus.
+ *
+ * @param blob  Device tree blbo
+ * @return the number of I2C bus
+ */
+void board_i2c_init(const void *blob);
+
+/**
+ * Find the I2C bus number by given a FDT I2C node.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return the number of I2C bus (zero based), or -1 on error
+ */
+int i2c_get_bus_num_fdt(int node);

include/i2c.h extern int get_multi_scl_pin(void); · line 291

Quoted 10 lines
include/i2c.h +9 -0
+
+/**
+ * Reset the I2C bus represented by the given a FDT I2C node.
+ *
+ * @param blob  Device tree blbo
+ * @param node  FDT I2C node to find
+ * @return 0 if port was reset, -1 if not found
+ */
+int i2c_reset_port_fdt(const void *blob, int node);
 #endif       /* _I2C_H_ */
Quoted 8 lines

--
Thanks,
Minkyu Kang.
_______________________________________________
U-Boot mailing list
U-Boot at lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot

--
Regards,
Rajeshwari Shinde

_______________________________________________
U-Boot mailing list
U-Boot at lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot

Signature · 2 lines
from. prom.
www.promsoft.net
#12 lore raw

PATCH 6/16 SMDK5250: Initialise I2C using FDT

In reply to Rajeshwari Shinde

This patch initialises I2C using FDT.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 board/samsung/smdk5250/smdk5250.c |   20 +-------------------
 1 files changed, 1 insertions(+), 19 deletions(-)
board/samsung/smdk5250/smdk5250.c +1 -19
index ac7346d..4d24978 100644
@@ -236,24 +236,6 @@ static int board_uart_init(void)
 	return 0;
 }
 
-#ifdef CONFIG_SYS_I2C_INIT_BOARD
-static int board_i2c_init(void)
-{
-	int i, err;
-
-	for (i = 0; i < CONFIG_MAX_I2C_NUM; i++) {
-		err = exynos_pinmux_config((PERIPH_ID_I2C0 + i),
-						PINMUX_FLAG_NONE);
-		if (err) {
-			debug("I2C%d not configured\n", (PERIPH_ID_I2C0 + i));
-			return err;
-		}
-	}
-	i2c_init(CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
-	return 0;
-}
-#endif
-
 #ifdef CONFIG_BOARD_EARLY_INIT_F
 int board_early_init_f(void)
 {
@@ -264,7 +246,7 @@ int board_early_init_f(void)
 		return err;
 	}
 #ifdef CONFIG_SYS_I2C_INIT_BOARD
-	err = board_i2c_init();
+	board_i2c_init(gd->fdt_blob);
 #endif
 	return err;
 }
Signature · 1 line
1.7.4.4
#13 lore raw

PATCH 7/16 EXYNOS5: FDT: Add sound device node data

In reply to Rajeshwari Shinde

Add sound device node data for exynos

---
Changes in V1:
-Rebased on latest u-boot-samsung

 arch/arm/dts/exynos5250.dtsi              |    5 +++++
 doc/device-tree-bindings/exynos/sound.txt |   27 +++++++++++++++++++++++++++
 2 files changed, 32 insertions(+), 0 deletions(-)
 create mode 100644 doc/device-tree-bindings/exynos/sound.txt
arch/arm/dts/exynos5250.dtsi +5 -0
index 7a50b2e..dc13f29 100644
@@ -92,4 +92,9 @@
 		reg = <0x12CD0000 0x100>;
 		interrupts = <0 63 0>;
 	};
+
+	sound at 12d60000 {
+		compatible = "samsung,exynos-sound";
+		reg = <0x12d60000 0x20>;
+	};
 };
doc/device-tree-bindings/exynos/sound.txt new file +27 -0
new file mode 100644
index 0000000..98d1798
@@ -0,0 +1,27 @@
+Exynos Sound Subsystem
+
+The device node for sound subsytem which contains codec and i2s block
+that is a part of Exynos5250
+
+Required properties :
+ - compatible : Should be "samsung,exynos-sound" for sound
+ - samsung,i2s-epll-clock-frequency : epll clock output frequency in Hz
+ - samsung,i2s-sampling-rate : sampling rate, default is 48000
+ - samsung,i2s-bits-per-sample : sample width, defalut is 16 bit
+ - samsung,i2s-channels : nummber of channels, default is 2
+ - samsung,i2s-lr-clk-framesize : lr clock frame size
+ - samsung,i2s-bit-clk-framesize : bit clock frame size
+ - samsung,codec-type : sound codec type
+
+Example:
+
+sound at 12d60000 {
+	compatible = "samsung,exynos-sound"
+	samsung,i2s-epll-clock-frequency = <192000000>;
+	samsung,i2s-sampling-rate = <48000>;
+	samsung,i2s-bits-per-sample = <16>;
+	samsung,i2s-channels = <2>;
+	samsung,i2s-lr-clk-framesize = <256>;
+	samsung,i2s-bit-clk-framesize = <32>;
+	samsung,codec-type = "wm8994";
+};
Signature · 1 line
1.7.4.4
#14 lore raw

PATCH 8/16 EXYNOS5: FDT: Add sound and codec device node

In reply to Rajeshwari Shinde

Adds sound and codec device node parameters

---
Changes in V1:
-Rebased on latest u-boot-samsung

 board/samsung/dts/exynos5250-smdk5250.dts |   17 +++++++++++++++++
 1 files changed, 17 insertions(+), 0 deletions(-)
board/samsung/dts/exynos5250-smdk5250.dts +17 -0
index 0f971c0..14f73d8 100644
@@ -37,4 +37,21 @@
 			phy-mode = "mii";
 		};
 	};
+
+	sound at 12d60000 {
+		samsung,i2s-epll-clock-frequency = <192000000>;
+		samsung,i2s-sampling-rate = <48000>;
+		samsung,i2s-bits-per-sample = <16>;
+		samsung,i2s-channels = <2>;
+		samsung,i2s-lr-clk-framesize = <256>;
+		samsung,i2s-bit-clk-framesize = <32>;
+		samsung,codec-type = "wm8994";
+	};
+
+	i2c at 12c70000 {
+		soundcodec at 1a {
+			reg = <0x1a>;
+			compatible = "wolfson,wm8994-codec";
+		};
+	};
 };
Signature · 1 line
1.7.4.4
#15 lore raw

PATCH 9/16 EXYNOS5: FDT: Add compatible strings for sound

In reply to Rajeshwari Shinde

Add required compatible information for sound driver.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 include/fdtdec.h |    2 ++
 lib/fdtdec.c     |    2 ++
 2 files changed, 4 insertions(+), 0 deletions(-)
include/fdtdec.h +2 -0
index 567ad13..976c9f3 100644
@@ -71,6 +71,8 @@ enum fdt_compat_id {
 	COMPAT_SMSC_LAN9215,		/* SMSC 10/100 Ethernet LAN9215 */
 	COMPAT_SAMSUNG_EXYNOS5_SROMC,	/* Exynos5 SROMC */
 	COMPAT_SAMSUNG_S3C2440_I2C,	/* Exynos I2C Controller */
+	COMPAT_SAMSUNG_EXYNOS5_SOUND,	/* Exynos Sound */
+	COMPAT_WOLFSON_WM8994_CODEC,	/* Wolfson WM8994 Sound Codec */
 
 	COMPAT_COUNT,
 };
lib/fdtdec.c +2 -0
index 6ae2dd0..43affaa 100644
@@ -48,6 +48,8 @@ static const char * const compat_names[COMPAT_COUNT] = {
 	COMPAT(SMSC_LAN9215, "smsc,lan9215"),
 	COMPAT(SAMSUNG_EXYNOS5_SROMC, "samsung,exynos-sromc"),
 	COMPAT(SAMSUNG_S3C2440_I2C, "samsung,s3c2440-i2c"),
+	COMPAT(SAMSUNG_EXYNOS5_SOUND, "samsung,exynos-sound"),
+	COMPAT(WOLFSON_WM8994_CODEC, "wolfson,wm8994-codec"),
 };
 
 const char *fdtdec_get_compatible(enum fdt_compat_id id)
Signature · 1 line
1.7.4.4
#16 lore raw

PATCH 10/16 Sound: Add FDT support to driver

In reply to Rajeshwari Shinde

This patch adds FDT support to the sound driver.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/sound/sound.c |  173 +++++++++++++++++++++++++++++--------------------
 include/sound.h       |    4 +-
 2 files changed, 105 insertions(+), 72 deletions(-)
drivers/sound/sound.c +102 -69
index 4c74534..fa8432d 100644
@@ -24,111 +24,159 @@
 #include <malloc.h>
 #include <common.h>
 #include <asm/io.h>
+#include <libfdt.h>
+#include <fdtdec.h>
 #include <i2c.h>
 #include <i2s.h>
 #include <sound.h>
-#include "wm8994.h"
 #include <asm/arch/sound.h>
+#include "wm8994.h"
 
 /* defines */
 #define SOUND_400_HZ 400
 #define SOUND_BITS_IN_BYTE 8
 
 static struct i2stx_info g_i2stx_pri;
-static struct sound_codec_info g_codec_info;
 
 /*
- * get_sound_fdt_values gets fdt values for i2s parameters
+ * get_sound_i2s_values gets values for i2s parameters
  *
  * @param i2stx_info	i2s transmitter transfer param structure
- * @param blob		FDT blob
- */
-static void get_sound_i2s_values(struct i2stx_info *i2s)
-{
-	i2s->base_address = samsung_get_base_i2s();
-	i2s->audio_pll_clk = I2S_PLL_CLK;
-	i2s->samplingrate = I2S_SAMPLING_RATE;
-	i2s->bitspersample = I2S_BITS_PER_SAMPLE;
-	i2s->channels = I2S_CHANNELS;
-	i2s->rfs = I2S_RFS;
-	i2s->bfs = I2S_BFS;
-}
-
-/*
- * Gets fdt values for wm8994 config parameters
- *
- * @param pcodec_info	codec information structure
- * @param blob		FDT blob
- * @return		int value, 0 for success
+ * @param blob		FDT blob if enabled else NULL
  */
-static int get_sound_wm8994_values(struct sound_codec_info *pcodec_info)
+static int get_sound_i2s_values(struct i2stx_info *i2s, const void *blob)
 {
+#ifdef CONFIG_OF_CONTROL
+	int node;
 	int error = 0;
+	int base;
 
-	switch (AUDIO_COMPAT) {
-	case AUDIO_COMPAT_SPI:
-		debug("%s: Support not added for SPI interface\n", __func__);
+	node = fdtdec_next_compatible(blob, 0,
+					COMPAT_SAMSUNG_EXYNOS5_SOUND);
+	if (node <= 0) {
+		debug("EXYNOS_SOUND: No node for sound in device tree\n");
 		return -1;
-		break;
-	case AUDIO_COMPAT_I2C:
-		pcodec_info->i2c_bus = AUDIO_I2C_BUS;
-		pcodec_info->i2c_dev_addr = AUDIO_I2C_REG;
-		debug("i2c dev addr = %d\n", pcodec_info->i2c_dev_addr);
-		break;
-	default:
-		debug("%s: Unknown compat id %d\n", __func__, AUDIO_COMPAT);
+	}
+
+	/*
+	 * Get the pre-defined sound specific values from FDT.
+	 * All of these are expected to be correct otherwise
+	 * wrong register values in i2s setup parameters
+	 * may result in no sound play.
+	 */
+	base = fdtdec_get_addr(blob, node, "reg");
+	if (base == FDT_ADDR_T_NONE) {
+		debug("%s: Missing  i2s base\n", __func__);
 		return -1;
 	}
+	i2s->base_address = base;
 
+	i2s->audio_pll_clk = fdtdec_get_int(blob,
+				node, "samsung,i2s-epll-clock-frequency", -1);
+	error |= i2s->audio_pll_clk;
+	debug("audio_pll_clk = %d\n", i2s->audio_pll_clk);
+	i2s->samplingrate = fdtdec_get_int(blob,
+				node, "samsung,i2s-sampling-rate", -1);
+	error |= i2s->samplingrate;
+	debug("samplingrate = %d\n", i2s->samplingrate);
+	i2s->bitspersample = fdtdec_get_int(blob,
+				node, "samsung,i2s-bits-per-sample", -1);
+	error |= i2s->bitspersample;
+	debug("bitspersample = %d\n", i2s->bitspersample);
+	i2s->channels = fdtdec_get_int(blob,
+			node, "samsung,i2s-channels", -1);
+	error |= i2s->channels;
+	debug("channels = %d\n", i2s->channels);
+	i2s->rfs = fdtdec_get_int(blob,
+				node, "samsung,i2s-lr-clk-framesize", -1);
+	error |= i2s->rfs;
+	debug("rfs = %d\n", i2s->rfs);
+	i2s->bfs = fdtdec_get_int(blob,
+				node, "samsung,i2s-bit-clk-framesize", -1);
+	error |= i2s->bfs;
+	debug("bfs = %d\n", i2s->bfs);
 	if (error == -1) {
-		debug("fail to get wm8994 codec node properties\n");
+		debug("fail to get sound i2s node properties\n");
 		return -1;
 	}
-
+#else
+	i2s->base_address = samsung_get_base_i2s();
+	i2s->audio_pll_clk = I2S_PLL_CLK;
+	i2s->samplingrate = I2S_SAMPLING_RATE;
+	i2s->bitspersample = I2S_BITS_PER_SAMPLE;
+	i2s->channels = I2S_CHANNELS;
+	i2s->rfs = I2S_RFS;
+	i2s->bfs = I2S_BFS;
+#endif
 	return 0;
 }
 
 /*
- * Gets fdt values for codec config parameters
+ * Init codec
  *
- * @param pcodec_info	codec information structure
- * @param blob		FDT blob
- * @return		int value, 0 for success
+ * @param blob          FDT blob
+ * @param pi2s_tx	i2s parameters required by codec
+ * @return              int value, 0 for success
  */
-static int get_sound_codec_values(struct sound_codec_info *pcodec_info)
+static int codec_init(const void *blob, struct i2stx_info *pi2s_tx)
 {
-	int error = 0;
+	int ret;
 	const char *codectype;
+#ifdef CONFIG_OF_CONTROL
+	int node;
 
-	codectype =  AUDIO_CODEC;
+	/* Get the node from FDT for sound */
+	node = fdtdec_next_compatible(blob, 0, COMPAT_SAMSUNG_EXYNOS5_SOUND);
+	if (node <= 0) {
+		debug("EXYNOS_SOUND: No node for sound in device tree\n");
+		debug("node = %d\n", node);
+		return -1;
+	}
 
+	/*
+	 * Get the pre-defined sound codec specific values from FDT.
+	 * All of these are expected to be correct otherwise sound
+	 * can not be played
+	 */
+	codectype = fdt_getprop(blob, node, "samsung,codec-type", NULL);
+	debug("device = %s\n", codectype);
+#else
+	codectype =  AUDIO_CODEC;
+#endif
 	if (!strcmp(codectype, "wm8994")) {
-		pcodec_info->codec_type = CODEC_WM_8994;
-		error = get_sound_wm8994_values(pcodec_info);
+		/* Check the codec type and initialise the same */
+		ret = wm8994_init(blob, WM8994_AIF2,
+			pi2s_tx->samplingrate,
+			(pi2s_tx->samplingrate * (pi2s_tx->rfs)),
+			pi2s_tx->bitspersample, pi2s_tx->channels);
 	} else {
-		error = -1;
+		debug("%s: Unknown code type %s\n", __func__,
+		      codectype);
+		return -1;
 	}
-
-	if (error == -1) {
-		debug("fail to get sound codec node properties\n");
+	if (ret) {
+		debug("%s: Codec init failed\n", __func__);
 		return -1;
 	}
 
 	return 0;
 }
 
-int sound_init(void)
+int sound_init(const void *blob)
 {
 	int ret;
 	struct i2stx_info *pi2s_tx = &g_i2stx_pri;
-	struct sound_codec_info *pcodec_info = &g_codec_info;
 
 	/* Get the I2S Values */
-	get_sound_i2s_values(pi2s_tx);
+	if (get_sound_i2s_values(pi2s_tx, blob) < 0) {
+		debug(" FDT I2S values failed\n");
+		return -1;
+	}
 
-	/* Get the codec Values */
-	if (get_sound_codec_values(pcodec_info) < 0)
+	if (codec_init(blob, pi2s_tx) < 0) {
+		debug(" Codec init failed\n");
 		return -1;
+	}
 
 	ret = i2s_tx_init(pi2s_tx);
 	if (ret) {
@@ -137,21 +185,6 @@ int sound_init(void)
 		return ret;
 	}
 
-	/* Check the codec type and initialise the same */
-	if (pcodec_info->codec_type == CODEC_WM_8994) {
-		ret = wm8994_init(pcodec_info, WM8994_AIF2,
-			pi2s_tx->samplingrate,
-			(pi2s_tx->samplingrate * (pi2s_tx->rfs)),
-			pi2s_tx->bitspersample, pi2s_tx->channels);
-	} else {
-		debug("%s: Unknown code type %d\n", __func__,
-		      pcodec_info->codec_type);
-		return -1;
-	}
-	if (ret) {
-		debug("%s: Codec init failed\n", __func__);
-		return -1;
-	}
 
 	return ret;
 }
include/sound.h +2 -2
index ea0b115..d73839d 100644
@@ -46,10 +46,10 @@ struct sound_codec_info {
 
 /*
  * Initialises audio sub system
- *
+ * @param blob	Pointer of device tree node or NULL if none.
  * @return	int value 0 for success, -1 for error
  */
-int sound_init(void);
+int sound_init(const void *blob);
 
 /*
  * plays the pcm data buffer in pcm_data.h through i2s1 to make the
Signature · 1 line
1.7.4.4
#17 lore raw

PATCH 11/16 Sound: WM8994: Add FDT support to codec

In reply to Rajeshwari Shinde

This patch adds FDT support to the codec.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/sound/wm8994.c |   76 ++++++++++++++++++++++++++++++++++++++++++++++-
 drivers/sound/wm8994.h |    6 +--
 2 files changed, 76 insertions(+), 6 deletions(-)
drivers/sound/wm8994.c +74 -2
index 293903a..a528502 100644
@@ -26,9 +26,11 @@
 #include <asm/io.h>
 #include <common.h>
 #include <div64.h>
+#include <fdtdec.h>
 #include <i2c.h>
 #include <i2s.h>
 #include <sound.h>
+#include <asm/arch/sound.h>
 #include "wm8994.h"
 #include "wm8994_registers.h"
 
@@ -77,6 +79,7 @@ static int bclk_divs[] = {
 
 static struct wm8994_priv g_wm8994_info;
 static unsigned char g_wm8994_i2c_dev_addr;
+static struct sound_codec_info g_codec_info;
 
 /*
  * Initialise I2C for wm 8994
@@ -747,13 +750,82 @@ err:
 	return -1;
 }
 
+/*
+ * Gets fdt values for wm8994 config parameters
+ *
+ * @param pcodec_info	codec information structure
+ * @param blob		FDT blob
+ * @return		int value, 0 for success
+ */
+static int get_codec_values(struct sound_codec_info *pcodec_info,
+			const void *blob)
+{
+	int error = 0;
+#ifdef CONFIG_OF_CONTROL
+	enum fdt_compat_id compat;
+	int node;
+	int parent;
+
+	/* Get the node from FDT for codec */
+	node = fdtdec_next_compatible(blob, 0, COMPAT_WOLFSON_WM8994_CODEC);
+	if (node <= 0) {
+		debug("EXYNOS_SOUND: No node for codec in device tree\n");
+		debug("node = %d\n", node);
+		return -1;
+	}
+
+	parent = fdt_parent_offset(blob, node);
+	if (parent < 0) {
+		debug("%s: Cannot find node parent\n", __func__);
+		return -1;
+	}
+
+	compat = fdtdec_lookup(blob, parent);
+	switch (compat) {
+	case COMPAT_SAMSUNG_S3C2440_I2C:
+		pcodec_info->i2c_bus = i2c_get_bus_num_fdt(parent);
+		error |= pcodec_info->i2c_bus;
+		debug("i2c bus = %d\n", pcodec_info->i2c_bus);
+		pcodec_info->i2c_dev_addr = fdtdec_get_int(blob, node,
+							"reg", 0);
+		error |= pcodec_info->i2c_dev_addr;
+		debug("i2c dev addr = %d\n", pcodec_info->i2c_dev_addr);
+		break;
+	default:
+		debug("%s: Unknown compat id %d\n", __func__, compat);
+		return -1;
+	}
+#else
+	pcodec_info->i2c_bus = AUDIO_I2C_BUS;
+	pcodec_info->i2c_dev_addr = AUDIO_I2C_REG;
+	debug("i2c dev addr = %d\n", pcodec_info->i2c_dev_addr);
+#endif
+
+	pcodec_info->codec_type = CODEC_WM_8994;
+
+	if (error == -1) {
+		debug("fail to get wm8994 codec node properties\n");
+		return -1;
+	}
+
+	return 0;
+
+}
+
+
 /*wm8994 Device Initialisation */
-int wm8994_init(struct sound_codec_info *pcodec_info,
-			enum en_audio_interface aif_id,
+int wm8994_init(const void *blob, enum en_audio_interface aif_id,
 			int sampling_rate, int mclk_freq,
 			int bits_per_sample, unsigned int channels)
 {
 	int ret = 0;
+	struct sound_codec_info *pcodec_info = &g_codec_info;
+
+	/* Get the codec Values */
+	if (get_codec_values(pcodec_info, blob) < 0) {
+		debug("FDT Codec values failed\n");
+		return -1;
+	}
 
 	/* shift the device address by 1 for 7 bit addressing */
 	g_wm8994_i2c_dev_addr = pcodec_info->i2c_dev_addr;
drivers/sound/wm8994.h +2 -4
index a8f0de1..a1e8335 100644
@@ -69,8 +69,7 @@ enum wm8994_type {
 /*
  * intialise wm8994 sound codec device for the given configuration
  *
- * @param pcodec_info		pointer value of the sound codec info structure
- *				parsed from device tree
+ * @param blob			FDT node for codec values
  * @param aif_id		enum value of codec interface port in which
  *				soc i2s is connected
  * @param sampling_rate		Sampling rate ranges between from 8khz to 96khz
@@ -80,8 +79,7 @@ enum wm8994_type {
  *
  * @returns -1 for error  and 0  Success.
  */
-int wm8994_init(struct sound_codec_info *pcodec_info,
-			enum en_audio_interface aif_id,
+int wm8994_init(const void *blob, enum en_audio_interface aif_id,
 			int sampling_rate, int mclk_freq,
 			int bits_per_sample, unsigned int channels);
 #endif /*__WM8994_H__ */
Signature · 1 line
1.7.4.4
#18 lore raw

PATCH 11/16 Sound: WM8994: Add FDT support to codec

Dear Rajeshwari Shinde,

Quoted 88 lines · Rajeshwari Shinde

This patch adds FDT support to the codec.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/sound/wm8994.c |   76 ++++++++++++++++++++++++++++++++++++++++++++++-
 drivers/sound/wm8994.h |    6 +--
 2 files changed, 76 insertions(+), 6 deletions(-)
drivers/sound/wm8994.c +52 -0
index 293903a..a528502 100644
@@ -26,9 +26,11 @@
 #include <asm/io.h>
 #include <common.h>
 #include <div64.h>
+#include <fdtdec.h>
 #include <i2c.h>
 #include <i2s.h>
 #include <sound.h>
+#include <asm/arch/sound.h>
 #include "wm8994.h"
 #include "wm8994_registers.h"
 
@@ -77,6 +79,7 @@ static int bclk_divs[] = {
 
 static struct wm8994_priv g_wm8994_info;
 static unsigned char g_wm8994_i2c_dev_addr;
+static struct sound_codec_info g_codec_info;
 
 /*
  * Initialise I2C for wm 8994
@@ -747,13 +750,82 @@ err:
 	return -1;
 }
 
+/*
+ * Gets fdt values for wm8994 config parameters
+ *
+ * @param pcodec_info	codec information structure
+ * @param blob		FDT blob
+ * @return		int value, 0 for success
+ */
+static int get_codec_values(struct sound_codec_info *pcodec_info,
+			const void *blob)
+{
+	int error = 0;
+#ifdef CONFIG_OF_CONTROL
+	enum fdt_compat_id compat;
+	int node;
+	int parent;
+
+	/* Get the node from FDT for codec */
+	node = fdtdec_next_compatible(blob, 0, COMPAT_WOLFSON_WM8994_CODEC);
+	if (node <= 0) {
+		debug("EXYNOS_SOUND: No node for codec in device tree\n");
+		debug("node = %d\n", node);
+		return -1;
+	}
+
+	parent = fdt_parent_offset(blob, node);
+	if (parent < 0) {
+		debug("%s: Cannot find node parent\n", __func__);
+		return -1;
+	}
+
+	compat = fdtdec_lookup(blob, parent);
+	switch (compat) {
+	case COMPAT_SAMSUNG_S3C2440_I2C:
+		pcodec_info->i2c_bus = i2c_get_bus_num_fdt(parent);
+		error |= pcodec_info->i2c_bus;
+		debug("i2c bus = %d\n", pcodec_info->i2c_bus);
+		pcodec_info->i2c_dev_addr = fdtdec_get_int(blob, node,
+							"reg", 0);
+		error |= pcodec_info->i2c_dev_addr;
+		debug("i2c dev addr = %d\n", pcodec_info->i2c_dev_addr);
+		break;
+	default:
+		debug("%s: Unknown compat id %d\n", __func__, compat);
+		return -1;
+	}
+#else
+	pcodec_info->i2c_bus = AUDIO_I2C_BUS;
+	pcodec_info->i2c_dev_addr = AUDIO_I2C_REG;
+	debug("i2c dev addr = %d\n", pcodec_info->i2c_dev_addr);

drivers/sound/wm8994.c err: · line 811

Quoted 10 lines
drivers/sound/wm8994.c +10 -0
+#endif
+
+	pcodec_info->codec_type = CODEC_WM_8994;
+
+	if (error == -1) {
+		debug("fail to get wm8994 codec node properties\n");
+		return -1;
+	}
+
+	return 0;

please remove this blank line.

drivers/sound/wm8994.c err: · line 776

Quoted 3 lines
drivers/sound/wm8994.c +3 -0
+
+}
+

please remove this blank line.

Quoted 35 lines
drivers/sound/wm8994.c +9 -2
+
 /*wm8994 Device Initialisation */
-int wm8994_init(struct sound_codec_info *pcodec_info,
-			enum en_audio_interface aif_id,
+int wm8994_init(const void *blob, enum en_audio_interface aif_id,
 			int sampling_rate, int mclk_freq,
 			int bits_per_sample, unsigned int channels)
 {
 	int ret = 0;
+	struct sound_codec_info *pcodec_info = &g_codec_info;
+
+	/* Get the codec Values */
+	if (get_codec_values(pcodec_info, blob) < 0) {
+		debug("FDT Codec values failed\n");
+		return -1;
+	}
 
 	/* shift the device address by 1 for 7 bit addressing */
 	g_wm8994_i2c_dev_addr = pcodec_info->i2c_dev_addr;
drivers/sound/wm8994.h +1 -2
index a8f0de1..a1e8335 100644
@@ -69,8 +69,7 @@ enum wm8994_type {
 /*
  * intialise wm8994 sound codec device for the given configuration
  *
- * @param pcodec_info		pointer value of the sound codec info structure
- *				parsed from device tree
+ * @param blob			FDT node for codec values
  * @param aif_id		enum value of codec interface port in which
  *				soc i2s is connected
  * @param sampling_rate		Sampling rate ranges between from 8khz to 96khz

drivers/sound/wm8994.h enum wm8994_type { · line 85

Quoted 9 lines
drivers/sound/wm8994.h +1 -2
@@ -80,8 +79,7 @@ enum wm8994_type {
  *
  * @returns -1 for error  and 0  Success.
  */
-int wm8994_init(struct sound_codec_info *pcodec_info,
-			enum en_audio_interface aif_id,
+int wm8994_init(const void *blob, enum en_audio_interface aif_id,
 			int sampling_rate, int mclk_freq,
 			int bits_per_sample, unsigned int channels);
 #endif /*__WM8994_H__ */

--
Thanks,
Minkyu Kang.

#19 lore raw

PATCH 11/16 Sound: WM8994: Add FDT support to codec

Hi Minkyu Kang,

Thank you for comments.Will correct them

Quoted 168 lines · Minkyu Kang

Dear Rajeshwari Shinde,

Quoted 8 lines · Rajeshwari Shinde

This patch adds FDT support to the codec.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/sound/wm8994.c |   76

++++++++++++++++++++++++++++++++++++++++++++++-

Quoted 39 lines
 drivers/sound/wm8994.h |    6 +--
 2 files changed, 76 insertions(+), 6 deletions(-)
drivers/sound/wm8994.c +11 -0
index 293903a..a528502 100644
@@ -26,9 +26,11 @@
 #include <asm/io.h>
 #include <common.h>
 #include <div64.h>
+#include <fdtdec.h>
 #include <i2c.h>
 #include <i2s.h>
 #include <sound.h>
+#include <asm/arch/sound.h>
 #include "wm8994.h"
 #include "wm8994_registers.h"
 
@@ -77,6 +79,7 @@ static int bclk_divs[] = {
 
 static struct wm8994_priv g_wm8994_info;
 static unsigned char g_wm8994_i2c_dev_addr;
+static struct sound_codec_info g_codec_info;
 
 /*
  * Initialise I2C for wm 8994
@@ -747,13 +750,82 @@ err:
      return -1;
 }
 
+/*
+ * Gets fdt values for wm8994 config parameters
+ *
+ * @param pcodec_info        codec information structure
+ * @param blob               FDT blob
+ * @return           int value, 0 for success
+ */
+static int get_codec_values(struct sound_codec_info *pcodec_info,

drivers/sound/wm8994.c err: · line 770

Quoted 10 lines
drivers/sound/wm8994.c +10 -0
+                     const void *blob)
+{
+     int error = 0;
+#ifdef CONFIG_OF_CONTROL
+     enum fdt_compat_id compat;
+     int node;
+     int parent;
+
+     /* Get the node from FDT for codec */
+     node = fdtdec_next_compatible(blob, 0,

COMPAT_WOLFSON_WM8994_CODEC);

Quoted 31 lines
drivers/sound/wm8994.c +31 -0
+     if (node <= 0) {
+             debug("EXYNOS_SOUND: No node for codec in device tree\n");
+             debug("node = %d\n", node);
+             return -1;
+     }
+
+     parent = fdt_parent_offset(blob, node);
+     if (parent < 0) {
+             debug("%s: Cannot find node parent\n", __func__);
+             return -1;
+     }
+
+     compat = fdtdec_lookup(blob, parent);
+     switch (compat) {
+     case COMPAT_SAMSUNG_S3C2440_I2C:
+             pcodec_info->i2c_bus = i2c_get_bus_num_fdt(parent);
+             error |= pcodec_info->i2c_bus;
+             debug("i2c bus = %d\n", pcodec_info->i2c_bus);
+             pcodec_info->i2c_dev_addr = fdtdec_get_int(blob, node,
+                                                     "reg", 0);
+             error |= pcodec_info->i2c_dev_addr;
+             debug("i2c dev addr = %d\n", pcodec_info->i2c_dev_addr);
+             break;
+     default:
+             debug("%s: Unknown compat id %d\n", __func__, compat);
+             return -1;
+     }
+#else
+     pcodec_info->i2c_bus = AUDIO_I2C_BUS;
+     pcodec_info->i2c_dev_addr = AUDIO_I2C_REG;
+     debug("i2c dev addr = %d\n", pcodec_info->i2c_dev_addr);

drivers/sound/wm8994.c err: · line 811

Quoted 10 lines
drivers/sound/wm8994.c +10 -0
+#endif
+
+     pcodec_info->codec_type = CODEC_WM_8994;
+
+     if (error == -1) {
+             debug("fail to get wm8994 codec node properties\n");
+             return -1;
+     }
+
+     return 0;

please remove this blank line.

drivers/sound/wm8994.c err: · line 776

Quoted 3 lines
drivers/sound/wm8994.c +3 -0
+
+}
+

please remove this blank line.

Quoted 24 lines
drivers/sound/wm8994.c +9 -2
+
 /*wm8994 Device Initialisation */
-int wm8994_init(struct sound_codec_info *pcodec_info,
-                     enum en_audio_interface aif_id,
+int wm8994_init(const void *blob, enum en_audio_interface aif_id,
                      int sampling_rate, int mclk_freq,
                      int bits_per_sample, unsigned int channels)
 {
      int ret = 0;
+     struct sound_codec_info *pcodec_info = &g_codec_info;
+
+     /* Get the codec Values */
+     if (get_codec_values(pcodec_info, blob) < 0) {
+             debug("FDT Codec values failed\n");
+             return -1;
+     }
 
      /* shift the device address by 1 for 7 bit addressing */
      g_wm8994_i2c_dev_addr = pcodec_info->i2c_dev_addr;
drivers/sound/wm8994.h +0 -0
index a8f0de1..a1e8335 100644

drivers/sound/wm8994.h enum wm8994_type { · line 72

Quoted 4 lines
drivers/sound/wm8994.h +0 -1
@@ -69,8 +69,7 @@ enum wm8994_type {
 /*
  * intialise wm8994 sound codec device for the given configuration
  *
- * @param pcodec_info                pointer value of the sound codec

info structure

drivers/sound/wm8994.h enum wm8994_type {

Quoted 5 lines
drivers/sound/wm8994.h +1 -1
- *                           parsed from device tree
+ * @param blob                       FDT node for codec values
  * @param aif_id             enum value of codec interface port in which
  *                           soc i2s is connected
  * @param sampling_rate              Sampling rate ranges between from

8khz to 96khz

drivers/sound/wm8994.h enum wm8994_type { · line 85

Quoted 11 lines
drivers/sound/wm8994.h +1 -2
@@ -80,8 +79,7 @@ enum wm8994_type {
  *
  * @returns -1 for error  and 0  Success.
  */
-int wm8994_init(struct sound_codec_info *pcodec_info,
-                     enum en_audio_interface aif_id,
+int wm8994_init(const void *blob, enum en_audio_interface aif_id,
                      int sampling_rate, int mclk_freq,
                      int bits_per_sample, unsigned int channels);
 #endif /*__WM8994_H__ */

--
Thanks,
Minkyu Kang.

_______________________________________________
U-Boot mailing list
U-Boot at lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot

Signature · 2 lines
Regards,
Rajeshwari Shinde
#20 lore raw

PATCH 12/16 Sound: Add FDT support to CMD.

In reply to Rajeshwari Shinde

This patch adds FDT support to sound init in CMD.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 common/cmd_sound.c |    2 +-
 1 files changed, 1 insertions(+), 1 deletions(-)
common/cmd_sound.c +1 -1
index 459d1eb..cfca9dd 100644
@@ -33,7 +33,7 @@ static int do_init(cmd_tbl_t *cmdtp, int flag, int argc, char *const argv[])
 {
 	int ret;
 
-	ret = sound_init();
+	ret = sound_init(gd->fdt_blob);
 	if (ret) {
 		printf("Initialise Audio driver failed\n");
 		return CMD_RET_FAILURE;
Signature · 1 line
1.7.4.4
#21 lore raw

PATCH 13/16 EXYNOS5: FDT: Add compatible strings for SPI

In reply to Rajeshwari Shinde

Add required compatible information for SPI driver.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 include/fdtdec.h |    1 +
 lib/fdtdec.c     |    1 +
 2 files changed, 2 insertions(+), 0 deletions(-)
include/fdtdec.h +1 -0
index 976c9f3..539bb1b 100644
@@ -73,6 +73,7 @@ enum fdt_compat_id {
 	COMPAT_SAMSUNG_S3C2440_I2C,	/* Exynos I2C Controller */
 	COMPAT_SAMSUNG_EXYNOS5_SOUND,	/* Exynos Sound */
 	COMPAT_WOLFSON_WM8994_CODEC,	/* Wolfson WM8994 Sound Codec */
+	COMPAT_SAMSUNG_EXYNOS_SPI,	/* Exynos SPI */
 
 	COMPAT_COUNT,
 };
lib/fdtdec.c +1 -0
index 43affaa..44c249d 100644
@@ -50,6 +50,7 @@ static const char * const compat_names[COMPAT_COUNT] = {
 	COMPAT(SAMSUNG_S3C2440_I2C, "samsung,s3c2440-i2c"),
 	COMPAT(SAMSUNG_EXYNOS5_SOUND, "samsung,exynos-sound"),
 	COMPAT(WOLFSON_WM8994_CODEC, "wolfson,wm8994-codec"),
+	COMPAT(SAMSUNG_EXYNOS_SPI, "samsung,exynos-spi"),
 };
 
 const char *fdtdec_get_compatible(enum fdt_compat_id id)
Signature · 1 line
1.7.4.4
#22 lore raw

PATCH 14/16 EXYNOS5 : FDT: Add Aliases for SPI device

In reply to Rajeshwari Shinde

This patch adds aliases for SPI.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 board/samsung/dts/exynos5250-smdk5250.dts |    5 +++++
 1 files changed, 5 insertions(+), 0 deletions(-)
board/samsung/dts/exynos5250-smdk5250.dts +5 -0
index 14f73d8..a8e62da 100644
@@ -25,6 +25,11 @@
 		i2c5 = "/i2c at 12cb0000";
 		i2c6 = "/i2c at 12cc0000";
 		i2c7 = "/i2c at 12cd0000";
+		spi0 = "/spi at 12d20000";
+		spi1 = "/spi at 12d30000";
+		spi2 = "/spi at 12d40000";
+		spi3 = "/spi at 131a0000";
+		spi4 = "/spi at 131b0000";
 	};
 
 	sromc at 12250000 {
Signature · 1 line
1.7.4.4
#23 lore raw

PATCH 15/16 EXYNOS5: FDT: Add SPI device node data

In reply to Rajeshwari Shinde

Add SPI device node data for exynos.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 arch/arm/dts/exynos5250.dtsi                |   41 +++++++++++++++++++++++++++
 doc/device-tree-bindings/exynos/isp-spi.txt |   22 ++++++++++++++
 2 files changed, 63 insertions(+), 0 deletions(-)
 create mode 100644 doc/device-tree-bindings/exynos/isp-spi.txt
arch/arm/dts/exynos5250.dtsi +41 -0
index dc13f29..1008797 100644
@@ -97,4 +97,45 @@
 		compatible = "samsung,exynos-sound";
 		reg = <0x12d60000 0x20>;
 	};
+
+	spi at 12d20000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,exynos-spi";
+		reg = <0x12d20000 0x30>;
+		interrupts = <0 68 0>;
+	};
+
+	spi at 12d30000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,exynos-spi";
+		reg = <0x12d30000 0x30>;
+		interrupts = <0 69 0>;
+	};
+
+	spi at 12d40000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,exynos-spi";
+		reg = <0x12d40000 0x30>;
+		clock-frequency = <50000000>;
+		interrupts = <0 70 0>;
+        };
+
+	spi at 131a0000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,exynos-spi";
+		reg = <0x131a0000 0x30>;
+		interrupts = <0 129 0>;
+	};
+
+	spi at 131b0000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "samsung,exynos-spi";
+		reg = <0x131b0000 0x30>;
+		interrupts = <0 130 0>;
+	};
 };
doc/device-tree-bindings/exynos/isp-spi.txt new file +22 -0
new file mode 100644
index 0000000..b8086e8
@@ -0,0 +1,22 @@
+Exynos ISP SPI Subsystem
+
+The device node for ISP SPI subsytem.
+Since Peripheral id in EXYNOS is decoded based on Interrupts, currently
+ISP SPI have no individual interrupts hence we add ad dummy interrupt node
+which will have a value beyond the maximum number of interrupts exynos5 can
+support.
+
+Required properties :
+ - compatible : Should be "samsung,exynos-spi" for spi.
+ - reg : Base adrress of the the subsystem.
+ - interrupts : A value which is beyond the maximum number of interrupts
+exynos5 can support.
+
+Example:
+spi at 131a0000 {
+	#address-cells = <1>;
+	#size-cells = <0>;
+	compatible = "samsung,exynos-spi";
+	reg = <0x131a0000 0x30>;
+	interrupts = <0 129 0>;
+};
Signature · 1 line
1.7.4.4
#24 lore raw

PATCH 16/16 SPI: EXYNOS: Add FDT support to driver.

In reply to Rajeshwari Shinde

This patch adds FDT support to the SPI driver.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/spi/exynos_spi.c |   96 +++++++++++++++++++++++++++++++++++++++++++---
 1 files changed, 90 insertions(+), 6 deletions(-)
drivers/spi/exynos_spi.c +90 -6
index 3e6c18f..7ecc566 100644
@@ -20,6 +20,7 @@
 #include <common.h>
 #include <malloc.h>
 #include <spi.h>
+#include <fdtdec.h>
 #include <asm/arch/clk.h>
 #include <asm/arch/clock.h>
 #include <asm/arch/cpu.h>
@@ -28,16 +29,20 @@
 #include <asm/arch-exynos/spi.h>
 #include <asm/io.h>
 
+DECLARE_GLOBAL_DATA_PTR;
+
 /* Information about each SPI controller */
 struct spi_bus {
 	enum periph_id periph_id;
 	s32 frequency;		/* Default clock frequency, -1 for none */
 	struct exynos_spi *regs;
 	int inited;		/* 1 if this bus is ready for use */
+	int node;
 };
 
 /* A list of spi buses that we know about */
 static struct spi_bus spi_bus[EXYNOS5_SPI_NUM_CONTROLLERS];
+static unsigned int bus_count;
 
 struct exynos_spi_slave {
 	struct spi_slave slave;
@@ -50,7 +55,7 @@ struct exynos_spi_slave {
 
 static struct spi_bus *spi_get_bus(unsigned dev_index)
 {
-	if (dev_index < EXYNOS5_SPI_NUM_CONTROLLERS)
+	if (dev_index < bus_count)
 		return &spi_bus[dev_index];
 	debug("%s: invalid bus %d", __func__, dev_index);
 
@@ -347,21 +352,100 @@ static inline struct exynos_spi *get_spi_base(int dev_index)
 					(dev_index - 3);
 }
 
+/*
+ * Read the SPI config from the device tree node.
+ *
+ * @param blob  FDT blob to read from
+ * @param node  Node offset to read from
+ * @param bus   SPI bus structure to fill with information
+ * @return 0 if ok, or -FDT_ERR_NOTFOUND if something was missing
+ */
+static int spi_get_config(const void *blob, int node, struct spi_bus *bus)
+{
+	bus->node = node;
+	bus->regs = (struct exynos_spi *)fdtdec_get_addr(blob, node, "reg");
+	bus->periph_id = pinmux_decode_periph_id(blob, node);
+	if (bus->periph_id == PERIPH_ID_NONE) {
+		debug("%s: Invalid peripheral ID %d\n", __func__,
+			bus->periph_id);
+		return -FDT_ERR_NOTFOUND;
+	}
+
+	/* Use 500KHz as a suitable default */
+	bus->frequency = fdtdec_get_int(blob, node, "spi-max-frequency",
+					500000);
+
+	return 0;
+}
+
+
+/*
+ * Process a list of nodes, adding them to our list of SPI ports.
+ *
+ * @param blob          fdt blob
+ * @param node_list     list of nodes to process (any <=0 are ignored)
+ * @param count         number of nodes to process
+ * @param is_dvc        1 if these are DVC ports, 0 if standard I2C
+ * @return 0 if ok, -1 on error
+ */
+static int process_nodes(const void *blob, int node_list[], int count)
+{
+	int i;
+
+	/* build the i2c_controllers[] for each controller */
+	for (i = 0; i < count; i++) {
+		int node = node_list[i];
+		struct spi_bus *bus;
+
+		if (node <= 0)
+			continue;
+
+		bus = &spi_bus[i];
+		if (spi_get_config(blob, node, bus)) {
+			printf("exynos spi_init: failed to decode bus %d\n",
+				i);
+			return -1;
+		}
+
+		debug("spi: controller bus %d@%p, periph_id %d\n",
+		      i, bus->regs, bus->periph_id);
+		bus->inited = 1;
+		bus_count++;
+	}
+
+	return 0;
+}
+
 /* Sadly there is no error return from this function */
 void spi_init(void)
 {
-	int i;
+	int count;
+
+#ifdef CONFIG_OF_CONTROL
+	int node_list[EXYNOS5_SPI_NUM_CONTROLLERS];
+	const void *blob = gd->fdt_blob;
+
+	count = fdtdec_find_aliases_for_id(blob, "spi",
+			COMPAT_SAMSUNG_EXYNOS_SPI, node_list,
+			EXYNOS5_SPI_NUM_CONTROLLERS);
+	if (process_nodes(blob, node_list, count))
+		return;
+
+#else
 	struct spi_bus *bus;
 
-	for (i = 0; i < EXYNOS5_SPI_NUM_CONTROLLERS; i++) {
-		bus = &spi_bus[i];
-		bus->regs = get_spi_base(i);
-		bus->periph_id = PERIPH_ID_SPI0 + i;
+	for (count = 0; i < EXYNOS5_SPI_NUM_CONTROLLERS; i++) {
+		bus = &spi_bus[count];
+		bus->regs = get_spi_base(count);
+		bus->periph_id = PERIPH_ID_SPI0 + count;
 
 		/* Although Exynos5 supports upto 50Mhz speed,
 		 * we are setting it to 10Mhz for safe side
 		 */
 		bus->frequency = 10000000;
 		bus->inited = 1;
+		bus->node = 0;
+		bus_count = EXYNOS5_SPI_NUM_CONTROLLERS;
 	}
+#endif
 }
Signature · 1 line
1.7.4.4
#25 lore raw

PATCH 16/16 SPI: EXYNOS: Add FDT support to driver.

Dear Rajeshwari Shinde,

Quoted 60 lines · Rajeshwari Shinde

This patch adds FDT support to the SPI driver.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/spi/exynos_spi.c |   96 +++++++++++++++++++++++++++++++++++++++++++---
 1 files changed, 90 insertions(+), 6 deletions(-)
drivers/spi/exynos_spi.c +9 -1
index 3e6c18f..7ecc566 100644
@@ -20,6 +20,7 @@
 #include <common.h>
 #include <malloc.h>
 #include <spi.h>
+#include <fdtdec.h>
 #include <asm/arch/clk.h>
 #include <asm/arch/clock.h>
 #include <asm/arch/cpu.h>
@@ -28,16 +29,20 @@
 #include <asm/arch-exynos/spi.h>
 #include <asm/io.h>
 
+DECLARE_GLOBAL_DATA_PTR;
+
 /* Information about each SPI controller */
 struct spi_bus {
 	enum periph_id periph_id;
 	s32 frequency;		/* Default clock frequency, -1 for none */
 	struct exynos_spi *regs;
 	int inited;		/* 1 if this bus is ready for use */
+	int node;
 };
 
 /* A list of spi buses that we know about */
 static struct spi_bus spi_bus[EXYNOS5_SPI_NUM_CONTROLLERS];
+static unsigned int bus_count;
 
 struct exynos_spi_slave {
 	struct spi_slave slave;
@@ -50,7 +55,7 @@ struct exynos_spi_slave {
 
 static struct spi_bus *spi_get_bus(unsigned dev_index)
 {
-	if (dev_index < EXYNOS5_SPI_NUM_CONTROLLERS)
+	if (dev_index < bus_count)
 		return &spi_bus[dev_index];
 	debug("%s: invalid bus %d", __func__, dev_index);
 
@@ -347,21 +352,100 @@ static inline struct exynos_spi *get_spi_base(int dev_index)
 					(dev_index - 3);
 }
 
+/*
+ * Read the SPI config from the device tree node.
+ *

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int dev_index) · line 367

Quoted 10 lines
drivers/spi/exynos_spi.c +10 -0
+ * @param blob  FDT blob to read from
+ * @param node  Node offset to read from
+ * @param bus   SPI bus structure to fill with information
+ * @return 0 if ok, or -FDT_ERR_NOTFOUND if something was missing
+ */
+static int spi_get_config(const void *blob, int node, struct spi_bus *bus)
+{
+	bus->node = node;
+	bus->regs = (struct exynos_spi *)fdtdec_get_addr(blob, node, "reg");
+	bus->periph_id = pinmux_decode_periph_id(blob, node);

Please add blank line here.

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int dev_index) · line 380

Quoted 13 lines
drivers/spi/exynos_spi.c +13 -0
+	if (bus->periph_id == PERIPH_ID_NONE) {
+		debug("%s: Invalid peripheral ID %d\n", __func__,
+			bus->periph_id);
+		return -FDT_ERR_NOTFOUND;
+	}
+
+	/* Use 500KHz as a suitable default */
+	bus->frequency = fdtdec_get_int(blob, node, "spi-max-frequency",
+					500000);
+
+	return 0;
+}
+

Please remove this blank line.

Quoted 52 lines
drivers/spi/exynos_spi.c +48 -1
+
+/*
+ * Process a list of nodes, adding them to our list of SPI ports.
+ *
+ * @param blob          fdt blob
+ * @param node_list     list of nodes to process (any <=0 are ignored)
+ * @param count         number of nodes to process
+ * @param is_dvc        1 if these are DVC ports, 0 if standard I2C
+ * @return 0 if ok, -1 on error
+ */
+static int process_nodes(const void *blob, int node_list[], int count)
+{
+	int i;
+
+	/* build the i2c_controllers[] for each controller */
+	for (i = 0; i < count; i++) {
+		int node = node_list[i];
+		struct spi_bus *bus;
+
+		if (node <= 0)
+			continue;
+
+		bus = &spi_bus[i];
+		if (spi_get_config(blob, node, bus)) {
+			printf("exynos spi_init: failed to decode bus %d\n",
+				i);
+			return -1;
+		}
+
+		debug("spi: controller bus %d at %p, periph_id %d\n",
+		      i, bus->regs, bus->periph_id);
+		bus->inited = 1;
+		bus_count++;
+	}
+
+	return 0;
+}
+
 /* Sadly there is no error return from this function */
 void spi_init(void)
 {
-	int i;
+	int count;
+
+#ifdef CONFIG_OF_CONTROL
+	int node_list[EXYNOS5_SPI_NUM_CONTROLLERS];
+	const void *blob = gd->fdt_blob;
+
+	count = fdtdec_find_aliases_for_id(blob, "spi",
+			COMPAT_SAMSUNG_EXYNOS_SPI, node_list,
+			EXYNOS5_SPI_NUM_CONTROLLERS);
+	if (process_nodes(blob, node_list, count))

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int dev_index) · line 437

Quoted 10 lines
drivers/spi/exynos_spi.c +4 -4
+		return;
+
+#else
 	struct spi_bus *bus;
 
-	for (i = 0; i < EXYNOS5_SPI_NUM_CONTROLLERS; i++) {
-		bus = &spi_bus[i];
-		bus->regs = get_spi_base(i);
-		bus->periph_id = PERIPH_ID_SPI0 + i;
+	for (count = 0; i < EXYNOS5_SPI_NUM_CONTROLLERS; i++) {

i or count?
Is it typo?

Quoted 5 lines
drivers/spi/exynos_spi.c +3 -0
+		bus = &spi_bus[count];
+		bus->regs = get_spi_base(count);
+		bus->periph_id = PERIPH_ID_SPI0 + count;
 

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int dev_index) · line 451

Quoted 10 lines
drivers/spi/exynos_spi.c +3 -0
 		/* Although Exynos5 supports upto 50Mhz speed,
 		 * we are setting it to 10Mhz for safe side
 		 */
 		bus->frequency = 10000000;
 		bus->inited = 1;
+		bus->node = 0;
+		bus_count = EXYNOS5_SPI_NUM_CONTROLLERS;
 	}
+#endif
 }

--
Thanks,
Minkyu Kang.

#26 lore raw

PATCH 16/16 SPI: EXYNOS: Add FDT support to driver.

Hi Minkyu Kang,

Thank you for comments.Will correct them.

Quoted 187 lines · Minkyu Kang

Dear Rajeshwari Shinde,

Quoted 9 lines · Rajeshwari Shinde

This patch adds FDT support to the SPI driver.

---
Changes in V1:
-Rebased on latest u-boot-samsung

 drivers/spi/exynos_spi.c |   96

+++++++++++++++++++++++++++++++++++++++++++---

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int

Quoted 45 lines
 1 files changed, 90 insertions(+), 6 deletions(-)
drivers/spi/exynos_spi.c +6 -1
index 3e6c18f..7ecc566 100644
@@ -20,6 +20,7 @@
 #include <common.h>
 #include <malloc.h>
 #include <spi.h>
+#include <fdtdec.h>
 #include <asm/arch/clk.h>
 #include <asm/arch/clock.h>
 #include <asm/arch/cpu.h>
@@ -28,16 +29,20 @@
 #include <asm/arch-exynos/spi.h>
 #include <asm/io.h>
 
+DECLARE_GLOBAL_DATA_PTR;
+
 /* Information about each SPI controller */
 struct spi_bus {
      enum periph_id periph_id;
      s32 frequency;          /* Default clock frequency, -1 for none */
      struct exynos_spi *regs;
      int inited;             /* 1 if this bus is ready for use */
+     int node;
 };
 
 /* A list of spi buses that we know about */
 static struct spi_bus spi_bus[EXYNOS5_SPI_NUM_CONTROLLERS];
+static unsigned int bus_count;
 
 struct exynos_spi_slave {
      struct spi_slave slave;
@@ -50,7 +55,7 @@ struct exynos_spi_slave {
 
 static struct spi_bus *spi_get_bus(unsigned dev_index)
 {
-     if (dev_index < EXYNOS5_SPI_NUM_CONTROLLERS)
+     if (dev_index < bus_count)
              return &spi_bus[dev_index];
      debug("%s: invalid bus %d", __func__, dev_index);
 
@@ -347,21 +352,100 @@ static inline struct exynos_spi *get_spi_base(int

dev_index)

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int dev_index)

Quoted 12 lines
drivers/spi/exynos_spi.c +9 -0
                                      (dev_index - 3);
 }
 
+/*
+ * Read the SPI config from the device tree node.
+ *
+ * @param blob  FDT blob to read from
+ * @param node  Node offset to read from
+ * @param bus   SPI bus structure to fill with information
+ * @return 0 if ok, or -FDT_ERR_NOTFOUND if something was missing
+ */
+static int spi_get_config(const void *blob, int node, struct spi_bus

*bus)

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int dev_index)

Quoted 3 lines
drivers/spi/exynos_spi.c +3 -0
+{
+     bus->node = node;
+     bus->regs = (struct exynos_spi *)fdtdec_get_addr(blob, node,

"reg");

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int dev_index) · line 367

Quoted 1 line
drivers/spi/exynos_spi.c +1 -0
+     bus->periph_id = pinmux_decode_periph_id(blob, node);

Please add blank line here.

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int dev_index) · line 380

Quoted 13 lines
drivers/spi/exynos_spi.c +13 -0
+     if (bus->periph_id == PERIPH_ID_NONE) {
+             debug("%s: Invalid peripheral ID %d\n", __func__,
+                     bus->periph_id);
+             return -FDT_ERR_NOTFOUND;
+     }
+
+     /* Use 500KHz as a suitable default */
+     bus->frequency = fdtdec_get_int(blob, node, "spi-max-frequency",
+                                     500000);
+
+     return 0;
+}
+

Please remove this blank line.

Quoted 15 lines
drivers/spi/exynos_spi.c +15 -0
+
+/*
+ * Process a list of nodes, adding them to our list of SPI ports.
+ *
+ * @param blob          fdt blob
+ * @param node_list     list of nodes to process (any <=0 are ignored)
+ * @param count         number of nodes to process
+ * @param is_dvc        1 if these are DVC ports, 0 if standard I2C
+ * @return 0 if ok, -1 on error
+ */
+static int process_nodes(const void *blob, int node_list[], int count)
+{
+     int i;
+
+     /* build the i2c_controllers[] for each controller */

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int dev_index)

Quoted 10 lines
drivers/spi/exynos_spi.c +10 -0
+     for (i = 0; i < count; i++) {
+             int node = node_list[i];
+             struct spi_bus *bus;
+
+             if (node <= 0)
+                     continue;
+
+             bus = &spi_bus[i];
+             if (spi_get_config(blob, node, bus)) {
+                     printf("exynos spi_init: failed to decode bus

%d\n",

Quoted 27 lines
drivers/spi/exynos_spi.c +23 -1
+                             i);
+                     return -1;
+             }
+
+             debug("spi: controller bus %d at %p, periph_id %d\n",
+                   i, bus->regs, bus->periph_id);
+             bus->inited = 1;
+             bus_count++;
+     }
+
+     return 0;
+}
+
 /* Sadly there is no error return from this function */
 void spi_init(void)
 {
-     int i;
+     int count;
+
+#ifdef CONFIG_OF_CONTROL
+     int node_list[EXYNOS5_SPI_NUM_CONTROLLERS];
+     const void *blob = gd->fdt_blob;
+
+     count = fdtdec_find_aliases_for_id(blob, "spi",
+                     COMPAT_SAMSUNG_EXYNOS_SPI, node_list,
+                     EXYNOS5_SPI_NUM_CONTROLLERS);
+     if (process_nodes(blob, node_list, count))

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int dev_index) · line 437

Quoted 10 lines
drivers/spi/exynos_spi.c +4 -4
+             return;
+
+#else
      struct spi_bus *bus;
 
-     for (i = 0; i < EXYNOS5_SPI_NUM_CONTROLLERS; i++) {
-             bus = &spi_bus[i];
-             bus->regs = get_spi_base(i);
-             bus->periph_id = PERIPH_ID_SPI0 + i;
+     for (count = 0; i < EXYNOS5_SPI_NUM_CONTROLLERS; i++) {

i or count?
Is it typo?

Quoted 5 lines
drivers/spi/exynos_spi.c +3 -0
+             bus = &spi_bus[count];
+             bus->regs = get_spi_base(count);
+             bus->periph_id = PERIPH_ID_SPI0 + count;
 

drivers/spi/exynos_spi.c static inline struct exynos_spi *get_spi_base(int dev_index) · line 451

Quoted 10 lines
drivers/spi/exynos_spi.c +3 -0
              /* Although Exynos5 supports upto 50Mhz speed,
               * we are setting it to 10Mhz for safe side
               */
              bus->frequency = 10000000;
              bus->inited = 1;
+             bus->node = 0;
+             bus_count = EXYNOS5_SPI_NUM_CONTROLLERS;
      }
+#endif
 }

--
Thanks,
Minkyu Kang.
_______________________________________________
U-Boot mailing list
U-Boot at lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot

Signature · 2 lines
Regards,
Rajeshwari Shinde