aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/media/rc/ir-lirc-codec.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/media/rc/ir-lirc-codec.c')
-rw-r--r--drivers/media/rc/ir-lirc-codec.c33
1 files changed, 29 insertions, 4 deletions
diff --git a/drivers/media/rc/ir-lirc-codec.c b/drivers/media/rc/ir-lirc-codec.c
index d2fd064474aa..6ad4a0770613 100644
--- a/drivers/media/rc/ir-lirc-codec.c
+++ b/drivers/media/rc/ir-lirc-codec.c
@@ -107,6 +107,12 @@ static ssize_t ir_lirc_transmit_ir(struct file *file, const char __user *buf,
107 unsigned int *txbuf; /* buffer with values to transmit */ 107 unsigned int *txbuf; /* buffer with values to transmit */
108 ssize_t ret = -EINVAL; 108 ssize_t ret = -EINVAL;
109 size_t count; 109 size_t count;
110 ktime_t start;
111 s64 towait;
112 unsigned int duration = 0; /* signal duration in us */
113 int i;
114
115 start = ktime_get();
110 116
111 lirc = lirc_get_pdata(file); 117 lirc = lirc_get_pdata(file);
112 if (!lirc) 118 if (!lirc)
@@ -129,11 +135,30 @@ static ssize_t ir_lirc_transmit_ir(struct file *file, const char __user *buf,
129 goto out; 135 goto out;
130 } 136 }
131 137
132 if (dev->tx_ir) 138 if (!dev->tx_ir) {
133 ret = dev->tx_ir(dev, txbuf, count); 139 ret = -ENOSYS;
140 goto out;
141 }
142
143 ret = dev->tx_ir(dev, txbuf, (u32)n);
144 if (ret < 0)
145 goto out;
146
147 for (i = 0; i < ret; i++)
148 duration += txbuf[i];
134 149
135 if (ret > 0) 150 ret *= sizeof(unsigned int);
136 ret *= sizeof(unsigned); 151
152 /*
153 * The lircd gap calculation expects the write function to
154 * wait for the actual IR signal to be transmitted before
155 * returning.
156 */
157 towait = ktime_us_delta(ktime_add_us(start, duration), ktime_get());
158 if (towait > 0) {
159 set_current_state(TASK_INTERRUPTIBLE);
160 schedule_timeout(usecs_to_jiffies(towait));
161 }
137 162
138out: 163out:
139 kfree(txbuf); 164 kfree(txbuf);