source: roaraudio/roard/meta.c @ 5381:430b1d26e12d

Last change on this file since 5381:430b1d26e12d was 5381:430b1d26e12d, checked in by phi, 12 years ago

updated copyright years

File size: 6.2 KB
Line 
1//meta.c:
2
3/*
4 *      Copyright (C) Philipp 'ph3-der-loewe' Schafft - 2008-2012
5 *
6 *  This file is part of roard a part of RoarAudio,
7 *  a cross-platform sound system for both, home and professional use.
8 *  See README for details.
9 *
10 *  This file is free software; you can redistribute it and/or modify
11 *  it under the terms of the GNU General Public License version 3
12 *  as published by the Free Software Foundation.
13 *
14 *  RoarAudio is distributed in the hope that it will be useful,
15 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17 *  GNU General Public License for more details.
18 *
19 *  You should have received a copy of the GNU General Public License
20 *  along with this software; see the file COPYING.  If not, write to
21 *  the Free Software Foundation, 51 Franklin Street, Fifth Floor,
22 *  Boston, MA 02110-1301, USA.
23 *
24 */
25
26#include "roard.h"
27
28#ifdef ROAR_SUPPORT_META
29
30int stream_meta_set   (int id, int type, const char * name, const char * val) {
31 int i;
32 struct roar_stream_server * s = g_streams[id];
33
34 roar_notify_core_emit_simple(ROAR_OE_STREAM_META_UPDATE, -1, id, ROAR_OT_STREAM, ROAR_META_MODE_SET, -1, NULL, 0);
35
36 if ( s == NULL )
37  return -1;
38
39 for (i = 0; i < ROAR_META_MAX_PER_STREAM; i++)
40  if ( s->meta[i].type == type ) {
41   s->meta[i].type = ROAR_META_TYPE_NONE;
42   if ( s->meta[i].value != NULL )
43    roar_mm_free(s->meta[i].value);
44   s->meta[i].value = NULL;
45  }
46
47 return stream_meta_add(id, type, name, val);
48}
49
50int stream_meta_add   (int id, int type, const char * name, const char * val) {
51 int i;
52 char * c;
53 struct roar_stream_server * s = g_streams[id];
54
55 roar_notify_core_emit_simple(ROAR_OE_STREAM_META_UPDATE, -1, id, ROAR_OT_STREAM, ROAR_META_MODE_ADD, -1, NULL, 0);
56
57 if ( s == NULL )
58  return -1;
59
60 for (i = 0; i < ROAR_META_MAX_PER_STREAM; i++) {
61  if ( s->meta[i].type == ROAR_META_TYPE_NONE ) {
62   s->meta[i].type = type;
63
64   if ( name == NULL ) {
65    s->meta[i].key[0] = 0;
66   } else {
67    strncpy(s->meta[i].key, name, ROAR_META_MAX_NAMELEN);
68   }
69
70   if ( (c = strdup(val)) == NULL ) {
71    s->meta[i].type = ROAR_META_TYPE_NONE;
72    s->meta[i].key[0] = 0;
73    return -1;
74   }
75
76   s->meta[i].value = c;
77
78   ROAR_DBG("stream_meta_add(id=%i, type=%i, name='%s', val='%s') = 0", id, type, name, val);
79
80   return 0;
81  }
82 }
83
84 return -1;
85}
86
87int stream_meta_get   (int id, int type, const char * name, char * val, size_t len) {
88 int i, vallen;
89 struct roar_stream_server * s = g_streams[id];
90
91 if ( s == NULL )
92  return -1;
93
94 for (i = 0; i < ROAR_META_MAX_PER_STREAM; i++) {
95  if ( s->meta[i].type == type ) {
96   if ( name != NULL )
97    if ( strncmp(s->meta[i].key, name, ROAR_META_MAX_NAMELEN) != 0 )
98     continue;
99
100   if ( s->meta[i].value == NULL )
101    return -1;
102
103   if ( (vallen = strlen(s->meta[i].value)) > (len - 1) ) {
104    ROAR_DBG("stream_meta_get(*): val too small: need %i have %i", vallen, len);
105    return -1;
106   }
107
108   strncpy(val, s->meta[i].value, vallen);
109   val[vallen] = 0;
110
111   return 0;
112  }
113 }
114
115 return -1;
116}
117
118int stream_meta_list  (int id, int * types, size_t len) {
119 int i, j;
120 int have = 0;
121 int found;
122 struct roar_stream_server * s = g_streams[id];
123
124 if ( s == NULL )
125  return -1;
126
127 if ( len < ROAR_META_MAX_PER_STREAM ) // TODO: find a way we do not need this
128  return -1;
129
130 types[0] = -1;
131
132 for (i = 0; i < ROAR_META_MAX_PER_STREAM; i++) {
133  found = 0;
134  for (j = 0; j < have; j++)
135   if ( types[j] == s->meta[i].type ) {
136    found = 1;
137    break;
138   }
139
140  if ( !found )
141   types[have++] = s->meta[i].type;
142 }
143
144 return have;
145}
146
147int stream_meta_clear (int id) {
148 int i;
149 struct roar_stream_server * s = NULL;
150
151 if ( id < 0 || id > ROAR_STREAMS_MAX ) {
152  ROAR_ERR("stream_meta_clear(id=%i): Can not clear meta data on stream: invalid stream ID", id);
153  return -1;
154 }
155
156 roar_notify_core_emit_simple(ROAR_OE_STREAM_META_UPDATE, -1, id, ROAR_OT_STREAM, ROAR_META_MODE_CLEAR, -1, NULL, 0);
157
158 s = g_streams[id];
159
160 if ( s == NULL )
161  return -1;
162
163 for (i = 0; i < ROAR_META_MAX_PER_STREAM; i++) {
164  s->meta[i].type   = ROAR_META_TYPE_NONE;
165  if ( s->meta[i].value )
166   roar_mm_free(s->meta[i].value);
167  s->meta[i].value  = NULL;
168  s->meta[i].key[0] = 0;
169 }
170
171 return 0;
172}
173
174int stream_meta_finalize(int id) {
175 register int dir;
176 register int co, ci, i;
177 struct roar_stream_server * s;
178
179 roar_notify_core_emit_simple(ROAR_OE_STREAM_META_UPDATE, -1, id, ROAR_OT_STREAM, ROAR_META_MODE_FINALIZE, -1, NULL, 0);
180
181 if ( streams_get_flag(id, ROAR_FLAG_META) != 1 ) // ignore non meta streams
182  return 0;
183
184 dir = ROAR_STREAM(g_streams[id])->dir;
185
186 if ( dir != ROAR_DIR_PLAY   && dir != ROAR_DIR_META  &&  // ignore on non input streams
187      dir != ROAR_DIR_FILTER && dir != ROAR_DIR_BIDIR &&
188      dir != ROAR_DIR_RECPLAY )
189  return 0;
190
191 ROAR_DBG("stream_meta_finalize(id=%i) = ?", id);
192
193 for (co = 0; co < ROAR_STREAMS_MAX; co++) {
194  if ( g_streams[co] == NULL )
195   continue;
196
197  dir = ROAR_STREAM(g_streams[co])->dir;
198
199  if ( dir != ROAR_DIR_MONITOR && dir != ROAR_DIR_FILTER &&
200       dir != ROAR_DIR_META    && dir != ROAR_DIR_BIDIR  &&
201       dir != ROAR_DIR_OUTPUT                             )
202   continue;
203
204  if ( streams_get_flag(co, ROAR_FLAG_META) != 1 )
205   continue;
206
207  ROAR_DBG("stream_meta_finalize(id=%i): found output stream: id=%i", id, co);
208  stream_meta_clear(co);
209
210  for (ci = 0; ci < ROAR_STREAMS_MAX; ci++) {
211   if ( g_streams[ci] == NULL )
212    continue;
213
214   dir = ROAR_STREAM(g_streams[ci])->dir;
215
216   if ( dir != ROAR_DIR_PLAY   && dir != ROAR_DIR_META &&
217        dir != ROAR_DIR_FILTER && dir != ROAR_DIR_BIDIR )
218    continue;
219
220   if ( streams_get_flag(ci, ROAR_FLAG_META) != 1 )
221    continue;
222
223   ROAR_DBG("stream_meta_finalize(id=%i): found input stream: id=%i", id, ci);
224
225   // ok, next we copy the date of ci to co:
226   s = g_streams[ci];
227
228   for (i = 0; i < ROAR_META_MAX_PER_STREAM; i++) {
229    if ( s->meta[i].type == ROAR_META_TYPE_NONE )
230     continue;
231
232    ROAR_DBG("stream_meta_finalize(id=%i): found meta data, copy: %i->%i", id, ci, co);
233    stream_meta_add(co, s->meta[i].type, s->meta[i].key, s->meta[i].value); // ignore errors
234   }
235  }
236
237  // ask the codec filter to update meta data:
238  ROAR_DBG("stream_meta_finalize(id=%i): Asking stream %i to update meta data", id, co);
239  streams_ctl(co, ROAR_CODECFILTER_CTL_META_UPDATE, NULL); // ignore errors...
240 }
241
242 return 0;
243}
244
245#endif
246
247//ll
Note: See TracBrowser for help on using the repository browser.