1 // SPDX-License-Identifier: GPL-2.0-or-later 2 /* Copyright (C) 2019 IBM Corp. */ 3 4 /* Pieces to enable drivers to implement the .set callback */ 5 6 #include "pinmux-aspeed.h" 7 8 static const char *const aspeed_pinmux_ips[] = { 9 [ASPEED_IP_SCU] = "SCU", 10 [ASPEED_IP_GFX] = "GFX", 11 [ASPEED_IP_LPC] = "LPC", 12 }; 13 14 static inline void aspeed_sig_desc_print_val( 15 const struct aspeed_sig_desc *desc, bool enable, u32 rv) 16 { 17 pr_debug("Want %s%X[0x%08X]=0x%X, got 0x%X from 0x%08X\n", 18 aspeed_pinmux_ips[desc->ip], desc->reg, 19 desc->mask, enable ? desc->enable : desc->disable, 20 (rv & desc->mask) >> __ffs(desc->mask), rv); 21 } 22 23 /** 24 * aspeed_sig_desc_eval() - Query the enabled or disabled state of a signal 25 * descriptor. 26 * 27 * @desc: The signal descriptor of interest 28 * @enabled: True to query the enabled state, false to query disabled state 29 * @map: The IP block's regmap instance 30 * 31 * Return: 1 if the descriptor's bitfield is configured to the state 32 * selected by @enabled, 0 if not, and less than zero if an unrecoverable 33 * failure occurred 34 * 35 * Evaluation of descriptor state is non-trivial in that it is not a binary 36 * outcome: The bitfields can be greater than one bit in size and thus can take 37 * a value that is neither the enabled nor disabled state recorded in the 38 * descriptor (typically this means a different function to the one of interest 39 * is enabled). Thus we must explicitly test for either condition as required. 40 */ 41 int aspeed_sig_desc_eval(const struct aspeed_sig_desc *desc, 42 bool enabled, struct regmap *map) 43 { 44 int ret; 45 unsigned int raw; 46 u32 want; 47 48 if (!map) 49 return -ENODEV; 50 51 ret = regmap_read(map, desc->reg, &raw); 52 if (ret) 53 return ret; 54 55 aspeed_sig_desc_print_val(desc, enabled, raw); 56 want = enabled ? desc->enable : desc->disable; 57 58 return ((raw & desc->mask) >> __ffs(desc->mask)) == want; 59 } 60 61 /** 62 * aspeed_sig_expr_eval - Query the enabled or disabled state for a 63 * mux function's signal on a pin 64 * 65 * @ctx: The driver context for the pinctrl IP 66 * @expr: An expression controlling the signal for a mux function on a pin 67 * @enabled: True to query the enabled state, false to query disabled state 68 * 69 * Return: 1 if the expression composed by @enabled evaluates true, 0 if not, 70 * and less than zero if an unrecoverable failure occurred. 71 * 72 * A mux function is enabled or disabled if the function's signal expression 73 * for each pin in the function's pin group evaluates true for the desired 74 * state. An signal expression evaluates true if all of its associated signal 75 * descriptors evaluate true for the desired state. 76 * 77 * If an expression's state is described by more than one bit, either through 78 * multi-bit bitfields in a single signal descriptor or through multiple signal 79 * descriptors of a single bit then it is possible for the expression to be in 80 * neither the enabled nor disabled state. Thus we must explicitly test for 81 * either condition as required. 82 */ 83 int aspeed_sig_expr_eval(struct aspeed_pinmux_data *ctx, 84 const struct aspeed_sig_expr *expr, bool enabled) 85 { 86 int ret; 87 int i; 88 89 if (ctx->ops->eval) 90 return ctx->ops->eval(ctx, expr, enabled); 91 92 for (i = 0; i < expr->ndescs; i++) { 93 const struct aspeed_sig_desc *desc = &expr->descs[i]; 94 95 ret = aspeed_sig_desc_eval(desc, enabled, ctx->maps[desc->ip]); 96 if (ret <= 0) 97 return ret; 98 } 99 100 return 1; 101 } 102