Merge https://gitlab.denx.de/u-boot/custodians/u-boot-clk
[platform/kernel/u-boot.git] / drivers / pinctrl / renesas / sh_pfc.h
index 13d9b99..f6159b8 100644 (file)
@@ -41,7 +41,8 @@ struct sh_pfc_pin {
                .name = #alias,                         \
                .pins = n##_pins,                       \
                .mux = n##_mux,                         \
-               .nr_pins = ARRAY_SIZE(n##_pins),        \
+               .nr_pins = ARRAY_SIZE(n##_pins) +       \
+               BUILD_BUG_ON_ZERO(sizeof(n##_pins) != sizeof(n##_mux)), \
        }
 #define SH_PFC_PIN_GROUP(n)    SH_PFC_PIN_GROUP_ALIAS(n, n)
 
@@ -66,6 +67,12 @@ struct sh_pfc_pin_group {
                .nr_pins = ARRAY_SIZE(n##__VA_ARGS__##_pins.data##s),   \
        }
 
+union vin_data12 {
+       unsigned int data12[12];
+       unsigned int data10[10];
+       unsigned int data8[8];
+};
+
 union vin_data16 {
        unsigned int data16[16];
        unsigned int data12[12];
@@ -104,40 +111,54 @@ struct pinmux_func {
 struct pinmux_cfg_reg {
        u32 reg;
        u8 reg_width, field_width;
+#ifdef DEBUG
+       u16 nr_enum_ids;        /* for variable width regs only */
+#define SET_NR_ENUM_IDS(n)     .nr_enum_ids = n,
+#else
+#define SET_NR_ENUM_IDS(n)
+#endif
        const u16 *enum_ids;
        const u8 *var_field_width;
 };
 
+#define GROUP(...)     __VA_ARGS__
+
 /*
  * Describe a config register consisting of several fields of the same width
  *   - name: Register name (unused, for documentation purposes only)
  *   - r: Physical register address
  *   - r_width: Width of the register (in bits)
  *   - f_width: Width of the fixed-width register fields (in bits)
- * This macro must be followed by initialization data: For each register field
- * (from left to right, i.e. MSB to LSB), 2^f_width enum IDs must be specified,
- * one for each possible combination of the register field bit values.
+ *   - ids: For each register field (from left to right, i.e. MSB to LSB),
+ *          2^f_width enum IDs must be specified, one for each possible
+ *          combination of the register field bit values, all wrapped using
+ *          the GROUP() macro.
  */
-#define PINMUX_CFG_REG(name, r, r_width, f_width) \
-       .reg = r, .reg_width = r_width, .field_width = f_width,         \
-       .enum_ids = (const u16 [(r_width / f_width) * (1 << f_width)])
+#define PINMUX_CFG_REG(name, r, r_width, f_width, ids)                 \
+       .reg = r, .reg_width = r_width,                                 \
+       .field_width = f_width + BUILD_BUG_ON_ZERO(r_width % f_width) + \
+       BUILD_BUG_ON_ZERO(sizeof((const u16 []) { ids }) / sizeof(u16) != \
+                         (r_width / f_width) * (1 << f_width)),        \
+       .enum_ids = (const u16 [(r_width / f_width) * (1 << f_width)])  \
+               { ids }
 
 /*
  * Describe a config register consisting of several fields of different widths
  *   - name: Register name (unused, for documentation purposes only)
  *   - r: Physical register address
  *   - r_width: Width of the register (in bits)
- *   - var_fw0, var_fwn...: List of widths of the register fields (in bits),
- *                          From left to right (i.e. MSB to LSB)
- * This macro must be followed by initialization data: For each register field
- * (from left to right, i.e. MSB to LSB), 2^var_fwi enum IDs must be specified,
- * one for each possible combination of the register field bit values.
+ *   - f_widths: List of widths of the register fields (in bits), from left
+ *               to right (i.e. MSB to LSB), wrapped using the GROUP() macro.
+ *   - ids: For each register field (from left to right, i.e. MSB to LSB),
+ *          2^f_widths[i] enum IDs must be specified, one for each possible
+ *          combination of the register field bit values, all wrapped using
+ *          the GROUP() macro.
  */
-#define PINMUX_CFG_REG_VAR(name, r, r_width, var_fw0, var_fwn...) \
-       .reg = r, .reg_width = r_width, \
-       .var_field_width = (const u8 [r_width]) \
-               { var_fw0, var_fwn, 0 }, \
-       .enum_ids = (const u16 [])
+#define PINMUX_CFG_REG_VAR(name, r, r_width, f_widths, ids)            \
+       .reg = r, .reg_width = r_width,                                 \
+       .var_field_width = (const u8 []) { f_widths, 0 },               \
+       SET_NR_ENUM_IDS(sizeof((const u16 []) { ids }) / sizeof(u16))   \
+       .enum_ids = (const u16 []) { ids }
 
 struct pinmux_drive_reg_field {
        u16 pin;
@@ -180,12 +201,14 @@ struct pinmux_data_reg {
  *   - name: Register name (unused, for documentation purposes only)
  *   - r: Physical register address
  *   - r_width: Width of the register (in bits)
- * This macro must be followed by initialization data: For each register bit
- * (from left to right, i.e. MSB to LSB), one enum ID must be specified.
+ *   - ids: For each register bit (from left to right, i.e. MSB to LSB), one
+ *          enum ID must be specified, all wrapped using the GROUP() macro.
  */
-#define PINMUX_DATA_REG(name, r, r_width) \
-       .reg = r, .reg_width = r_width, \
-       .enum_ids = (const u16 [r_width]) \
+#define PINMUX_DATA_REG(name, r, r_width, ids)                         \
+       .reg = r, .reg_width = r_width +                                \
+       BUILD_BUG_ON_ZERO(sizeof((const u16 []) { ids }) / sizeof(u16) != \
+                         r_width),                                     \
+       .enum_ids = (const u16 [r_width]) { ids }
 
 struct pinmux_irq {
        const short *gpios;
@@ -269,7 +292,6 @@ void sh_pfc_write(struct sh_pfc *pfc, u32 reg, u32 data);
 const struct pinmux_bias_reg *
 sh_pfc_pin_to_bias_reg(const struct sh_pfc *pfc, unsigned int pin,
                       unsigned int *bit);
-int sh_pfc_config_mux_for_gpio(struct udevice *dev, unsigned pin_selector);
 
 extern const struct sh_pfc_soc_info r8a7790_pinmux_info;
 extern const struct sh_pfc_soc_info r8a7791_pinmux_info;
@@ -282,6 +304,7 @@ extern const struct sh_pfc_soc_info r8a77965_pinmux_info;
 extern const struct sh_pfc_soc_info r8a77970_pinmux_info;
 extern const struct sh_pfc_soc_info r8a77990_pinmux_info;
 extern const struct sh_pfc_soc_info r8a77995_pinmux_info;
+
 /* -----------------------------------------------------------------------------
  * Helper macros to create pin and port lists
  */
@@ -351,6 +374,28 @@ extern const struct sh_pfc_soc_info r8a77995_pinmux_info;
        PINMUX_DATA(fn##_MARK, FN_##msel, FN_##fn, FN_##ipsr)
 
 /*
+ * Describe a pinmux configuration similar to PINMUX_IPSR_MSEL, but with
+ * an additional select register that controls physical multiplexing
+ * with another pin.
+ *   - ipsr: IPSR field
+ *   - fn: Function name, also referring to the IPSR field
+ *   - psel: Physical multiplexing selector
+ *   - msel: Module selector
+ */
+#define PINMUX_IPSR_PHYS_MSEL(ipsr, fn, psel, msel) \
+       PINMUX_DATA(fn##_MARK, FN_##psel, FN_##msel, FN_##fn, FN_##ipsr)
+
+/*
+ * Describe a pinmux configuration in which a pin is physically multiplexed
+ * with other pins.
+ *   - ipsr: IPSR field (unused, for documentation purposes only)
+ *   - fn: Function name
+ *   - psel: Physical multiplexing selector
+ */
+#define PINMUX_IPSR_PHYS(ipsr, fn, psel) \
+       PINMUX_DATA(fn##_MARK, FN_##psel)
+
+/*
  * Describe a pinmux configuration for a single-function pin with GPIO
  * capability.
  *   - fn: Function name
@@ -397,12 +442,11 @@ extern const struct sh_pfc_soc_info r8a77995_pinmux_info;
 
 #define PORT_GP_CFG_11(bank, fn, sfx, cfg)                             \
        PORT_GP_CFG_10(bank, fn, sfx, cfg),                             \
-       PORT_GP_CFG_1(bank, 10,  fn, sfx, cfg)
+       PORT_GP_CFG_1(bank, 10, fn, sfx, cfg)
 #define PORT_GP_11(bank, fn, sfx)      PORT_GP_CFG_11(bank, fn, sfx, 0)
 
 #define PORT_GP_CFG_12(bank, fn, sfx, cfg)                             \
-       PORT_GP_CFG_10(bank, fn, sfx, cfg),                             \
-       PORT_GP_CFG_1(bank, 10, fn, sfx, cfg),                          \
+       PORT_GP_CFG_11(bank, fn, sfx, cfg),                             \
        PORT_GP_CFG_1(bank, 11, fn, sfx, cfg)
 #define PORT_GP_12(bank, fn, sfx)      PORT_GP_CFG_12(bank, fn, sfx, 0)
 
@@ -605,7 +649,9 @@ extern const struct sh_pfc_soc_info r8a77995_pinmux_info;
  */
 #define PORTCR(nr, reg)                                                        \
        {                                                               \
-               PINMUX_CFG_REG_VAR("PORT" nr "CR", reg, 8, 2, 2, 1, 3) {\
+               PINMUX_CFG_REG_VAR("PORT" nr "CR", reg, 8,              \
+                                  GROUP(2, 2, 1, 3),                   \
+                                  GROUP(                               \
                        /* PULMD[1:0], handled by .set_bias() */        \
                        0, 0, 0, 0,                                     \
                        /* IE and OE */                                 \
@@ -617,7 +663,7 @@ extern const struct sh_pfc_soc_info r8a77995_pinmux_info;
                        PORT##nr##_FN2, PORT##nr##_FN3,                 \
                        PORT##nr##_FN4, PORT##nr##_FN5,                 \
                        PORT##nr##_FN6, PORT##nr##_FN7                  \
-                                                                     \
+               ))                                                      \
        }
 
 /*