1 // SPDX-License-Identifier: GPL-2.0-only 2 /* 3 * Copyright (C) 2021-2023 Digiteq Automotive 4 * author: Martin Tuma <martin.tuma@digiteqautomotive.com> 5 * 6 * This module handles the IIO trigger device. The card has two signal inputs 7 * for event triggers that can be used to record events related to the video 8 * stream. A standard linux IIO device with triggered buffer capability is 9 * created and configured that can be used to fetch the events with the same 10 * clock source as the video frames. 11 */ 12 13 #include <linux/iio/iio.h> 14 #include <linux/iio/buffer.h> 15 #include <linux/iio/trigger.h> 16 #include <linux/iio/trigger_consumer.h> 17 #include <linux/iio/triggered_buffer.h> 18 #include <linux/pci.h> 19 #include <linux/dma/amd_xdma.h> 20 #include "mgb4_core.h" 21 #include "mgb4_trigger.h" 22 23 struct trigger_data { 24 struct mgb4_dev *mgbdev; 25 struct iio_trigger *trig; 26 }; 27 28 static int trigger_read_raw(struct iio_dev *indio_dev, 29 struct iio_chan_spec const *chan, int *val, 30 int *val2, long mask) 31 { 32 struct trigger_data *st = iio_priv(indio_dev); 33 34 switch (mask) { 35 case IIO_CHAN_INFO_RAW: 36 if (iio_buffer_enabled(indio_dev)) 37 return -EBUSY; 38 *val = mgb4_read_reg(&st->mgbdev->video, 0xA0); 39 40 return IIO_VAL_INT; 41 } 42 43 return -EINVAL; 44 } 45 46 static int trigger_set_state(struct iio_trigger *trig, bool state) 47 { 48 struct iio_dev *indio_dev = iio_trigger_get_drvdata(trig); 49 struct trigger_data *st = iio_priv(indio_dev); 50 int irq = xdma_get_user_irq(st->mgbdev->xdev, 11); 51 52 if (state) 53 xdma_enable_user_irq(st->mgbdev->xdev, irq); 54 else 55 xdma_disable_user_irq(st->mgbdev->xdev, irq); 56 57 return 0; 58 } 59 60 static const struct iio_trigger_ops trigger_ops = { 61 .set_trigger_state = &trigger_set_state, 62 }; 63 64 static const struct iio_info trigger_info = { 65 .read_raw = trigger_read_raw, 66 }; 67 68 #define TRIGGER_CHANNEL(_si) { \ 69 .type = IIO_ACTIVITY, \ 70 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \ 71 .scan_index = _si, \ 72 .scan_type = { \ 73 .sign = 'u', \ 74 .realbits = 32, \ 75 .storagebits = 32, \ 76 .shift = 0, \ 77 .endianness = IIO_CPU \ 78 }, \ 79 } 80 81 static const struct iio_chan_spec trigger_channels[] = { 82 TRIGGER_CHANNEL(0), 83 IIO_CHAN_SOFT_TIMESTAMP(1), 84 }; 85 86 static irqreturn_t trigger_handler(int irq, void *p) 87 { 88 struct iio_poll_func *pf = p; 89 struct iio_dev *indio_dev = pf->indio_dev; 90 struct trigger_data *st = iio_priv(indio_dev); 91 struct { 92 u32 data; 93 s64 ts __aligned(8); 94 } scan; 95 96 scan.data = mgb4_read_reg(&st->mgbdev->video, 0xA0); 97 mgb4_write_reg(&st->mgbdev->video, 0xA0, scan.data); 98 99 iio_push_to_buffers_with_timestamp(indio_dev, &scan, pf->timestamp); 100 iio_trigger_notify_done(indio_dev->trig); 101 102 mgb4_write_reg(&st->mgbdev->video, 0xB4, 1U << 11); 103 104 return IRQ_HANDLED; 105 } 106 107 static int probe_trigger(struct iio_dev *indio_dev, int irq) 108 { 109 int ret; 110 struct trigger_data *st = iio_priv(indio_dev); 111 112 st->trig = iio_trigger_alloc(&st->mgbdev->pdev->dev, "%s-dev%d", 113 indio_dev->name, iio_device_id(indio_dev)); 114 if (!st->trig) 115 return -ENOMEM; 116 117 ret = request_irq(irq, &iio_trigger_generic_data_rdy_poll, 0, 118 "mgb4-trigger", st->trig); 119 if (ret) 120 goto error_free_trig; 121 122 st->trig->ops = &trigger_ops; 123 iio_trigger_set_drvdata(st->trig, indio_dev); 124 ret = iio_trigger_register(st->trig); 125 if (ret) 126 goto error_free_irq; 127 128 indio_dev->trig = iio_trigger_get(st->trig); 129 130 return 0; 131 132 error_free_irq: 133 free_irq(irq, st->trig); 134 error_free_trig: 135 iio_trigger_free(st->trig); 136 137 return ret; 138 } 139 140 static void remove_trigger(struct iio_dev *indio_dev, int irq) 141 { 142 struct trigger_data *st = iio_priv(indio_dev); 143 144 iio_trigger_unregister(st->trig); 145 free_irq(irq, st->trig); 146 iio_trigger_free(st->trig); 147 } 148 149 struct iio_dev *mgb4_trigger_create(struct mgb4_dev *mgbdev) 150 { 151 struct iio_dev *indio_dev; 152 struct trigger_data *data; 153 struct pci_dev *pdev = mgbdev->pdev; 154 struct device *dev = &pdev->dev; 155 int rv, irq; 156 157 indio_dev = iio_device_alloc(dev, sizeof(*data)); 158 if (!indio_dev) 159 return NULL; 160 161 indio_dev->info = &trigger_info; 162 indio_dev->name = "mgb4"; 163 indio_dev->modes = INDIO_DIRECT_MODE; 164 indio_dev->channels = trigger_channels; 165 indio_dev->num_channels = ARRAY_SIZE(trigger_channels); 166 167 data = iio_priv(indio_dev); 168 data->mgbdev = mgbdev; 169 170 irq = xdma_get_user_irq(mgbdev->xdev, 11); 171 rv = probe_trigger(indio_dev, irq); 172 if (rv < 0) { 173 dev_err(dev, "iio triggered setup failed\n"); 174 goto error_alloc; 175 } 176 rv = iio_triggered_buffer_setup(indio_dev, &iio_pollfunc_store_time, 177 trigger_handler, NULL); 178 if (rv < 0) { 179 dev_err(dev, "iio triggered buffer setup failed\n"); 180 goto error_trigger; 181 } 182 rv = iio_device_register(indio_dev); 183 if (rv < 0) { 184 dev_err(dev, "iio device register failed\n"); 185 goto error_buffer; 186 } 187 188 return indio_dev; 189 190 error_buffer: 191 iio_triggered_buffer_cleanup(indio_dev); 192 error_trigger: 193 remove_trigger(indio_dev, irq); 194 error_alloc: 195 iio_device_free(indio_dev); 196 197 return NULL; 198 } 199 200 void mgb4_trigger_free(struct iio_dev *indio_dev) 201 { 202 struct trigger_data *st = iio_priv(indio_dev); 203 204 iio_device_unregister(indio_dev); 205 iio_triggered_buffer_cleanup(indio_dev); 206 remove_trigger(indio_dev, xdma_get_user_irq(st->mgbdev->xdev, 11)); 207 iio_device_free(indio_dev); 208 } 209