1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * Input driver for joysticks connected over ADC. 4 * Copyright (c) 2019-2020 Artur Rojek <contact@artur-rojek.eu> 5 */ 6 #include <linux/ctype.h> 7 #include <linux/input.h> 8 #include <linux/iio/iio.h> 9 #include <linux/iio/consumer.h> 10 #include <linux/module.h> 11 #include <linux/platform_device.h> 12 #include <linux/property.h> 13 14 #include <linux/unaligned.h> 15 16 struct adc_joystick_axis { 17 u32 code; 18 bool inverted; 19 }; 20 21 struct adc_joystick { 22 struct input_dev *input; 23 struct iio_cb_buffer *buffer; 24 struct iio_channel *chans; 25 unsigned int num_chans; 26 struct adc_joystick_axis axes[] __counted_by(num_chans); 27 }; 28 29 static int adc_joystick_invert(struct input_dev *dev, 30 unsigned int axis, int val) 31 { 32 int min = input_abs_get_min(dev, axis); 33 int max = input_abs_get_max(dev, axis); 34 35 return (max + min) - val; 36 } 37 38 static void adc_joystick_poll(struct input_dev *input) 39 { 40 struct adc_joystick *joy = input_get_drvdata(input); 41 int i, val, ret; 42 43 for (i = 0; i < joy->num_chans; i++) { 44 ret = iio_read_channel_raw(&joy->chans[i], &val); 45 if (ret < 0) 46 return; 47 if (joy->axes[i].inverted) 48 val = adc_joystick_invert(input, i, val); 49 input_report_abs(input, joy->axes[i].code, val); 50 } 51 input_sync(input); 52 } 53 54 static int adc_joystick_handle(const void *data, void *private) 55 { 56 struct adc_joystick *joy = private; 57 enum iio_endian endianness; 58 int bytes, msb, val, idx, i; 59 const u16 *data_u16; 60 bool sign; 61 62 bytes = joy->chans[0].channel->scan_type.storagebits >> 3; 63 64 for (i = 0; i < joy->num_chans; ++i) { 65 idx = joy->chans[i].channel->scan_index; 66 endianness = joy->chans[i].channel->scan_type.endianness; 67 msb = joy->chans[i].channel->scan_type.realbits - 1; 68 sign = tolower(joy->chans[i].channel->scan_type.sign) == 's'; 69 70 switch (bytes) { 71 case 1: 72 val = ((const u8 *)data)[idx]; 73 break; 74 case 2: 75 data_u16 = (const u16 *)data + idx; 76 77 /* 78 * Data is aligned to the sample size by IIO core. 79 * Call `get_unaligned_xe16` to hide type casting. 80 */ 81 if (endianness == IIO_BE) 82 val = get_unaligned_be16(data_u16); 83 else if (endianness == IIO_LE) 84 val = get_unaligned_le16(data_u16); 85 else /* IIO_CPU */ 86 val = *data_u16; 87 break; 88 default: 89 return -EINVAL; 90 } 91 92 val >>= joy->chans[i].channel->scan_type.shift; 93 if (sign) 94 val = sign_extend32(val, msb); 95 else 96 val &= GENMASK(msb, 0); 97 if (joy->axes[i].inverted) 98 val = adc_joystick_invert(joy->input, i, val); 99 input_report_abs(joy->input, joy->axes[i].code, val); 100 } 101 102 input_sync(joy->input); 103 104 return 0; 105 } 106 107 static int adc_joystick_open(struct input_dev *dev) 108 { 109 struct adc_joystick *joy = input_get_drvdata(dev); 110 struct device *devp = &dev->dev; 111 int ret; 112 113 ret = iio_channel_start_all_cb(joy->buffer); 114 if (ret) 115 dev_err(devp, "Unable to start callback buffer: %d\n", ret); 116 117 return ret; 118 } 119 120 static void adc_joystick_close(struct input_dev *dev) 121 { 122 struct adc_joystick *joy = input_get_drvdata(dev); 123 124 iio_channel_stop_all_cb(joy->buffer); 125 } 126 127 static void adc_joystick_cleanup(void *data) 128 { 129 iio_channel_release_all_cb(data); 130 } 131 132 static int adc_joystick_set_axes(struct device *dev, struct adc_joystick *joy) 133 { 134 struct adc_joystick_axis *axes = joy->axes; 135 s32 range[2], fuzz, flat; 136 unsigned int num_axes; 137 int error, i; 138 139 num_axes = device_get_child_node_count(dev); 140 if (!num_axes) { 141 dev_err(dev, "Unable to find child nodes\n"); 142 return -EINVAL; 143 } 144 145 if (num_axes != joy->num_chans) { 146 dev_err(dev, "Got %d child nodes for %d channels\n", 147 num_axes, joy->num_chans); 148 return -EINVAL; 149 } 150 151 device_for_each_child_node_scoped(dev, child) { 152 error = fwnode_property_read_u32(child, "reg", &i); 153 if (error) { 154 dev_err(dev, "reg invalid or missing\n"); 155 return error; 156 } 157 158 if (i >= num_axes) { 159 dev_err(dev, "No matching axis for reg %d\n", i); 160 return -EINVAL; 161 } 162 163 error = fwnode_property_read_u32(child, "linux,code", 164 &axes[i].code); 165 if (error) { 166 dev_err(dev, "linux,code invalid or missing\n"); 167 return error; 168 } 169 170 error = fwnode_property_read_u32_array(child, "abs-range", 171 range, 2); 172 if (error) { 173 dev_err(dev, "abs-range invalid or missing\n"); 174 return error; 175 } 176 177 if (range[0] > range[1]) { 178 dev_dbg(dev, "abs-axis %d inverted\n", i); 179 axes[i].inverted = true; 180 swap(range[0], range[1]); 181 } 182 183 if (fwnode_property_read_u32(child, "abs-fuzz", &fuzz)) 184 fuzz = 0; 185 186 if (fwnode_property_read_u32(child, "abs-flat", &flat)) 187 flat = 0; 188 189 input_set_abs_params(joy->input, axes[i].code, 190 range[0], range[1], fuzz, flat); 191 } 192 193 return 0; 194 } 195 196 197 static int adc_joystick_count_channels(struct device *dev, 198 const struct iio_channel *chans, 199 bool polled, 200 unsigned int *num_chans) 201 { 202 int bits; 203 int i; 204 205 /* 206 * Count how many channels we got. NULL terminated. 207 * Do not check the storage size if using polling. 208 */ 209 for (i = 0; chans[i].indio_dev; i++) { 210 if (polled) 211 continue; 212 bits = chans[i].channel->scan_type.storagebits; 213 if (!bits || bits > 16) { 214 dev_err(dev, "Unsupported channel storage size\n"); 215 return -EINVAL; 216 } 217 if (bits != chans[0].channel->scan_type.storagebits) { 218 dev_err(dev, "Channels must have equal storage size\n"); 219 return -EINVAL; 220 } 221 } 222 223 *num_chans = i; 224 return 0; 225 } 226 227 static int adc_joystick_probe(struct platform_device *pdev) 228 { 229 struct device *dev = &pdev->dev; 230 struct iio_channel *chans; 231 struct adc_joystick *joy; 232 struct input_dev *input; 233 unsigned int poll_interval = 0; 234 unsigned int num_chans; 235 int error; 236 237 chans = devm_iio_channel_get_all(dev); 238 error = PTR_ERR_OR_ZERO(chans); 239 if (error) { 240 if (error != -EPROBE_DEFER) 241 dev_err(dev, "Unable to get IIO channels"); 242 return error; 243 } 244 245 error = device_property_read_u32(dev, "poll-interval", &poll_interval); 246 if (error) { 247 /* -EINVAL means the property is absent. */ 248 if (error != -EINVAL) 249 return error; 250 } else if (poll_interval == 0) { 251 dev_err(dev, "Unable to get poll-interval\n"); 252 return -EINVAL; 253 } 254 255 error = adc_joystick_count_channels(dev, chans, poll_interval != 0, 256 &num_chans); 257 if (error) 258 return error; 259 260 joy = devm_kzalloc(dev, struct_size(joy, axes, num_chans), GFP_KERNEL); 261 if (!joy) 262 return -ENOMEM; 263 264 joy->chans = chans; 265 joy->num_chans = num_chans; 266 267 input = devm_input_allocate_device(dev); 268 if (!input) { 269 dev_err(dev, "Unable to allocate input device\n"); 270 return -ENOMEM; 271 } 272 273 joy->input = input; 274 input->name = pdev->name; 275 input->id.bustype = BUS_HOST; 276 277 error = adc_joystick_set_axes(dev, joy); 278 if (error) 279 return error; 280 281 if (poll_interval != 0) { 282 input_setup_polling(input, adc_joystick_poll); 283 input_set_poll_interval(input, poll_interval); 284 } else { 285 input->open = adc_joystick_open; 286 input->close = adc_joystick_close; 287 288 joy->buffer = iio_channel_get_all_cb(dev, adc_joystick_handle, 289 joy); 290 if (IS_ERR(joy->buffer)) { 291 dev_err(dev, "Unable to allocate callback buffer\n"); 292 return PTR_ERR(joy->buffer); 293 } 294 295 error = devm_add_action_or_reset(dev, adc_joystick_cleanup, 296 joy->buffer); 297 if (error) { 298 dev_err(dev, "Unable to add action\n"); 299 return error; 300 } 301 } 302 303 input_set_drvdata(input, joy); 304 305 error = input_register_device(input); 306 if (error) { 307 dev_err(dev, "Unable to register input device\n"); 308 return error; 309 } 310 311 return 0; 312 } 313 314 static const struct of_device_id adc_joystick_of_match[] = { 315 { .compatible = "adc-joystick", }, 316 { } 317 }; 318 MODULE_DEVICE_TABLE(of, adc_joystick_of_match); 319 320 static struct platform_driver adc_joystick_driver = { 321 .driver = { 322 .name = "adc-joystick", 323 .of_match_table = adc_joystick_of_match, 324 }, 325 .probe = adc_joystick_probe, 326 }; 327 module_platform_driver(adc_joystick_driver); 328 329 MODULE_DESCRIPTION("Input driver for joysticks connected over ADC"); 330 MODULE_AUTHOR("Artur Rojek <contact@artur-rojek.eu>"); 331 MODULE_LICENSE("GPL"); 332