ALSA: oxfw: Add support for AV/C stream format command to get/set supported stream...
[sfrench/cifs-2.6.git] / sound / firewire / oxfw / oxfw-stream.c
1 /*
2  * oxfw_stream.c - a part of driver for OXFW970/971 based devices
3  *
4  * Copyright (c) 2014 Takashi Sakamoto
5  *
6  * Licensed under the terms of the GNU General Public License, version 2.
7  */
8
9 #include "oxfw.h"
10
11 int snd_oxfw_stream_init_simplex(struct snd_oxfw *oxfw)
12 {
13         int err;
14
15         err = cmp_connection_init(&oxfw->in_conn, oxfw->unit,
16                                   CMP_INPUT, 0);
17         if (err < 0)
18                 goto end;
19
20         err = amdtp_stream_init(&oxfw->rx_stream, oxfw->unit,
21                                 AMDTP_OUT_STREAM, CIP_NONBLOCKING);
22         if (err < 0) {
23                 amdtp_stream_destroy(&oxfw->rx_stream);
24                 cmp_connection_destroy(&oxfw->in_conn);
25         }
26 end:
27         return err;
28 }
29
30 static void stop_stream(struct snd_oxfw *oxfw)
31 {
32         amdtp_stream_pcm_abort(&oxfw->rx_stream);
33         amdtp_stream_stop(&oxfw->rx_stream);
34         cmp_connection_break(&oxfw->in_conn);
35 }
36
37 int snd_oxfw_stream_start_simplex(struct snd_oxfw *oxfw)
38 {
39         int err = 0;
40
41         if (amdtp_streaming_error(&oxfw->rx_stream))
42                 stop_stream(oxfw);
43
44         if (amdtp_stream_running(&oxfw->rx_stream))
45                 goto end;
46
47         err = cmp_connection_establish(&oxfw->in_conn,
48                         amdtp_stream_get_max_payload(&oxfw->rx_stream));
49         if (err < 0)
50                 goto end;
51
52         err = amdtp_stream_start(&oxfw->rx_stream,
53                                  oxfw->in_conn.resources.channel,
54                                  oxfw->in_conn.speed);
55         if (err < 0)
56                 stop_stream(oxfw);
57 end:
58         return err;
59 }
60
61 void snd_oxfw_stream_stop_simplex(struct snd_oxfw *oxfw)
62 {
63         stop_stream(oxfw);
64 }
65
66 void snd_oxfw_stream_destroy_simplex(struct snd_oxfw *oxfw)
67 {
68         stop_stream(oxfw);
69
70         amdtp_stream_destroy(&oxfw->rx_stream);
71         cmp_connection_destroy(&oxfw->in_conn);
72 }
73
74 void snd_oxfw_stream_update_simplex(struct snd_oxfw *oxfw)
75 {
76         if (cmp_connection_update(&oxfw->in_conn) < 0)
77                 stop_stream(oxfw);
78         else
79                 amdtp_stream_update(&oxfw->rx_stream);
80 }