diff options
author | Wolfram Sang <wsa@the-dreams.de> | 2015-01-05 17:45:59 -0500 |
---|---|---|
committer | Wolfram Sang <wsa@the-dreams.de> | 2015-03-13 10:10:44 -0400 |
commit | b7f625840267b18ef1011cba0085bb7e237d76f7 (patch) | |
tree | abc1b0d0ed98c147c6a0bc60f3fd30ed89ec3c73 | |
parent | 2187f03a9576c4fb8342deed912b5ba6fcf98cba (diff) |
i2c: add quirk checks to core
Let the core do the checks if HW quirks prevent a transfer. Saves code
from drivers and adds consistency.
Signed-off-by: Wolfram Sang <wsa@the-dreams.de>
Tested-by: Ray Jui <rjui@broadcom.com>
Tested-by: Ivan T. Ivanov <iivanov@mm-sol.com>
Tested-by: Neelesh Gupta <neelegup@linux.vnet.ibm.com>
Tested-By: Ludovic Desroches <ludovic.desroches@atmel.com>
-rw-r--r-- | drivers/i2c/i2c-core.c | 62 |
1 files changed, 62 insertions, 0 deletions
diff --git a/drivers/i2c/i2c-core.c b/drivers/i2c/i2c-core.c index 210cf4874cb7..57a86f4aab43 100644 --- a/drivers/i2c/i2c-core.c +++ b/drivers/i2c/i2c-core.c | |||
@@ -1929,6 +1929,65 @@ module_exit(i2c_exit); | |||
1929 | * ---------------------------------------------------- | 1929 | * ---------------------------------------------------- |
1930 | */ | 1930 | */ |
1931 | 1931 | ||
1932 | /* Check if val is exceeding the quirk IFF quirk is non 0 */ | ||
1933 | #define i2c_quirk_exceeded(val, quirk) ((quirk) && ((val) > (quirk))) | ||
1934 | |||
1935 | static int i2c_quirk_error(struct i2c_adapter *adap, struct i2c_msg *msg, char *err_msg) | ||
1936 | { | ||
1937 | dev_err_ratelimited(&adap->dev, "adapter quirk: %s (addr 0x%04x, size %u, %s)\n", | ||
1938 | err_msg, msg->addr, msg->len, | ||
1939 | msg->flags & I2C_M_RD ? "read" : "write"); | ||
1940 | return -EOPNOTSUPP; | ||
1941 | } | ||
1942 | |||
1943 | static int i2c_check_for_quirks(struct i2c_adapter *adap, struct i2c_msg *msgs, int num) | ||
1944 | { | ||
1945 | const struct i2c_adapter_quirks *q = adap->quirks; | ||
1946 | int max_num = q->max_num_msgs, i; | ||
1947 | bool do_len_check = true; | ||
1948 | |||
1949 | if (q->flags & I2C_AQ_COMB) { | ||
1950 | max_num = 2; | ||
1951 | |||
1952 | /* special checks for combined messages */ | ||
1953 | if (num == 2) { | ||
1954 | if (q->flags & I2C_AQ_COMB_WRITE_FIRST && msgs[0].flags & I2C_M_RD) | ||
1955 | return i2c_quirk_error(adap, &msgs[0], "1st comb msg must be write"); | ||
1956 | |||
1957 | if (q->flags & I2C_AQ_COMB_READ_SECOND && !(msgs[1].flags & I2C_M_RD)) | ||
1958 | return i2c_quirk_error(adap, &msgs[1], "2nd comb msg must be read"); | ||
1959 | |||
1960 | if (q->flags & I2C_AQ_COMB_SAME_ADDR && msgs[0].addr != msgs[1].addr) | ||
1961 | return i2c_quirk_error(adap, &msgs[0], "comb msg only to same addr"); | ||
1962 | |||
1963 | if (i2c_quirk_exceeded(msgs[0].len, q->max_comb_1st_msg_len)) | ||
1964 | return i2c_quirk_error(adap, &msgs[0], "msg too long"); | ||
1965 | |||
1966 | if (i2c_quirk_exceeded(msgs[1].len, q->max_comb_2nd_msg_len)) | ||
1967 | return i2c_quirk_error(adap, &msgs[1], "msg too long"); | ||
1968 | |||
1969 | do_len_check = false; | ||
1970 | } | ||
1971 | } | ||
1972 | |||
1973 | if (i2c_quirk_exceeded(num, max_num)) | ||
1974 | return i2c_quirk_error(adap, &msgs[0], "too many messages"); | ||
1975 | |||
1976 | for (i = 0; i < num; i++) { | ||
1977 | u16 len = msgs[i].len; | ||
1978 | |||
1979 | if (msgs[i].flags & I2C_M_RD) { | ||
1980 | if (do_len_check && i2c_quirk_exceeded(len, q->max_read_len)) | ||
1981 | return i2c_quirk_error(adap, &msgs[i], "msg too long"); | ||
1982 | } else { | ||
1983 | if (do_len_check && i2c_quirk_exceeded(len, q->max_write_len)) | ||
1984 | return i2c_quirk_error(adap, &msgs[i], "msg too long"); | ||
1985 | } | ||
1986 | } | ||
1987 | |||
1988 | return 0; | ||
1989 | } | ||
1990 | |||
1932 | /** | 1991 | /** |
1933 | * __i2c_transfer - unlocked flavor of i2c_transfer | 1992 | * __i2c_transfer - unlocked flavor of i2c_transfer |
1934 | * @adap: Handle to I2C bus | 1993 | * @adap: Handle to I2C bus |
@@ -1946,6 +2005,9 @@ int __i2c_transfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num) | |||
1946 | unsigned long orig_jiffies; | 2005 | unsigned long orig_jiffies; |
1947 | int ret, try; | 2006 | int ret, try; |
1948 | 2007 | ||
2008 | if (adap->quirks && i2c_check_for_quirks(adap, msgs, num)) | ||
2009 | return -EOPNOTSUPP; | ||
2010 | |||
1949 | /* i2c_trace_msg gets enabled when tracepoint i2c_transfer gets | 2011 | /* i2c_trace_msg gets enabled when tracepoint i2c_transfer gets |
1950 | * enabled. This is an efficient way of keeping the for-loop from | 2012 | * enabled. This is an efficient way of keeping the for-loop from |
1951 | * being executed when not needed. | 2013 | * being executed when not needed. |