From f3f3f15d90ae9c0a8fec183efdfd0dcb8bd054eb Mon Sep 17 00:00:00 2001 From: Winfried Ritsch Date: Tue, 3 May 2005 07:18:08 +0000 Subject: This commit was generated by cvs2svn to compensate for changes in r2884, which included commits to RCS files with non-trunk default branches. svn path=/trunk/externals/iem/iemstream/; revision=2885 --- streamogg.cpp | 113 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 113 insertions(+) create mode 100644 streamogg.cpp (limited to 'streamogg.cpp') diff --git a/streamogg.cpp b/streamogg.cpp new file mode 100644 index 0000000..947753b --- /dev/null +++ b/streamogg.cpp @@ -0,0 +1,113 @@ +/************************************************************* + * + * streaming external for PD + * + * File: streamogg.cpp + * + * Description: Implementation of the streamer class for OGG/vorbis + * + * Author: Thomas Grill (t.grill@gmx.net) + * + *************************************************************/ + +#include "streamogg.h" + + +// explicit definition of report functions +extern "C" { + extern void post(char *fmt, ...); + extern void error(char *fmt, ...); +} + + +StreamOGG::StreamOGG(): + ov_inf(NULL),ov_comm(NULL) +{ + // set OGG callbacks + callbacks.read_func = read_func; + callbacks.seek_func = seek_func; + callbacks.close_func = close_func; + callbacks.tell_func = tell_func; +} + +void StreamOGG::Reset() +{ + Stream::Reset(); + ov_inf = NULL; + ov_comm = NULL; +} + +std::string StreamOGG::getTag(const char *tag) const +{ + const char *c = NULL; + if(ov_comm) c = vorbis_comment_query(ov_comm,const_cast(tag),0); + return c?c:""; +} + + +#define MAXINITTRIES 5 + +bool StreamOGG::WorkInit() +{ + bool ok = true; + + // read in enough data to represent the OGG header + char hdrbuf[8500]; + int i,need = sizeof hdrbuf; + for(i = MAXINITTRIES; i > 0 && need > 0; ) { + int n = ReadChunk(hdrbuf,need,true); + if(n) + need -= n; + else { + --i; + if(debug) post("Try to init again (%i)....",i); + } + } + if(!i) ok = false; + + // got n bytes into fifo + + if(ok && ov_open_callbacks(this,&ov_file,hdrbuf,sizeof hdrbuf,callbacks) < 0 ) { + post("Header format error"); + ok = false; + } + else { + ov_inf = ov_info(&ov_file,-1); + ov_comm = ov_comment(&ov_file,-1); + } + + return ok; +} + +int StreamOGG::DataRead(int frames) +{ + int current_section; + return ov_read_float(&ov_file,&bufs,frames,¤t_section); +} + +size_t StreamOGG::read_func(void *ptr, size_t size, size_t nmemb, void *datasource) +{ + StreamOGG *str = (StreamOGG *)datasource; + + if(!str->isInitializing()) pthread_mutex_lock(&str->mutex); + + int ret = str->encoded.Read(size*nmemb,(char *)ptr); + + if(str->debug) post("read %i of %i bytes from fifo",ret,size*nmemb); + + if(!str->isInitializing()) pthread_mutex_unlock(&str->mutex); + + return ret; +} + +int StreamOGG::close_func(void *datasource) +{ + post("Closing stream"); + + StreamOGG *str = (StreamOGG *)datasource; + pthread_mutex_lock(&str->mutex); + str->Reset(); + pthread_mutex_unlock(&str->mutex); + return 0; +} + -- cgit v1.2.1