blob: 9be76c808fccf09ef8a8785152657510bcef1f1e [file] [log] [blame]
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001/*
2 * Audio and Music Data Transmission Protocol (IEC 61883-6) streams
3 * with Common Isochronous Packet (IEC 61883-1) headers
4 *
5 * Copyright (c) Clemens Ladisch <clemens@ladisch.de>
6 * Licensed under the terms of the GNU General Public License, version 2.
7 */
8
9#include <linux/device.h>
10#include <linux/err.h>
11#include <linux/firewire.h>
12#include <linux/module.h>
13#include <linux/slab.h>
14#include <sound/pcm.h>
Takashi Sakamoto7b2d99f2014-04-25 22:44:52 +090015#include <sound/pcm_params.h>
Takashi Sakamotod67c46b2015-09-19 11:21:54 +090016#include "amdtp-stream.h"
Clemens Ladisch31ef9132011-03-15 07:53:21 +010017
18#define TICKS_PER_CYCLE 3072
19#define CYCLES_PER_SECOND 8000
20#define TICKS_PER_SECOND (TICKS_PER_CYCLE * CYCLES_PER_SECOND)
21
Takashi Sakamoto0c95c1d2016-05-09 21:12:46 +090022/* Always support Linux tracing subsystem. */
23#define CREATE_TRACE_POINTS
24#include "amdtp-stream-trace.h"
25
Takashi Sakamotoca5b5052015-02-21 11:50:17 +090026#define TRANSFER_DELAY_TICKS 0x2e00 /* 479.17 microseconds */
Clemens Ladisch31ef9132011-03-15 07:53:21 +010027
Takashi Sakamotob445db42014-04-25 22:44:43 +090028/* isochronous header parameters */
29#define ISO_DATA_LENGTH_SHIFT 16
Takashi Sakamoto3b196c392017-03-31 22:06:07 +090030#define TAG_NO_CIP_HEADER 0
Clemens Ladisch31ef9132011-03-15 07:53:21 +010031#define TAG_CIP 1
32
Takashi Sakamotob445db42014-04-25 22:44:43 +090033/* common isochronous packet header parameters */
Takashi Sakamoto9a2820c2015-05-22 23:21:12 +090034#define CIP_EOH_SHIFT 31
35#define CIP_EOH (1u << CIP_EOH_SHIFT)
Takashi Sakamotob445db42014-04-25 22:44:43 +090036#define CIP_EOH_MASK 0x80000000
Takashi Sakamoto9a2820c2015-05-22 23:21:12 +090037#define CIP_SID_SHIFT 24
38#define CIP_SID_MASK 0x3f000000
39#define CIP_DBS_MASK 0x00ff0000
40#define CIP_DBS_SHIFT 16
Takashi Sakamoto98638742017-03-22 21:30:16 +090041#define CIP_SPH_MASK 0x00000400
42#define CIP_SPH_SHIFT 10
Takashi Sakamoto9a2820c2015-05-22 23:21:12 +090043#define CIP_DBC_MASK 0x000000ff
44#define CIP_FMT_SHIFT 24
Takashi Sakamotob445db42014-04-25 22:44:43 +090045#define CIP_FMT_MASK 0x3f000000
Takashi Sakamoto9a2820c2015-05-22 23:21:12 +090046#define CIP_FDF_MASK 0x00ff0000
47#define CIP_FDF_SHIFT 16
Takashi Sakamotob445db42014-04-25 22:44:43 +090048#define CIP_SYT_MASK 0x0000ffff
49#define CIP_SYT_NO_INFO 0xffff
Takashi Sakamotob445db42014-04-25 22:44:43 +090050
Takashi Sakamoto51c29fd2015-09-19 11:21:56 +090051/* Audio and Music transfer protocol specific parameters */
Takashi Sakamoto414ba022015-09-19 11:21:53 +090052#define CIP_FMT_AM 0x10
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +090053#define AMDTP_FDF_NO_DATA 0xff
Clemens Ladisch31ef9132011-03-15 07:53:21 +010054
55/* TODO: make these configurable */
56#define INTERRUPT_INTERVAL 16
57#define QUEUE_LENGTH 48
58
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +090059#define IN_PACKET_HEADER_SIZE 4
Takashi Sakamoto4b7da112014-04-25 22:44:45 +090060#define OUT_PACKET_HEADER_SIZE 0
61
Clemens Ladisch76fb8782012-05-13 22:03:09 +020062static void pcm_period_tasklet(unsigned long data);
63
Clemens Ladisch31ef9132011-03-15 07:53:21 +010064/**
Takashi Sakamotobe4a2892014-04-25 22:44:42 +090065 * amdtp_stream_init - initialize an AMDTP stream structure
66 * @s: the AMDTP stream to initialize
Clemens Ladisch31ef9132011-03-15 07:53:21 +010067 * @unit: the target of the stream
Takashi Sakamoto3ff7e8f2014-04-25 22:44:44 +090068 * @dir: the direction of stream
Clemens Ladisch31ef9132011-03-15 07:53:21 +010069 * @flags: the packet transmission method to use
Takashi Sakamoto59558152015-09-19 11:21:55 +090070 * @fmt: the value of fmt field in CIP header
Takashi Sakamotodf075fe2015-09-19 11:22:02 +090071 * @process_data_blocks: callback handler to process data blocks
72 * @protocol_size: the size to allocate newly for protocol
Clemens Ladisch31ef9132011-03-15 07:53:21 +010073 */
Takashi Sakamotobe4a2892014-04-25 22:44:42 +090074int amdtp_stream_init(struct amdtp_stream *s, struct fw_unit *unit,
Takashi Sakamoto59558152015-09-19 11:21:55 +090075 enum amdtp_stream_direction dir, enum cip_flags flags,
Takashi Sakamotodf075fe2015-09-19 11:22:02 +090076 unsigned int fmt,
77 amdtp_stream_process_data_blocks_t process_data_blocks,
78 unsigned int protocol_size)
Clemens Ladisch31ef9132011-03-15 07:53:21 +010079{
Takashi Sakamotodf075fe2015-09-19 11:22:02 +090080 if (process_data_blocks == NULL)
81 return -EINVAL;
82
83 s->protocol = kzalloc(protocol_size, GFP_KERNEL);
84 if (!s->protocol)
85 return -ENOMEM;
86
Takashi Sakamotoc6f224d2015-02-21 23:54:58 +090087 s->unit = unit;
Takashi Sakamoto3ff7e8f2014-04-25 22:44:44 +090088 s->direction = dir;
Clemens Ladisch31ef9132011-03-15 07:53:21 +010089 s->flags = flags;
90 s->context = ERR_PTR(-1);
91 mutex_init(&s->mutex);
Clemens Ladisch76fb8782012-05-13 22:03:09 +020092 tasklet_init(&s->period_tasklet, pcm_period_tasklet, (unsigned long)s);
Clemens Ladischec00f5e2011-03-15 07:57:24 +010093 s->packet_index = 0;
Clemens Ladisch31ef9132011-03-15 07:53:21 +010094
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +090095 init_waitqueue_head(&s->callback_wait);
96 s->callbacked = false;
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +090097
Takashi Sakamoto59558152015-09-19 11:21:55 +090098 s->fmt = fmt;
Takashi Sakamotodf075fe2015-09-19 11:22:02 +090099 s->process_data_blocks = process_data_blocks;
Takashi Sakamoto414ba022015-09-19 11:21:53 +0900100
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100101 return 0;
102}
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900103EXPORT_SYMBOL(amdtp_stream_init);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100104
105/**
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900106 * amdtp_stream_destroy - free stream resources
107 * @s: the AMDTP stream to destroy
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100108 */
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900109void amdtp_stream_destroy(struct amdtp_stream *s)
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100110{
Takashi Sakamoto44c376b2016-03-31 08:47:02 +0900111 /* Not initialized. */
112 if (s->protocol == NULL)
113 return;
114
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900115 WARN_ON(amdtp_stream_running(s));
Takashi Sakamotodf075fe2015-09-19 11:22:02 +0900116 kfree(s->protocol);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100117 mutex_destroy(&s->mutex);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100118}
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900119EXPORT_SYMBOL(amdtp_stream_destroy);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100120
Clemens Ladischc5280e92011-10-16 21:39:00 +0200121const unsigned int amdtp_syt_intervals[CIP_SFC_COUNT] = {
Clemens Ladischa7304e32011-09-04 22:16:10 +0200122 [CIP_SFC_32000] = 8,
123 [CIP_SFC_44100] = 8,
124 [CIP_SFC_48000] = 8,
125 [CIP_SFC_88200] = 16,
126 [CIP_SFC_96000] = 16,
127 [CIP_SFC_176400] = 32,
128 [CIP_SFC_192000] = 32,
129};
130EXPORT_SYMBOL(amdtp_syt_intervals);
131
Takashi Sakamotof9503a62014-05-28 00:14:36 +0900132const unsigned int amdtp_rate_table[CIP_SFC_COUNT] = {
Takashi Sakamoto1017abe2014-04-25 22:44:59 +0900133 [CIP_SFC_32000] = 32000,
134 [CIP_SFC_44100] = 44100,
135 [CIP_SFC_48000] = 48000,
136 [CIP_SFC_88200] = 88200,
137 [CIP_SFC_96000] = 96000,
138 [CIP_SFC_176400] = 176400,
139 [CIP_SFC_192000] = 192000,
140};
141EXPORT_SYMBOL(amdtp_rate_table);
142
Takashi Sakamoto59502292018-10-01 04:11:49 +0900143static int apply_constraint_to_size(struct snd_pcm_hw_params *params,
144 struct snd_pcm_hw_rule *rule)
145{
146 struct snd_interval *s = hw_param_interval(params, rule->var);
147 const struct snd_interval *r =
148 hw_param_interval_c(params, SNDRV_PCM_HW_PARAM_RATE);
Takashi Sakamoto826b5de2018-10-30 15:31:15 +0900149 struct snd_interval t = {0};
150 unsigned int step = 0;
Takashi Sakamoto59502292018-10-01 04:11:49 +0900151 int i;
152
153 for (i = 0; i < CIP_SFC_COUNT; ++i) {
Takashi Sakamoto826b5de2018-10-30 15:31:15 +0900154 if (snd_interval_test(r, amdtp_rate_table[i]))
155 step = max(step, amdtp_syt_intervals[i]);
Takashi Sakamoto59502292018-10-01 04:11:49 +0900156 }
157
Takashi Sakamoto826b5de2018-10-30 15:31:15 +0900158 t.min = roundup(s->min, step);
159 t.max = rounddown(s->max, step);
160 t.integer = 1;
Takashi Sakamoto59502292018-10-01 04:11:49 +0900161
162 return snd_interval_refine(s, &t);
163}
164
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100165/**
Takashi Sakamoto7b2d99f2014-04-25 22:44:52 +0900166 * amdtp_stream_add_pcm_hw_constraints - add hw constraints for PCM substream
167 * @s: the AMDTP stream, which must be initialized.
168 * @runtime: the PCM substream runtime
169 */
170int amdtp_stream_add_pcm_hw_constraints(struct amdtp_stream *s,
171 struct snd_pcm_runtime *runtime)
172{
Takashi Sakamoto55799c52017-06-08 09:11:03 +0900173 struct snd_pcm_hardware *hw = &runtime->hw;
Takashi Sakamoto7b2d99f2014-04-25 22:44:52 +0900174 int err;
175
Takashi Sakamoto55799c52017-06-08 09:11:03 +0900176 hw->info = SNDRV_PCM_INFO_BATCH |
177 SNDRV_PCM_INFO_BLOCK_TRANSFER |
178 SNDRV_PCM_INFO_INTERLEAVED |
179 SNDRV_PCM_INFO_JOINT_DUPLEX |
180 SNDRV_PCM_INFO_MMAP |
181 SNDRV_PCM_INFO_MMAP_VALID;
182
183 /* SNDRV_PCM_INFO_BATCH */
184 hw->periods_min = 2;
185 hw->periods_max = UINT_MAX;
186
187 /* bytes for a frame */
188 hw->period_bytes_min = 4 * hw->channels_max;
189
190 /* Just to prevent from allocating much pages. */
191 hw->period_bytes_max = hw->period_bytes_min * 2048;
192 hw->buffer_bytes_max = hw->period_bytes_max * hw->periods_min;
193
Takashi Sakamoto7b2d99f2014-04-25 22:44:52 +0900194 /*
195 * Currently firewire-lib processes 16 packets in one software
196 * interrupt callback. This equals to 2msec but actually the
197 * interval of the interrupts has a jitter.
198 * Additionally, even if adding a constraint to fit period size to
199 * 2msec, actual calculated frames per period doesn't equal to 2msec,
200 * depending on sampling rate.
201 * Anyway, the interval to call snd_pcm_period_elapsed() cannot 2msec.
202 * Here let us use 5msec for safe period interrupt.
203 */
204 err = snd_pcm_hw_constraint_minmax(runtime,
205 SNDRV_PCM_HW_PARAM_PERIOD_TIME,
206 5000, UINT_MAX);
207 if (err < 0)
208 goto end;
209
210 /* Non-Blocking stream has no more constraints */
211 if (!(s->flags & CIP_BLOCKING))
212 goto end;
213
214 /*
215 * One AMDTP packet can include some frames. In blocking mode, the
216 * number equals to SYT_INTERVAL. So the number is 8, 16 or 32,
217 * depending on its sampling rate. For accurate period interrupt, it's
Yannick Guerrinice991982015-03-09 22:13:03 +0100218 * preferrable to align period/buffer sizes to current SYT_INTERVAL.
Takashi Sakamoto7b2d99f2014-04-25 22:44:52 +0900219 */
Takashi Sakamoto59502292018-10-01 04:11:49 +0900220 err = snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_PERIOD_SIZE,
221 apply_constraint_to_size, NULL,
Takashi Sakamoto826b5de2018-10-30 15:31:15 +0900222 SNDRV_PCM_HW_PARAM_PERIOD_SIZE,
Takashi Sakamoto59502292018-10-01 04:11:49 +0900223 SNDRV_PCM_HW_PARAM_RATE, -1);
Takashi Sakamoto7b2d99f2014-04-25 22:44:52 +0900224 if (err < 0)
225 goto end;
Takashi Sakamoto59502292018-10-01 04:11:49 +0900226 err = snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_BUFFER_SIZE,
227 apply_constraint_to_size, NULL,
Takashi Sakamoto826b5de2018-10-30 15:31:15 +0900228 SNDRV_PCM_HW_PARAM_BUFFER_SIZE,
Takashi Sakamoto59502292018-10-01 04:11:49 +0900229 SNDRV_PCM_HW_PARAM_RATE, -1);
230 if (err < 0)
231 goto end;
Takashi Sakamoto7b2d99f2014-04-25 22:44:52 +0900232end:
233 return err;
234}
235EXPORT_SYMBOL(amdtp_stream_add_pcm_hw_constraints);
236
237/**
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900238 * amdtp_stream_set_parameters - set stream parameters
239 * @s: the AMDTP stream to configure
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100240 * @rate: the sample rate
Takashi Sakamotodf075fe2015-09-19 11:22:02 +0900241 * @data_block_quadlets: the size of a data block in quadlet unit
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100242 *
Clemens Ladischa7304e32011-09-04 22:16:10 +0200243 * The parameters must be set before the stream is started, and must not be
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100244 * changed while the stream is running.
245 */
Takashi Sakamotodf075fe2015-09-19 11:22:02 +0900246int amdtp_stream_set_parameters(struct amdtp_stream *s, unsigned int rate,
247 unsigned int data_block_quadlets)
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100248{
Takashi Sakamotodf075fe2015-09-19 11:22:02 +0900249 unsigned int sfc;
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100250
Takashi Sakamoto547e6312015-09-19 11:21:49 +0900251 for (sfc = 0; sfc < ARRAY_SIZE(amdtp_rate_table); ++sfc) {
Takashi Sakamoto1017abe2014-04-25 22:44:59 +0900252 if (amdtp_rate_table[sfc] == rate)
Takashi Sakamoto547e6312015-09-19 11:21:49 +0900253 break;
254 }
255 if (sfc == ARRAY_SIZE(amdtp_rate_table))
256 return -EINVAL;
Clemens Ladische84d15f2011-09-04 22:12:48 +0200257
Clemens Ladische84d15f2011-09-04 22:12:48 +0200258 s->sfc = sfc;
Takashi Sakamotodf075fe2015-09-19 11:22:02 +0900259 s->data_block_quadlets = data_block_quadlets;
Clemens Ladischa7304e32011-09-04 22:16:10 +0200260 s->syt_interval = amdtp_syt_intervals[sfc];
Clemens Ladische84d15f2011-09-04 22:12:48 +0200261
262 /* default buffering in the device */
263 s->transfer_delay = TRANSFER_DELAY_TICKS - TICKS_PER_CYCLE;
264 if (s->flags & CIP_BLOCKING)
265 /* additional buffering needed to adjust for no-data packets */
266 s->transfer_delay += TICKS_PER_SECOND * s->syt_interval / rate;
Takashi Sakamoto77d2a8a2014-04-25 22:44:50 +0900267
Takashi Sakamoto547e6312015-09-19 11:21:49 +0900268 return 0;
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100269}
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900270EXPORT_SYMBOL(amdtp_stream_set_parameters);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100271
272/**
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900273 * amdtp_stream_get_max_payload - get the stream's packet size
274 * @s: the AMDTP stream
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100275 *
276 * This function must not be called before the stream has been configured
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900277 * with amdtp_stream_set_parameters().
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100278 */
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900279unsigned int amdtp_stream_get_max_payload(struct amdtp_stream *s)
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100280{
Takashi Sakamotoa2064712015-05-22 23:00:50 +0900281 unsigned int multiplier = 1;
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900282 unsigned int header_size = 0;
Takashi Sakamotoa2064712015-05-22 23:00:50 +0900283
284 if (s->flags & CIP_JUMBO_PAYLOAD)
285 multiplier = 5;
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900286 if (!(s->flags & CIP_NO_HEADER))
287 header_size = 8;
Takashi Sakamotoa2064712015-05-22 23:00:50 +0900288
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900289 return header_size +
290 s->syt_interval * s->data_block_quadlets * 4 * multiplier;
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100291}
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900292EXPORT_SYMBOL(amdtp_stream_get_max_payload);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100293
Clemens Ladisch76fb8782012-05-13 22:03:09 +0200294/**
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900295 * amdtp_stream_pcm_prepare - prepare PCM device for running
296 * @s: the AMDTP stream
Clemens Ladisch76fb8782012-05-13 22:03:09 +0200297 *
298 * This function should be called from the PCM device's .prepare callback.
299 */
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900300void amdtp_stream_pcm_prepare(struct amdtp_stream *s)
Clemens Ladisch76fb8782012-05-13 22:03:09 +0200301{
302 tasklet_kill(&s->period_tasklet);
303 s->pcm_buffer_pointer = 0;
304 s->pcm_period_pointer = 0;
305}
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900306EXPORT_SYMBOL(amdtp_stream_pcm_prepare);
Clemens Ladisch76fb8782012-05-13 22:03:09 +0200307
Takashi Sakamoto875be092015-05-22 23:00:51 +0900308static unsigned int calculate_data_blocks(struct amdtp_stream *s,
309 unsigned int syt)
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100310{
311 unsigned int phase, data_blocks;
312
Takashi Sakamoto875be092015-05-22 23:00:51 +0900313 /* Blocking mode. */
314 if (s->flags & CIP_BLOCKING) {
315 /* This module generate empty packet for 'no data'. */
316 if (syt == CIP_SYT_NO_INFO)
317 data_blocks = 0;
318 else
319 data_blocks = s->syt_interval;
320 /* Non-blocking mode. */
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100321 } else {
Takashi Sakamoto875be092015-05-22 23:00:51 +0900322 if (!cip_sfc_is_base_44100(s->sfc)) {
323 /* Sample_rate / 8000 is an integer, and precomputed. */
324 data_blocks = s->data_block_state;
325 } else {
326 phase = s->data_block_state;
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100327
328 /*
329 * This calculates the number of data blocks per packet so that
330 * 1) the overall rate is correct and exactly synchronized to
331 * the bus clock, and
332 * 2) packets with a rounded-up number of blocks occur as early
333 * as possible in the sequence (to prevent underruns of the
334 * device's buffer).
335 */
Takashi Sakamoto875be092015-05-22 23:00:51 +0900336 if (s->sfc == CIP_SFC_44100)
337 /* 6 6 5 6 5 6 5 ... */
338 data_blocks = 5 + ((phase & 1) ^
339 (phase == 0 || phase >= 40));
340 else
341 /* 12 11 11 11 11 ... or 23 22 22 22 22 ... */
342 data_blocks = 11 * (s->sfc >> 1) + (phase == 0);
343 if (++phase >= (80 >> (s->sfc >> 1)))
344 phase = 0;
345 s->data_block_state = phase;
346 }
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100347 }
348
349 return data_blocks;
350}
351
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900352static unsigned int calculate_syt(struct amdtp_stream *s,
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100353 unsigned int cycle)
354{
355 unsigned int syt_offset, phase, index, syt;
356
357 if (s->last_syt_offset < TICKS_PER_CYCLE) {
358 if (!cip_sfc_is_base_44100(s->sfc))
359 syt_offset = s->last_syt_offset + s->syt_offset_state;
360 else {
361 /*
362 * The time, in ticks, of the n'th SYT_INTERVAL sample is:
363 * n * SYT_INTERVAL * 24576000 / sample_rate
364 * Modulo TICKS_PER_CYCLE, the difference between successive
365 * elements is about 1386.23. Rounding the results of this
366 * formula to the SYT precision results in a sequence of
367 * differences that begins with:
368 * 1386 1386 1387 1386 1386 1386 1387 1386 1386 1386 1387 ...
369 * This code generates _exactly_ the same sequence.
370 */
371 phase = s->syt_offset_state;
372 index = phase % 13;
373 syt_offset = s->last_syt_offset;
374 syt_offset += 1386 + ((index && !(index & 3)) ||
375 phase == 146);
376 if (++phase >= 147)
377 phase = 0;
378 s->syt_offset_state = phase;
379 }
380 } else
381 syt_offset = s->last_syt_offset - TICKS_PER_CYCLE;
382 s->last_syt_offset = syt_offset;
383
Clemens Ladischbe454362011-03-15 07:55:02 +0100384 if (syt_offset < TICKS_PER_CYCLE) {
Clemens Ladische84d15f2011-09-04 22:12:48 +0200385 syt_offset += s->transfer_delay;
Clemens Ladischbe454362011-03-15 07:55:02 +0100386 syt = (cycle + syt_offset / TICKS_PER_CYCLE) << 12;
387 syt += syt_offset % TICKS_PER_CYCLE;
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100388
Takashi Sakamotob445db42014-04-25 22:44:43 +0900389 return syt & CIP_SYT_MASK;
Clemens Ladischbe454362011-03-15 07:55:02 +0100390 } else {
Takashi Sakamotob445db42014-04-25 22:44:43 +0900391 return CIP_SYT_NO_INFO;
Clemens Ladischbe454362011-03-15 07:55:02 +0100392 }
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100393}
394
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900395static void update_pcm_pointers(struct amdtp_stream *s,
396 struct snd_pcm_substream *pcm,
397 unsigned int frames)
Takashi Sakamoto65845f22014-08-29 13:40:45 +0900398{
399 unsigned int ptr;
400
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900401 ptr = s->pcm_buffer_pointer + frames;
402 if (ptr >= pcm->runtime->buffer_size)
403 ptr -= pcm->runtime->buffer_size;
Mark Rutland6aa7de02017-10-23 14:07:29 -0700404 WRITE_ONCE(s->pcm_buffer_pointer, ptr);
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900405
406 s->pcm_period_pointer += frames;
407 if (s->pcm_period_pointer >= pcm->runtime->period_size) {
408 s->pcm_period_pointer -= pcm->runtime->period_size;
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900409 tasklet_hi_schedule(&s->period_tasklet);
410 }
411}
412
413static void pcm_period_tasklet(unsigned long data)
414{
415 struct amdtp_stream *s = (void *)data;
Mark Rutland6aa7de02017-10-23 14:07:29 -0700416 struct snd_pcm_substream *pcm = READ_ONCE(s->pcm);
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900417
418 if (pcm)
419 snd_pcm_period_elapsed(pcm);
420}
421
Takashi Sakamotoff38e0c2016-05-11 07:35:09 +0900422static int queue_packet(struct amdtp_stream *s, unsigned int header_length,
423 unsigned int payload_length)
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900424{
425 struct fw_iso_packet p = {0};
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +0900426 int err = 0;
427
428 if (IS_ERR(s->context))
429 goto end;
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900430
431 p.interrupt = IS_ALIGNED(s->packet_index + 1, INTERRUPT_INTERVAL);
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900432 p.tag = s->tag;
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900433 p.header_length = header_length;
Takashi Sakamotoff38e0c2016-05-11 07:35:09 +0900434 if (payload_length > 0)
435 p.payload_length = payload_length;
436 else
437 p.skip = true;
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900438 err = fw_iso_context_queue(s->context, &p, &s->buffer.iso_buffer,
439 s->buffer.packets[s->packet_index].offset);
440 if (err < 0) {
441 dev_err(&s->unit->device, "queueing error: %d\n", err);
442 goto end;
443 }
444
445 if (++s->packet_index >= QUEUE_LENGTH)
446 s->packet_index = 0;
447end:
448 return err;
449}
450
451static inline int queue_out_packet(struct amdtp_stream *s,
Takashi Sakamotoff38e0c2016-05-11 07:35:09 +0900452 unsigned int payload_length)
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900453{
Takashi Sakamotoff38e0c2016-05-11 07:35:09 +0900454 return queue_packet(s, OUT_PACKET_HEADER_SIZE, payload_length);
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900455}
456
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900457static inline int queue_in_packet(struct amdtp_stream *s)
458{
Takashi Sakamotof91c9d72017-04-11 20:33:18 +0900459 return queue_packet(s, IN_PACKET_HEADER_SIZE, s->max_payload_length);
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900460}
461
Takashi Sakamotoff0fb5a2017-03-31 22:06:06 +0900462static int handle_out_packet(struct amdtp_stream *s,
463 unsigned int payload_length, unsigned int cycle,
Takashi Sakamotoa9c42842016-05-11 07:33:27 +0900464 unsigned int index)
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100465{
466 __be32 *buffer;
Takashi Sakamoto390a1512016-05-09 23:15:55 +0900467 unsigned int syt;
468 unsigned int data_blocks;
Takashi Sakamoto20e44572015-09-19 11:21:52 +0900469 unsigned int pcm_frames;
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100470 struct snd_pcm_substream *pcm;
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100471
Takashi Sakamotoccccad82014-04-25 22:44:48 +0900472 buffer = s->buffer.packets[s->packet_index].buffer;
Takashi Sakamoto390a1512016-05-09 23:15:55 +0900473 syt = calculate_syt(s, cycle);
474 data_blocks = calculate_data_blocks(s, syt);
Takashi Sakamotodf075fe2015-09-19 11:22:02 +0900475 pcm_frames = s->process_data_blocks(s, buffer + 2, data_blocks, &syt);
Takashi Sakamoto20e44572015-09-19 11:21:52 +0900476
Takashi Sakamoto9dae0172017-03-22 21:30:17 +0900477 if (s->flags & CIP_DBC_IS_END_EVENT)
478 s->data_block_counter =
479 (s->data_block_counter + data_blocks) & 0xff;
480
Mark Rutland6aa7de02017-10-23 14:07:29 -0700481 buffer[0] = cpu_to_be32(READ_ONCE(s->source_node_id_field) |
Takashi Sakamoto9a2820c2015-05-22 23:21:12 +0900482 (s->data_block_quadlets << CIP_DBS_SHIFT) |
Takashi Sakamoto98638742017-03-22 21:30:16 +0900483 ((s->sph << CIP_SPH_SHIFT) & CIP_SPH_MASK) |
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100484 s->data_block_counter);
Takashi Sakamoto414ba022015-09-19 11:21:53 +0900485 buffer[1] = cpu_to_be32(CIP_EOH |
486 ((s->fmt << CIP_FMT_SHIFT) & CIP_FMT_MASK) |
487 ((s->fdf << CIP_FDF_SHIFT) & CIP_FDF_MASK) |
488 (syt & CIP_SYT_MASK));
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100489
Takashi Sakamoto9dae0172017-03-22 21:30:17 +0900490 if (!(s->flags & CIP_DBC_IS_END_EVENT))
491 s->data_block_counter =
492 (s->data_block_counter + data_blocks) & 0xff;
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900493 payload_length = 8 + data_blocks * 4 * s->data_block_quadlets;
Takashi Sakamoto0c95c1d2016-05-09 21:12:46 +0900494
Takashi Sakamotoa9c42842016-05-11 07:33:27 +0900495 trace_out_packet(s, cycle, buffer, payload_length, index);
Takashi Sakamoto0c95c1d2016-05-09 21:12:46 +0900496
Takashi Sakamotoff38e0c2016-05-11 07:35:09 +0900497 if (queue_out_packet(s, payload_length) < 0)
Takashi Sakamotoa4103bd2015-05-22 23:00:53 +0900498 return -EIO;
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100499
Mark Rutland6aa7de02017-10-23 14:07:29 -0700500 pcm = READ_ONCE(s->pcm);
Takashi Sakamoto20e44572015-09-19 11:21:52 +0900501 if (pcm && pcm_frames > 0)
502 update_pcm_pointers(s, pcm, pcm_frames);
Takashi Sakamotoa4103bd2015-05-22 23:00:53 +0900503
504 /* No need to return the number of handled data blocks. */
505 return 0;
Clemens Ladisch76fb8782012-05-13 22:03:09 +0200506}
507
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900508static int handle_out_packet_without_header(struct amdtp_stream *s,
509 unsigned int payload_length, unsigned int cycle,
510 unsigned int index)
511{
512 __be32 *buffer;
513 unsigned int syt;
514 unsigned int data_blocks;
515 unsigned int pcm_frames;
516 struct snd_pcm_substream *pcm;
517
518 buffer = s->buffer.packets[s->packet_index].buffer;
519 syt = calculate_syt(s, cycle);
520 data_blocks = calculate_data_blocks(s, syt);
521 pcm_frames = s->process_data_blocks(s, buffer, data_blocks, &syt);
522 s->data_block_counter = (s->data_block_counter + data_blocks) & 0xff;
523
524 payload_length = data_blocks * 4 * s->data_block_quadlets;
Takashi Sakamotob164d2f2017-04-09 21:33:27 +0900525
526 trace_out_packet_without_header(s, cycle, payload_length, data_blocks,
527 index);
528
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900529 if (queue_out_packet(s, payload_length) < 0)
530 return -EIO;
531
Mark Rutland6aa7de02017-10-23 14:07:29 -0700532 pcm = READ_ONCE(s->pcm);
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900533 if (pcm && pcm_frames > 0)
534 update_pcm_pointers(s, pcm, pcm_frames);
535
536 /* No need to return the number of handled data blocks. */
537 return 0;
538}
539
Takashi Sakamoto6fc6b9c2015-05-22 23:00:52 +0900540static int handle_in_packet(struct amdtp_stream *s,
Takashi Sakamotoff0fb5a2017-03-31 22:06:06 +0900541 unsigned int payload_length, unsigned int cycle,
Takashi Sakamotoa9c42842016-05-11 07:33:27 +0900542 unsigned int index)
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900543{
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900544 __be32 *buffer;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900545 u32 cip_header[2];
Takashi Sakamoto98638742017-03-22 21:30:16 +0900546 unsigned int sph, fmt, fdf, syt;
Takashi Sakamoto6fc6b9c2015-05-22 23:00:52 +0900547 unsigned int data_block_quadlets, data_block_counter, dbc_interval;
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900548 unsigned int data_blocks;
Takashi Sakamoto20e44572015-09-19 11:21:52 +0900549 struct snd_pcm_substream *pcm;
550 unsigned int pcm_frames;
Takashi Sakamotoc8bdf492014-04-25 22:45:04 +0900551 bool lost;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900552
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900553 buffer = s->buffer.packets[s->packet_index].buffer;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900554 cip_header[0] = be32_to_cpu(buffer[0]);
555 cip_header[1] = be32_to_cpu(buffer[1]);
556
Takashi Sakamotoff0fb5a2017-03-31 22:06:06 +0900557 trace_in_packet(s, cycle, cip_header, payload_length, index);
Takashi Sakamoto0c95c1d2016-05-09 21:12:46 +0900558
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900559 /*
560 * This module supports 'Two-quadlet CIP header with SYT field'.
Takashi Sakamoto77d2a8a2014-04-25 22:44:50 +0900561 * For convenience, also check FMT field is AM824 or not.
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900562 */
Takashi Sakamoto2128f782017-03-22 21:30:27 +0900563 if ((((cip_header[0] & CIP_EOH_MASK) == CIP_EOH) ||
564 ((cip_header[1] & CIP_EOH_MASK) != CIP_EOH)) &&
565 (!(s->flags & CIP_HEADER_WITHOUT_EOH))) {
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900566 dev_info_ratelimited(&s->unit->device,
567 "Invalid CIP header for AMDTP: %08X:%08X\n",
568 cip_header[0], cip_header[1]);
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900569 data_blocks = 0;
Takashi Sakamoto20e44572015-09-19 11:21:52 +0900570 pcm_frames = 0;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900571 goto end;
572 }
573
Takashi Sakamoto414ba022015-09-19 11:21:53 +0900574 /* Check valid protocol or not. */
Takashi Sakamoto98638742017-03-22 21:30:16 +0900575 sph = (cip_header[0] & CIP_SPH_MASK) >> CIP_SPH_SHIFT;
Takashi Sakamoto414ba022015-09-19 11:21:53 +0900576 fmt = (cip_header[1] & CIP_FMT_MASK) >> CIP_FMT_SHIFT;
Takashi Sakamoto98638742017-03-22 21:30:16 +0900577 if (sph != s->sph || fmt != s->fmt) {
Takashi Sakamoto2a7e1712015-10-11 22:33:50 +0900578 dev_info_ratelimited(&s->unit->device,
579 "Detect unexpected protocol: %08x %08x\n",
580 cip_header[0], cip_header[1]);
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900581 data_blocks = 0;
Takashi Sakamoto2a7e1712015-10-11 22:33:50 +0900582 pcm_frames = 0;
583 goto end;
Takashi Sakamoto414ba022015-09-19 11:21:53 +0900584 }
585
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900586 /* Calculate data blocks */
Takashi Sakamoto414ba022015-09-19 11:21:53 +0900587 fdf = (cip_header[1] & CIP_FDF_MASK) >> CIP_FDF_SHIFT;
Takashi Sakamotoff0fb5a2017-03-31 22:06:06 +0900588 if (payload_length < 12 ||
Takashi Sakamoto414ba022015-09-19 11:21:53 +0900589 (fmt == CIP_FMT_AM && fdf == AMDTP_FDF_NO_DATA)) {
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900590 data_blocks = 0;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900591 } else {
592 data_block_quadlets =
Takashi Sakamoto9a2820c2015-05-22 23:21:12 +0900593 (cip_header[0] & CIP_DBS_MASK) >> CIP_DBS_SHIFT;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900594 /* avoid division by zero */
595 if (data_block_quadlets == 0) {
Takashi Sakamoto12e0f432015-05-22 23:21:13 +0900596 dev_err(&s->unit->device,
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900597 "Detect invalid value in dbs field: %08X\n",
598 cip_header[0]);
Takashi Sakamotoa9007052015-05-22 23:21:14 +0900599 return -EPROTO;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900600 }
Takashi Sakamoto69702232014-04-25 22:45:05 +0900601 if (s->flags & CIP_WRONG_DBS)
602 data_block_quadlets = s->data_block_quadlets;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900603
Takashi Sakamotoff0fb5a2017-03-31 22:06:06 +0900604 data_blocks = (payload_length / 4 - 2) /
605 data_block_quadlets;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900606 }
607
608 /* Check data block counter continuity */
Takashi Sakamoto9a2820c2015-05-22 23:21:12 +0900609 data_block_counter = cip_header[0] & CIP_DBC_MASK;
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900610 if (data_blocks == 0 && (s->flags & CIP_EMPTY_HAS_WRONG_DBC) &&
Takashi Sakamoto9d591242014-04-25 22:45:27 +0900611 s->data_block_counter != UINT_MAX)
612 data_block_counter = s->data_block_counter;
613
Takashi Sakamoto18f5ed32015-08-05 09:21:05 +0900614 if (((s->flags & CIP_SKIP_DBC_ZERO_CHECK) &&
615 data_block_counter == s->tx_first_dbc) ||
616 s->data_block_counter == UINT_MAX) {
Takashi Sakamotob84b1a22014-04-25 22:45:07 +0900617 lost = false;
618 } else if (!(s->flags & CIP_DBC_IS_END_EVENT)) {
Takashi Sakamotoc8bdf492014-04-25 22:45:04 +0900619 lost = data_block_counter != s->data_block_counter;
Takashi Sakamotod9cd0062014-04-25 22:45:06 +0900620 } else {
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900621 if (data_blocks > 0 && s->tx_dbc_interval > 0)
Takashi Sakamotod9cd0062014-04-25 22:45:06 +0900622 dbc_interval = s->tx_dbc_interval;
623 else
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900624 dbc_interval = data_blocks;
Takashi Sakamotod9cd0062014-04-25 22:45:06 +0900625
Takashi Sakamotoc8bdf492014-04-25 22:45:04 +0900626 lost = data_block_counter !=
Takashi Sakamotod9cd0062014-04-25 22:45:06 +0900627 ((s->data_block_counter + dbc_interval) & 0xff);
628 }
Takashi Sakamotoc8bdf492014-04-25 22:45:04 +0900629
630 if (lost) {
Takashi Sakamoto12e0f432015-05-22 23:21:13 +0900631 dev_err(&s->unit->device,
632 "Detect discontinuity of CIP: %02X %02X\n",
633 s->data_block_counter, data_block_counter);
Takashi Sakamoto6fc6b9c2015-05-22 23:00:52 +0900634 return -EIO;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900635 }
636
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900637 syt = be32_to_cpu(buffer[1]) & CIP_SYT_MASK;
638 pcm_frames = s->process_data_blocks(s, buffer + 2, data_blocks, &syt);
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900639
Takashi Sakamotoc8bdf492014-04-25 22:45:04 +0900640 if (s->flags & CIP_DBC_IS_END_EVENT)
641 s->data_block_counter = data_block_counter;
642 else
643 s->data_block_counter =
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900644 (data_block_counter + data_blocks) & 0xff;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900645end:
646 if (queue_in_packet(s) < 0)
Takashi Sakamoto6fc6b9c2015-05-22 23:00:52 +0900647 return -EIO;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900648
Mark Rutland6aa7de02017-10-23 14:07:29 -0700649 pcm = READ_ONCE(s->pcm);
Takashi Sakamoto20e44572015-09-19 11:21:52 +0900650 if (pcm && pcm_frames > 0)
651 update_pcm_pointers(s, pcm, pcm_frames);
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900652
Takashi Sakamoto31ea49b2015-05-28 00:02:59 +0900653 return 0;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900654}
655
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900656static int handle_in_packet_without_header(struct amdtp_stream *s,
657 unsigned int payload_quadlets, unsigned int cycle,
658 unsigned int index)
659{
660 __be32 *buffer;
661 unsigned int data_blocks;
662 struct snd_pcm_substream *pcm;
663 unsigned int pcm_frames;
664
665 buffer = s->buffer.packets[s->packet_index].buffer;
666 data_blocks = payload_quadlets / s->data_block_quadlets;
Takashi Sakamotob164d2f2017-04-09 21:33:27 +0900667
668 trace_in_packet_without_header(s, cycle, payload_quadlets, data_blocks,
669 index);
670
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900671 pcm_frames = s->process_data_blocks(s, buffer, data_blocks, NULL);
672 s->data_block_counter = (s->data_block_counter + data_blocks) & 0xff;
673
674 if (queue_in_packet(s) < 0)
675 return -EIO;
676
Mark Rutland6aa7de02017-10-23 14:07:29 -0700677 pcm = READ_ONCE(s->pcm);
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900678 if (pcm && pcm_frames > 0)
679 update_pcm_pointers(s, pcm, pcm_frames);
680
681 return 0;
682}
683
Takashi Sakamoto73fc7f02016-05-09 21:12:44 +0900684/*
685 * In CYCLE_TIMER register of IEEE 1394, 7 bits are used to represent second. On
686 * the other hand, in DMA descriptors of 1394 OHCI, 3 bits are used to represent
687 * it. Thus, via Linux firewire subsystem, we can get the 3 bits for second.
688 */
689static inline u32 compute_cycle_count(u32 tstamp)
690{
691 return (((tstamp >> 13) & 0x07) * 8000) + (tstamp & 0x1fff);
692}
693
694static inline u32 increment_cycle_count(u32 cycle, unsigned int addend)
695{
696 cycle += addend;
697 if (cycle >= 8 * CYCLES_PER_SECOND)
698 cycle -= 8 * CYCLES_PER_SECOND;
699 return cycle;
700}
701
Takashi Sakamotof90e2de2016-05-09 21:12:45 +0900702static inline u32 decrement_cycle_count(u32 cycle, unsigned int subtrahend)
703{
704 if (cycle < subtrahend)
705 cycle += 8 * CYCLES_PER_SECOND;
706 return cycle - subtrahend;
707}
708
Takashi Sakamoto73fc7f02016-05-09 21:12:44 +0900709static void out_stream_callback(struct fw_iso_context *context, u32 tstamp,
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900710 size_t header_length, void *header,
711 void *private_data)
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100712{
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900713 struct amdtp_stream *s = private_data;
Takashi Sakamoto390a1512016-05-09 23:15:55 +0900714 unsigned int i, packets = header_length / 4;
Takashi Sakamoto73fc7f02016-05-09 21:12:44 +0900715 u32 cycle;
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100716
Takashi Sakamotoa4103bd2015-05-22 23:00:53 +0900717 if (s->packet_index < 0)
718 return;
719
Takashi Sakamoto73fc7f02016-05-09 21:12:44 +0900720 cycle = compute_cycle_count(tstamp);
721
722 /* Align to actual cycle count for the last packet. */
723 cycle = increment_cycle_count(cycle, QUEUE_LENGTH - packets);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100724
Takashi Sakamotoccccad82014-04-25 22:44:48 +0900725 for (i = 0; i < packets; ++i) {
Takashi Sakamoto73fc7f02016-05-09 21:12:44 +0900726 cycle = increment_cycle_count(cycle, 1);
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900727 if (s->handle_packet(s, 0, cycle, i) < 0) {
Takashi Sakamotoa4103bd2015-05-22 23:00:53 +0900728 s->packet_index = -1;
Takashi Sakamoto4a9bfaf2017-06-11 16:08:21 +0900729 if (in_interrupt())
730 amdtp_stream_pcm_abort(s);
731 WRITE_ONCE(s->pcm_buffer_pointer, SNDRV_PCM_POS_XRUN);
Takashi Sakamotoa4103bd2015-05-22 23:00:53 +0900732 return;
733 }
Takashi Sakamotoccccad82014-04-25 22:44:48 +0900734 }
Takashi Sakamotoa4103bd2015-05-22 23:00:53 +0900735
Clemens Ladisch13882a82011-05-02 09:33:56 +0200736 fw_iso_context_queue_flush(s->context);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100737}
738
Takashi Sakamoto73fc7f02016-05-09 21:12:44 +0900739static void in_stream_callback(struct fw_iso_context *context, u32 tstamp,
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900740 size_t header_length, void *header,
741 void *private_data)
742{
743 struct amdtp_stream *s = private_data;
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900744 unsigned int i, packets;
Takashi Sakamotoff0fb5a2017-03-31 22:06:06 +0900745 unsigned int payload_length, max_payload_length;
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900746 __be32 *headers = header;
Takashi Sakamotof90e2de2016-05-09 21:12:45 +0900747 u32 cycle;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900748
Takashi Sakamotoa4103bd2015-05-22 23:00:53 +0900749 if (s->packet_index < 0)
750 return;
751
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900752 /* The number of packets in buffer */
753 packets = header_length / IN_PACKET_HEADER_SIZE;
754
Takashi Sakamotof90e2de2016-05-09 21:12:45 +0900755 cycle = compute_cycle_count(tstamp);
756
757 /* Align to actual cycle count for the last packet. */
758 cycle = decrement_cycle_count(cycle, packets);
759
Takashi Sakamotoa2064712015-05-22 23:00:50 +0900760 /* For buffer-over-run prevention. */
Takashi Sakamotof91c9d72017-04-11 20:33:18 +0900761 max_payload_length = s->max_payload_length;
Takashi Sakamotoa2064712015-05-22 23:00:50 +0900762
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900763 for (i = 0; i < packets; i++) {
Takashi Sakamotof90e2de2016-05-09 21:12:45 +0900764 cycle = increment_cycle_count(cycle, 1);
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900765
Takashi Sakamotof91c9d72017-04-11 20:33:18 +0900766 /* The number of bytes in this packet */
Takashi Sakamotoff0fb5a2017-03-31 22:06:06 +0900767 payload_length =
768 (be32_to_cpu(headers[i]) >> ISO_DATA_LENGTH_SHIFT);
769 if (payload_length > max_payload_length) {
Takashi Sakamotoa2064712015-05-22 23:00:50 +0900770 dev_err(&s->unit->device,
Takashi Sakamotoff0fb5a2017-03-31 22:06:06 +0900771 "Detect jumbo payload: %04x %04x\n",
772 payload_length, max_payload_length);
Takashi Sakamotoa2064712015-05-22 23:00:50 +0900773 break;
774 }
775
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900776 if (s->handle_packet(s, payload_length, cycle, i) < 0)
Takashi Sakamoto6fc6b9c2015-05-22 23:00:52 +0900777 break;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900778 }
779
Takashi Sakamotodec63cc2016-05-09 23:15:53 +0900780 /* Queueing error or detecting invalid payload. */
Takashi Sakamotod9a16fc2016-05-09 23:15:54 +0900781 if (i < packets) {
Takashi Sakamotodec63cc2016-05-09 23:15:53 +0900782 s->packet_index = -1;
Takashi Sakamoto4a9bfaf2017-06-11 16:08:21 +0900783 if (in_interrupt())
784 amdtp_stream_pcm_abort(s);
785 WRITE_ONCE(s->pcm_buffer_pointer, SNDRV_PCM_POS_XRUN);
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +0900786 return;
787 }
788
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900789 fw_iso_context_queue_flush(s->context);
790}
791
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +0900792/* this is executed one time */
793static void amdtp_stream_first_callback(struct fw_iso_context *context,
Takashi Sakamoto73fc7f02016-05-09 21:12:44 +0900794 u32 tstamp, size_t header_length,
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +0900795 void *header, void *private_data)
796{
797 struct amdtp_stream *s = private_data;
Takashi Sakamotoa04513f2017-03-22 21:30:15 +0900798 u32 cycle;
799 unsigned int packets;
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +0900800
801 /*
802 * For in-stream, first packet has come.
803 * For out-stream, prepared to transmit first packet
804 */
805 s->callbacked = true;
806 wake_up(&s->callback_wait);
807
Takashi Sakamotoa04513f2017-03-22 21:30:15 +0900808 cycle = compute_cycle_count(tstamp);
809
810 if (s->direction == AMDTP_IN_STREAM) {
811 packets = header_length / IN_PACKET_HEADER_SIZE;
812 cycle = decrement_cycle_count(cycle, packets);
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +0900813 context->callback.sc = in_stream_callback;
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900814 if (s->flags & CIP_NO_HEADER)
815 s->handle_packet = handle_in_packet_without_header;
816 else
817 s->handle_packet = handle_in_packet;
Takashi Sakamotoa04513f2017-03-22 21:30:15 +0900818 } else {
819 packets = header_length / 4;
820 cycle = increment_cycle_count(cycle, QUEUE_LENGTH - packets);
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +0900821 context->callback.sc = out_stream_callback;
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900822 if (s->flags & CIP_NO_HEADER)
823 s->handle_packet = handle_out_packet_without_header;
824 else
825 s->handle_packet = handle_out_packet;
Takashi Sakamotoa04513f2017-03-22 21:30:15 +0900826 }
827
828 s->start_cycle = cycle;
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +0900829
Takashi Sakamoto73fc7f02016-05-09 21:12:44 +0900830 context->callback.sc(context, tstamp, header_length, header, s);
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +0900831}
832
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100833/**
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900834 * amdtp_stream_start - start transferring packets
835 * @s: the AMDTP stream to start
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100836 * @channel: the isochronous channel on the bus
837 * @speed: firewire speed code
838 *
839 * The stream cannot be started until it has been configured with
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900840 * amdtp_stream_set_parameters() and it must be started before any PCM or MIDI
841 * device can be started.
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100842 */
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900843int amdtp_stream_start(struct amdtp_stream *s, int channel, int speed)
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100844{
845 static const struct {
846 unsigned int data_block;
847 unsigned int syt_offset;
848 } initial_state[] = {
849 [CIP_SFC_32000] = { 4, 3072 },
850 [CIP_SFC_48000] = { 6, 1024 },
851 [CIP_SFC_96000] = { 12, 1024 },
852 [CIP_SFC_192000] = { 24, 1024 },
853 [CIP_SFC_44100] = { 0, 67 },
854 [CIP_SFC_88200] = { 0, 67 },
855 [CIP_SFC_176400] = { 0, 67 },
856 };
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900857 unsigned int header_size;
858 enum dma_data_direction dir;
Takashi Sakamoto7ab56642014-04-25 22:45:03 +0900859 int type, tag, err;
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100860
861 mutex_lock(&s->mutex);
862
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900863 if (WARN_ON(amdtp_stream_running(s) ||
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900864 (s->data_block_quadlets < 1))) {
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100865 err = -EBADFD;
866 goto err_unlock;
867 }
868
Takashi Sakamoto62f00e42016-05-09 23:15:56 +0900869 if (s->direction == AMDTP_IN_STREAM)
Takashi Sakamotob6bc8122014-04-25 22:45:16 +0900870 s->data_block_counter = UINT_MAX;
871 else
872 s->data_block_counter = 0;
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100873 s->data_block_state = initial_state[s->sfc].data_block;
874 s->syt_offset_state = initial_state[s->sfc].syt_offset;
875 s->last_syt_offset = TICKS_PER_CYCLE;
876
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900877 /* initialize packet buffer */
878 if (s->direction == AMDTP_IN_STREAM) {
879 dir = DMA_FROM_DEVICE;
880 type = FW_ISO_CONTEXT_RECEIVE;
881 header_size = IN_PACKET_HEADER_SIZE;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900882 } else {
883 dir = DMA_TO_DEVICE;
884 type = FW_ISO_CONTEXT_TRANSMIT;
885 header_size = OUT_PACKET_HEADER_SIZE;
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900886 }
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100887 err = iso_packets_buffer_init(&s->buffer, s->unit, QUEUE_LENGTH,
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900888 amdtp_stream_get_max_payload(s), dir);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100889 if (err < 0)
890 goto err_unlock;
891
892 s->context = fw_iso_context_create(fw_parent_device(s->unit)->card,
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900893 type, channel, speed, header_size,
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +0900894 amdtp_stream_first_callback, s);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100895 if (IS_ERR(s->context)) {
896 err = PTR_ERR(s->context);
897 if (err == -EBUSY)
898 dev_err(&s->unit->device,
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900899 "no free stream on this controller\n");
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100900 goto err_buffer;
901 }
902
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900903 amdtp_stream_update(s);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100904
Takashi Sakamoto52759c092018-04-29 15:01:46 +0900905 if (s->direction == AMDTP_IN_STREAM)
906 s->max_payload_length = amdtp_stream_get_max_payload(s);
907
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900908 if (s->flags & CIP_NO_HEADER)
909 s->tag = TAG_NO_CIP_HEADER;
910 else
911 s->tag = TAG_CIP;
912
Clemens Ladischec00f5e2011-03-15 07:57:24 +0100913 s->packet_index = 0;
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900914 do {
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900915 if (s->direction == AMDTP_IN_STREAM)
916 err = queue_in_packet(s);
917 else
Takashi Sakamotoff38e0c2016-05-11 07:35:09 +0900918 err = queue_out_packet(s, 0);
Takashi Sakamoto4b7da112014-04-25 22:44:45 +0900919 if (err < 0)
920 goto err_context;
921 } while (s->packet_index > 0);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100922
Takashi Sakamoto2b3fc452014-04-25 22:44:46 +0900923 /* NOTE: TAG1 matches CIP. This just affects in stream. */
Takashi Sakamoto7ab56642014-04-25 22:45:03 +0900924 tag = FW_ISO_CONTEXT_MATCH_TAG1;
Takashi Sakamoto3b196c392017-03-31 22:06:07 +0900925 if ((s->flags & CIP_EMPTY_WITH_TAG0) || (s->flags & CIP_NO_HEADER))
Takashi Sakamoto7ab56642014-04-25 22:45:03 +0900926 tag |= FW_ISO_CONTEXT_MATCH_TAG0;
927
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +0900928 s->callbacked = false;
Takashi Sakamoto7ab56642014-04-25 22:45:03 +0900929 err = fw_iso_context_start(s->context, -1, 0, tag);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100930 if (err < 0)
931 goto err_context;
932
933 mutex_unlock(&s->mutex);
934
935 return 0;
936
937err_context:
938 fw_iso_context_destroy(s->context);
939 s->context = ERR_PTR(-1);
940err_buffer:
941 iso_packets_buffer_destroy(&s->buffer, s->unit);
942err_unlock:
943 mutex_unlock(&s->mutex);
944
945 return err;
946}
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900947EXPORT_SYMBOL(amdtp_stream_start);
Clemens Ladisch31ef9132011-03-15 07:53:21 +0100948
949/**
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900950 * amdtp_stream_pcm_pointer - get the PCM buffer position
951 * @s: the AMDTP stream that transports the PCM data
Clemens Ladische9148dd2012-05-13 18:49:14 +0200952 *
953 * Returns the current buffer position, in frames.
954 */
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900955unsigned long amdtp_stream_pcm_pointer(struct amdtp_stream *s)
Clemens Ladische9148dd2012-05-13 18:49:14 +0200956{
Takashi Sakamoto1dba9db2016-05-12 02:17:39 +0900957 /*
958 * This function is called in software IRQ context of period_tasklet or
959 * process context.
960 *
961 * When the software IRQ context was scheduled by software IRQ context
962 * of IR/IT contexts, queued packets were already handled. Therefore,
963 * no need to flush the queue in buffer anymore.
964 *
965 * When the process context reach here, some packets will be already
966 * queued in the buffer. These packets should be handled immediately
967 * to keep better granularity of PCM pointer.
968 *
969 * Later, the process context will sometimes schedules software IRQ
970 * context of the period_tasklet. Then, no need to flush the queue by
971 * the same reason as described for IR/IT contexts.
972 */
973 if (!in_interrupt() && amdtp_stream_running(s))
Clemens Ladisch92b862c2012-05-13 19:07:22 +0200974 fw_iso_context_flush_completions(s->context);
Clemens Ladische9148dd2012-05-13 18:49:14 +0200975
Mark Rutland6aa7de02017-10-23 14:07:29 -0700976 return READ_ONCE(s->pcm_buffer_pointer);
Clemens Ladische9148dd2012-05-13 18:49:14 +0200977}
Takashi Sakamotobe4a2892014-04-25 22:44:42 +0900978EXPORT_SYMBOL(amdtp_stream_pcm_pointer);
Clemens Ladische9148dd2012-05-13 18:49:14 +0200979
980/**
Takashi Sakamoto875becf2017-06-07 09:38:05 +0900981 * amdtp_stream_pcm_ack - acknowledge queued PCM frames
982 * @s: the AMDTP stream that transfers the PCM frames
983 *
984 * Returns zero always.
985 */
986int amdtp_stream_pcm_ack(struct amdtp_stream *s)
987{
988 /*
989 * Process isochronous packets for recent isochronous cycle to handle
990 * queued PCM frames.
991 */
992 if (amdtp_stream_running(s))
993 fw_iso_context_flush_completions(s->context);
994
995 return 0;
996}
997EXPORT_SYMBOL(amdtp_stream_pcm_ack);
998
999/**
Takashi Sakamotobe4a2892014-04-25 22:44:42 +09001000 * amdtp_stream_update - update the stream after a bus reset
1001 * @s: the AMDTP stream
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001002 */
Takashi Sakamotobe4a2892014-04-25 22:44:42 +09001003void amdtp_stream_update(struct amdtp_stream *s)
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001004{
Takashi Sakamoto9a2820c2015-05-22 23:21:12 +09001005 /* Precomputing. */
Mark Rutland6aa7de02017-10-23 14:07:29 -07001006 WRITE_ONCE(s->source_node_id_field,
1007 (fw_parent_device(s->unit)->card->node_id << CIP_SID_SHIFT) & CIP_SID_MASK);
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001008}
Takashi Sakamotobe4a2892014-04-25 22:44:42 +09001009EXPORT_SYMBOL(amdtp_stream_update);
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001010
1011/**
Takashi Sakamotobe4a2892014-04-25 22:44:42 +09001012 * amdtp_stream_stop - stop sending packets
1013 * @s: the AMDTP stream to stop
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001014 *
1015 * All PCM and MIDI devices of the stream must be stopped before the stream
1016 * itself can be stopped.
1017 */
Takashi Sakamotobe4a2892014-04-25 22:44:42 +09001018void amdtp_stream_stop(struct amdtp_stream *s)
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001019{
1020 mutex_lock(&s->mutex);
1021
Takashi Sakamotobe4a2892014-04-25 22:44:42 +09001022 if (!amdtp_stream_running(s)) {
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001023 mutex_unlock(&s->mutex);
1024 return;
1025 }
1026
Clemens Ladisch76fb8782012-05-13 22:03:09 +02001027 tasklet_kill(&s->period_tasklet);
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001028 fw_iso_context_stop(s->context);
1029 fw_iso_context_destroy(s->context);
1030 s->context = ERR_PTR(-1);
1031 iso_packets_buffer_destroy(&s->buffer, s->unit);
1032
Takashi Sakamoto7b3b0d82014-04-25 22:44:49 +09001033 s->callbacked = false;
1034
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001035 mutex_unlock(&s->mutex);
1036}
Takashi Sakamotobe4a2892014-04-25 22:44:42 +09001037EXPORT_SYMBOL(amdtp_stream_stop);
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001038
1039/**
Takashi Sakamotobe4a2892014-04-25 22:44:42 +09001040 * amdtp_stream_pcm_abort - abort the running PCM device
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001041 * @s: the AMDTP stream about to be stopped
1042 *
1043 * If the isochronous stream needs to be stopped asynchronously, call this
1044 * function first to stop the PCM device.
1045 */
Takashi Sakamotobe4a2892014-04-25 22:44:42 +09001046void amdtp_stream_pcm_abort(struct amdtp_stream *s)
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001047{
1048 struct snd_pcm_substream *pcm;
1049
Mark Rutland6aa7de02017-10-23 14:07:29 -07001050 pcm = READ_ONCE(s->pcm);
Takashi Iwai1fb85102014-11-07 17:08:28 +01001051 if (pcm)
1052 snd_pcm_stop_xrun(pcm);
Clemens Ladisch31ef9132011-03-15 07:53:21 +01001053}
Takashi Sakamotobe4a2892014-04-25 22:44:42 +09001054EXPORT_SYMBOL(amdtp_stream_pcm_abort);