2 * Copyright (C) 2003-2010 The Music Player Daemon Project
3 * http://www.musicpd.org
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License along
16 * with this program; if not, write to the Free Software Foundation, Inc.,
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
30 /** the first chunk */
31 struct music_chunk
*head
;
33 /** a pointer to the tail of the chunk */
34 struct music_chunk
**tail_r
;
36 /** the current number of chunks */
39 /** a mutex which protects #head and #tail_r */
43 struct audio_format audio_format
;
50 struct music_pipe
*mp
= g_new(struct music_pipe
, 1);
53 mp
->tail_r
= &mp
->head
;
55 mp
->mutex
= g_mutex_new();
58 audio_format_clear(&mp
->audio_format
);
65 music_pipe_free(struct music_pipe
*mp
)
67 assert(mp
->head
== NULL
);
68 assert(mp
->tail_r
== &mp
->head
);
70 g_mutex_free(mp
->mutex
);
77 music_pipe_check_format(const struct music_pipe
*pipe
,
78 const struct audio_format
*audio_format
)
81 assert(audio_format
!= NULL
);
83 return !audio_format_defined(&pipe
->audio_format
) ||
84 audio_format_equals(&pipe
->audio_format
, audio_format
);
88 music_pipe_contains(const struct music_pipe
*mp
,
89 const struct music_chunk
*chunk
)
91 g_mutex_lock(mp
->mutex
);
93 for (const struct music_chunk
*i
= mp
->head
;
94 i
!= NULL
; i
= i
->next
) {
96 g_mutex_unlock(mp
->mutex
);
101 g_mutex_unlock(mp
->mutex
);
108 const struct music_chunk
*
109 music_pipe_peek(const struct music_pipe
*mp
)
115 music_pipe_shift(struct music_pipe
*mp
)
117 struct music_chunk
*chunk
;
119 g_mutex_lock(mp
->mutex
);
123 assert(!music_chunk_is_empty(chunk
));
125 mp
->head
= chunk
->next
;
128 if (mp
->head
== NULL
) {
129 assert(mp
->size
== 0);
130 assert(mp
->tail_r
== &chunk
->next
);
132 mp
->tail_r
= &mp
->head
;
134 assert(mp
->size
> 0);
135 assert(mp
->tail_r
!= &chunk
->next
);
139 /* poison the "next" reference */
140 chunk
->next
= (void*)0x01010101;
143 audio_format_clear(&mp
->audio_format
);
147 g_mutex_unlock(mp
->mutex
);
153 music_pipe_clear(struct music_pipe
*mp
, struct music_buffer
*buffer
)
155 struct music_chunk
*chunk
;
157 while ((chunk
= music_pipe_shift(mp
)) != NULL
)
158 music_buffer_return(buffer
, chunk
);
162 music_pipe_push(struct music_pipe
*mp
, struct music_chunk
*chunk
)
164 assert(!music_chunk_is_empty(chunk
));
165 assert(chunk
->length
== 0 || audio_format_valid(&chunk
->audio_format
));
167 g_mutex_lock(mp
->mutex
);
169 assert(mp
->size
> 0 || !audio_format_defined(&mp
->audio_format
));
170 assert(!audio_format_defined(&mp
->audio_format
) ||
171 music_chunk_check_format(chunk
, &mp
->audio_format
));
174 if (!audio_format_defined(&mp
->audio_format
) && chunk
->length
> 0)
175 mp
->audio_format
= chunk
->audio_format
;
180 mp
->tail_r
= &chunk
->next
;
184 g_mutex_unlock(mp
->mutex
);
188 music_pipe_size(const struct music_pipe
*mp
)