diff options
author | Josh Coalson <jcoalson@users.sourceforce.net> | 2001-11-08 23:52:32 +0000 |
---|---|---|
committer | Josh Coalson <jcoalson@users.sourceforce.net> | 2001-11-08 23:52:32 +0000 |
commit | 8c13e6526e42330e623a191cde45961df05f3a7b (patch) | |
tree | 1b8619145b3252d8f1d4f82863781ed2b6f0ae7d /src | |
parent | 96a5d88839a6ccb920555b8166fbaaeefcb1f378 (diff) | |
download | flac-8c13e6526e42330e623a191cde45961df05f3a7b.tar.gz |
remove the old version to make way for the new version
Diffstat (limited to 'src')
-rw-r--r-- | src/plugin_winamp3/Makefile.vc | 40 | ||||
-rw-r--r-- | src/plugin_winamp3/core_api.h | 563 | ||||
-rw-r--r-- | src/plugin_winamp3/in_flac.cpp | 434 |
3 files changed, 0 insertions, 1037 deletions
diff --git a/src/plugin_winamp3/Makefile.vc b/src/plugin_winamp3/Makefile.vc deleted file mode 100644 index 1b33ec73..00000000 --- a/src/plugin_winamp3/Makefile.vc +++ /dev/null @@ -1,40 +0,0 @@ -# in_flac - Winamp3 FLAC input plugin
-# Copyright (C) 2001 Josh Coalson
-#
-# This program is free software; you can redistribute it and/or
-# modify it under the terms of the GNU General Public License
-# as published by the Free Software Foundation; either version 2
-# of the License, or (at your option) any later version.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with this program; if not, write to the Free Software
-# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
-
-!include <win32.mak>
-
-!IFDEF DEBUG
-.c.obj:
- $(cc) /GX $(cdebug) $(cflags) $(cvarsdll) /I "..\..\include" /I ".\include" -DSTRICT -YX /Od /D "_DEBUG" $<
-!else
-.c.obj:
- $(cc) /O2 $(crelease) $(cflags) $(cvarsdll) /I "..\..\include" /I ".\include" -DSTRICT -YX -DNODEBUG $<
-!endif
-
-C_FILES= \
- in_flac.c
-
-OBJS= $(C_FILES:.c=.obj)
-
-all: in_flac.dll
-
-in_flac.dll: $(OBJS)
- link.exe /dll /libpath:"..\..\obj\lib" -out:../../obj/bin/$*.dll $(OBJS) libFLAC.lib user32.lib kernel32.lib
-
-clean:
- -del *.obj *.pch
- -del ..\..\obj\bin\in_flac.*
diff --git a/src/plugin_winamp3/core_api.h b/src/plugin_winamp3/core_api.h deleted file mode 100644 index c627726b..00000000 --- a/src/plugin_winamp3/core_api.h +++ /dev/null @@ -1,563 +0,0 @@ - -/* Winamp 3 Player core api v0.1 -** (c)2000 nullsoft jcf/ct/dk -** Notes: -** Keep in mind that this header file is subject to change prior to the -** release of Winamp 3. The ability to configure plug-ins has yet to be -** added and is the first and foremost concern of the engineering team. -*/ - -#ifndef __CORE_API_H -#define __CORE_API_H - -// Visual C 6 makes big unaligned dlls. the following will correct it -#ifndef _DEBUG -// release optimizations -// /Og (global optimizations), /Os (favor small code), /Oy (no frame pointers) -#pragma optimize("gsy",on) -#pragma comment(linker,"/RELEASE") -// set the 512-byte alignment -#pragma comment(linker,"/opt:nowin98") -#endif - -// Use Assert in your code to catch errors that shouldn't happen, when compiled in release mode, they are #defined out -#ifndef ASSERT -#ifdef _DEBUG -#define ASSERT(x) if (!(x)) MessageBox(NULL,"ASSERT FAILED: " #x,"ASSERT FAILED in " __FILE__ ,MB_OK|MB_ICONSTOP); -#else -#define ASSERT(x) -#endif -#endif - - - -/* CLASS DESCRIPTIONS */ - -/* WReader -** File reader module class, ie. opens and reads files, streams -*/ -class WReader; - -/* WInputInfo -** Class that returns information (length, title, metadata) about a specified file -*/ -class WInputInfo; - -/* WInfo_callback -** Player's interface that provides Winamp 3 core functions to your WInputInfo classes -*/ -class WInfo_callback; - -/* WInputSource -** Input Source manager base class, ie. decodes mp3's, wavs -*/ -class WInputSource; - -/* WOutputFilter -** Abstract base class for any Output Filter plug-in, ie. changes pitch, converts format, outputs to speakers -*/ -class WOutputFilter; - -/* WPlayer_callback -** Player's interface that provides Winamp 3 core functions to your Input Sources and Output Filter plug-ins -** (Getting a reader for opening a file, sending stuff about what's going on to the Winamp 3 core) -*/ -class WPlayer_callback; - - - - -class WPlayer_callback -{ - public: - /* GetReader - ** Allows your Input Source and Output Filter plugins to request a reader from Winamp, - ** so you don't have to worry about opening files or streams - */ - virtual WReader *GetReader(char *url)=0; - - - /* The 3 following functions allows your Input Source and Output Filter plugins to send error/warning/status - ** messages back to the Winamp 3 core - */ - - /* Error - ** playback should stop (soundcard driver error, etc) - */ - virtual void Error(char *reason)=0; - - /* Warning - ** warning (something recoverable, like file not found, etc) - */ - virtual void Warning(char *warning)=0; - - /* Status - ** status update (nothing really wrong) - */ - virtual void Status(char *status)=0; - - - - - /* TitleChange - ** should be called if the current file titlename changes during the decoding - */ - virtual void TitleChange(char *new_title)=0; - - /* InfoChange - ** should be called if the infos about the current file changes during the decoding - */ - virtual void InfoChange(char *new_info_str, int new_length)=0; - - /* UrlChange - ** should be called if the current file associated URL changes during the decoding - */ - virtual void UrlChange(char *new_url)=0; -}; - - - - -class WInfo_callback -{ - public: - /* GetReader - ** Allows your WInfo classes to request a reader from Winamp - ** so you don't have to worry about opening files or streams - */ - virtual WReader *GetReader(char *url)=0; -}; - - - - -class WInputInfo -{ - public: - /* WInputInfo - ** WInputInfo constructor - */ - WInputInfo(){ }; - - /* m_info - ** Filled by Winamp. Pointer to WInputInfo callback function - */ - WInfo_callback *m_info; - - /* Open - ** Called by Winamp to request informations about a specified media (file, url, etc...) - ** returns 0 if succesful, 1 if not - ** - ** You must open, get all information and close the specified file here and store - ** the useful information into member elements for quick access by other functions - */ - virtual int Open(char *url) { return 1; } - - /* GetTitle - ** Called by Winamp to get the decoded title about the file opened - ** i.e. id3 title name, etc... - */ - virtual void GetTitle(char *buf, int maxlen) { if (maxlen>0) buf[0]=0; }; - - /* GetInfoString - ** Called by Winamp to get extra informations about the file opened - ** i.e. "160kbps stereo 44Khz" for MP3 files,"4 channels" for MOD files,etc... - */ - virtual void GetInfoString(char *buf, int maxlen) { if (maxlen>0) buf[0]=0; }; - - /* GetLength - ** Called by Winamp to retrieves media type length in milliseconds - ** returns -1 if length is undefined/infinite - */ - virtual int GetLength(void) { return -1; }; - - /* GetMetaData - ** Fetches metadata by attribute name (Artist, Album, Bitrate, etc...) - ** attribute names are non case-sensitive. - ** returns size of data - */ - virtual int GetMetaData(char *name, char *data, int data_len) { if (data&&data_len>0) *data=0; return 0; } - - /* ~WInputInfo - ** WInputInfo virtual destructor - */ - virtual ~WInputInfo() { }; -}; - - - - - - - - -/* WINAMP Output Filter NOTIFY MESSAGES -** Messages returned to notify Output Filter plug-ins of events -*/ - -typedef enum { - - /* WOFNM_FILETITLECHANGE - ** Sent when the song changes - ** param1=new filename song - ** param2=new title song - */ - WOFNM_FILETITLECHANGE=1024, - - /* WOFNM_ENDOFDECODE - ** Sent when decoding ends - */ - WOFNM_ENDOFDECODE, - -} WOutputFilterNotifyMsg; - - - - -class WOutputFilter -{ - protected: - /* WOutputFilter - ** WOutputFilter constructor - */ - WOutputFilter() { m_next=NULL; }; - - public: - /* m_player - ** Filled by Winamp. Pointer to Winamp 3 core player interface - */ - WPlayer_callback *m_player; - - /* m_next - ** Internally used by Winamp. Pointer to next activated Output Filter - */ - WOutputFilter *m_next; - - /* ~WOutputFilter - ** WOutputFilter destructor - */ - virtual ~WOutputFilter() { }; - - /* GetDescription - ** Retrieves your plug-in's text description - */ - virtual char *GetDescription() { return "Unknown"; }; - - /* ProcessSamples - ** Render data as it receives it - ** sampledata: Data to process - ** bytes: number of bytes to process - ** bps: Bits per sample (8 or 16) - ** nch: Number of channels (1 or 2) - ** srate: Sample rate in Hz - ** killswitch: Will be set to 1 by winamp if stop if requested. Poll the pointed value very often to - ** make sure Winamp doesn't hang - ** - ** Returns the number of processed bytes or -1 if unable to open the device or an error occured. - ** - ** You have to open your device (ie. Directsound) the first time this function is called. - */ - virtual int ProcessSamples(char *sampledata, int bytes, int *bps, int *nch, int *srate, bool *killswitch) { return bytes; } - - /* FlushSamples - ** Flushes output buffers so that all is written - */ - virtual void FlushSamples(bool *killswitch) { }; - - /* Restart - ** Called by Winamp after a seek - */ - virtual void Restart(void) { } - - /* GetLatency - ** Returns < 0 for a final output latency, > 0 for an additive - */ - virtual int GetLatency(void) { return 0; } - - /* Pause - ** Suspends output - */ - virtual void Pause(int pause) { } - - /* ShutDown - ** Completely stops output - ** - ** Close your device here (not in destructor) - */ - virtual void ShutDown(void) { } - - /* SetVolume - ** Sets the volume (0 to 255) - ** return 1 if volume successfully modified - */ - virtual int SetVolume(int volume) { return 0; } - - /* SetPan - ** Sets Left-Right sound balance (-127 to 127) - ** return 1 if pan successfully modified - */ - virtual int SetPan(int pan) { return 0; } - - /* Notify - ** Called by Winamp to notify what's going on - */ - virtual void Notify(WOutputFilterNotifyMsg msg, int data1, int data2) { } - -}; - - - - -class WInputSource -{ - - protected: - /* WInputSource - ** WInputSource constructor - */ - WInputSource(){ }; - - - public: - /* m_player - ** Filled by Winamp. Pointer to Winamp 3 core interface - */ - WPlayer_callback *m_player; - - /* GetDescription - ** Retrieves your plug-in's text description - */ - virtual char *GetDescription() { return "Unknown"; }; - - /* UsesOutputFilters - ** Returns whether or not the Output Filter pipeline can be used - */ - virtual int UsesOutputFilters(void) { return 1; } - - /* Open - ** Used to open and prepare input media type - */ - virtual int Open(char *url, bool *killswitch)=0; - - /* GetSamples - ** This function must fill bps, nch and srate. - ** Here, you have to fill the sample_buffer with decoded data. Be sure to fill it with the specified - ** size (bytes). Use an internal buffer, etc ... - ** - ** sample_buffer: buffer to put decoded data into - ** bytes: size of the sample_buffer - ** bps: Bits par sample (8 or 16) - ** nch: Number of channels (1 or 2) - ** srate: Sample rate in Hz - ** killswitch: Will be set to 1 by winamp if stop if requested. Poll the pointed value very often to - ** make sure Winamp doesn't hang - */ - virtual int GetSamples(char *sample_buffer, int bytes, int *bps, int *nch, int *srate, bool *killswitch)=0; - - /* SetVolume - ** Sets the volume (0 to 255) - ** Return 1 if volume has been set - */ - virtual int SetVolume(int volume) { return 0; }; - - /* SetPan - ** Sets Left-Right sound balance (-127 to 127) - ** return 1 if pan successfully modified - */ - virtual int SetPan(int pan) { return 0; }; - - /* SetPosition - ** Sets position in ms. returns 0 on success, 1 if seek impossible - */ - virtual int SetPosition(int)=0; - - /* Pause - ** Suspends input - */ - virtual void Pause(int pause) { }; - - /* GetPosition - ** Retrieve position in milliseconds - */ - virtual int GetPosition(void) { return 0; } - - /* GetTitle - ** Called by Winamp to get the decoded title about the file opened - ** i.e. stream name, id3 title name, etc... - */ - virtual void GetTitle(char *buf, int maxlen) { if(maxlen>0) buf[0]=0; }; - - /* GetInfoString - ** Called by Winamp to get extra informations about the file openend - ** i.e. "32kbps 44khz", etc... - */ - virtual void GetInfoString(char *buf, int maxlen) { if(maxlen>0) buf[0]=0; }; - - /* GetLength - ** Called by Winamp to retrieves media type length in milliseconds - ** returns -1 if length is undefined/infinite - */ - virtual int GetLength(void) { return -1; } - - /* ~WInputSource - ** ~WInputSource virtual destructor - */ - virtual ~WInputSource() { }; -}; - - - - -class WReader -{ - protected: - - /* WReader - ** WReader constructor - */ - WReader() { } - - public: - - /* m_player - ** Filled by Winamp. Pointer to Winamp 3 core interface - */ - WPlayer_callback *m_player; - - /* GetDescription - ** Retrieves your plug-in's text description - */ - virtual char *GetDescription() { return "Unknown"; }; - - /* Open - ** Used to open a file, return 0 on success - */ - virtual int Open(char *url, bool *killswitch)=0; - - /* Read - ** Returns number of BYTES read (if < length then eof or killswitch) - */ - virtual int Read(char *buffer, int length, bool *killswitch)=0; - - /* GetLength - ** Returns length of the entire file in BYTES, return -1 on unknown/infinite (as for a stream) - */ - virtual int GetLength(void)=0; - - /* CanSeek - ** Returns 1 if you can skip ahead in the file, 0 if not - */ - virtual int CanSeek(void)=0; - - /* Seek - ** Jump to a certain absolute position - */ - virtual int Seek(int position, bool *killswitch)=0; - - /* GetHeader - ** Retrieve header. Used in read_http to retrieve the HTTP header - */ - virtual char *GetHeader(char *name) { return 0; } - - /* ~WReader - ** WReader virtual destructor - */ - virtual ~WReader() { } -}; - - - - -/* DLL PLUGINS EXPORT STRUCTURES */ - -#define READ_VER 0x100 -#define IN_VER 0x100 -#define OF_VER 0x100 - - -typedef struct -{ - /* version - ** Version revision number - */ - int version; - - /* description - ** Text description of the reader plug-in - */ - char *description; - - /* create - ** Function pointer to create a reader module - */ - WReader *(*create)(); - - /* ismine - ** Determines whether or not a file should be read by this plug-in - */ - int (*ismine)(char *url); - -} reader_source; - - - - -typedef struct -{ - /* version - ** Version revision number - */ - int version; - - /* description - ** Text description of the input plug-in - */ - char *description; - - /* extension_list - ** Defines all the supported filetypes by this input plug-in - ** In semicolon delimited format ("ext;desc;ext;desc" etc). - */ - char *extension_list; - - /* ismine - ** called before extension checks, to allow detection of tone://,http://, etc - ** Determines whether or not a file type should be decoded by this plug-in - */ - int (*ismine)(char *filename); - - /* create - ** Function pointer to create a decoder module - */ - WInputSource *(*create)(void); - - /* createinfo - ** Function pointer to create a decoder module information - */ - WInputInfo *(*createinfo)(void); - -} input_source; - - - -typedef struct -{ - /* version - ** Version revision number - */ - int version; - - /* description - ** Text description of the output plug-in - */ - char *description; - - /* create - ** Function pointer to create an Output Filter - */ - WOutputFilter *(*create)(); - -} output_filter; - - -#endif diff --git a/src/plugin_winamp3/in_flac.cpp b/src/plugin_winamp3/in_flac.cpp deleted file mode 100644 index c5eca0bf..00000000 --- a/src/plugin_winamp3/in_flac.cpp +++ /dev/null @@ -1,434 +0,0 @@ -/* in_flac - Winamp3 FLAC input plugin - * Copyright (C) 2001 Josh Coalson - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License - * as published by the Free Software Foundation; either version 2 - * of the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. - */ - -#include <windows.h> -#include <stdio.h> -#include "core_api.h" -#include "FLAC/all.h" - -typedef struct { - FLAC__byte raw[128]; - char title[31]; - char artist[31]; - char album[31]; - char comment[31]; - unsigned year; - unsigned track; /* may be 0 if v1 (not v1.1) tag */ - unsigned genre; - char description[1024]; /* the formatted description passed to xmms */ -} id3v1_struct; - -typedef struct { - FLAC__bool abort_flag; - FLAC__bool is_playing; - FLAC__bool eof; - unsigned total_samples; - unsigned bits_per_sample; - unsigned channels; - unsigned sample_rate; - unsigned length_in_msec; -} file_info_struct; - -static FLAC__bool get_id3v1_tag_(const char *filename, id3v1_struct *tag); -static FLAC__bool decoder_init_(const char *filename); -static FLAC__StreamDecoderWriteStatus write_callback_(const FLAC__FileDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 *buffer[], void *client_data); -static void metadata_callback_(const FLAC__FileDecoder *decoder, const FLAC__StreamMetaData *metadata, void *client_data); -static void error_callback_(const FLAC__FileDecoder *decoder, FLAC__StreamDecoderErrorStatus status, void *client_data); - -static char plugin_description_[] = "Reference FLAC Player v" FLAC__VERSION_STRING; -static HINSTANCE g_hDllInstance_; - -class FLAC_Info : public WInputInfo -{ - private: - id3v1_struct tag_; - int length_in_msec_; - public: - FLAC_Info(); - ~FLAC_Info(); - int Open(char *url); - void GetTitle(char *buf, int maxlen); - void GetInfoString(char *buf, int maxlen); - inline int GetLength(void) { return length_in_msec_; } -}; - -FLAC_Info::FLAC_Info() : WInputInfo() -{ - length_in_msec_ = -1; -} - -FLAC_Info::~FLAC_Info() -{ -} - -int FLAC_Info::Open(char *url) -{ - const char *filename = url; /* @@@ right now we only handle files */ - - (void)get_id3v1_tag_(filename, &tag_); - - file_info_struct tmp_file_info; - FLAC__FileDecoder *tmp_decoder = FLAC__file_decoder_new(); - if(0 == tmp_decoder) { - length_in_msec_ = -1; - return 1; - } - tmp_file_info.abort_flag = false; - FLAC__file_decoder_set_md5_checking(tmp_decoder, false); - FLAC__file_decoder_set_filename(tmp_decoder, filename); - FLAC__file_decoder_set_write_callback(tmp_decoder, write_callback_); - FLAC__file_decoder_set_metadata_callback(tmp_decoder, metadata_callback_); - FLAC__file_decoder_set_error_callback(tmp_decoder, error_callback_); - FLAC__file_decoder_set_client_data(tmp_decoder, &tmp_file_info); - if(FLAC__file_decoder_init(tmp_decoder) != FLAC__FILE_DECODER_OK) { - length_in_msec_ = -1; - return 1; - } - if(!FLAC__file_decoder_process_metadata(tmp_decoder)) { - length_in_msec_ = -1; - return 1; - } - - length_in_msec_ = (int)tmp_file_info.length_in_msec; - - if(FLAC__file_decoder_get_state(tmp_decoder) != FLAC__FILE_DECODER_UNINITIALIZED) - FLAC__file_decoder_finish(tmp_decoder); - FLAC__file_decoder_delete(tmp_decoder); - - return 0; -} - -void FLAC_Info::GetTitle(char *buf, int maxlen) -{ - strncpy(buf, title, maxlen-1); - buf[maxlen-1] = 0; -} - -void FLAC_Info::GetInfoString(char *buf, int maxlen) -{ - strncpy(buf, description, maxlen-1); - buf[maxlen-1] = 0; -} - - -class FLAC_Source : public WInputSource -{ - private: - id3v1_struct tag_; - FLAC__FileDecoder *decoder_; - FLAC__int16 reservoir_[FLAC__MAX_BLOCK_SIZE * 2 * 2]; /* *2 for max channels, another *2 for overflow */ - unsigned reservoir_samples_; - file_info_struct file_info_; - FLAC__bool audio_error_; - public: - FLAC_Source(); - ~FLAC_Source(); - inline char *GetDescription(void) { return plugin_description_; } - inline int UsesOutputFilters(void) { return 1; } - int Open(char *url, FLAC__bool *killswitch); - int GetSamples(char *sample_buffer, int bytes, int *bps, int *nch, int *srate, FLAC__bool *killswitch); - int SetPosition(int); // sets position in ms - void GetTitle(char *buf, int maxlen); - void GetInfoString(char *buf, int maxlen); - inline int GetLength(void) { return (int)file_info_.length_in_msec; } - void cleanup(); -}; - -FLAC_Source::FLAC_Source() : WInputSource() -{ - decoder_ = FLAC__file_decoder_new(); - file_info_.length_in_msec = -1; - audio_error_ = false; -} - -FLAC_Source::~FLAC_Source() -{ - if(decoder_) - FLAC__file_decoder_delete(decoder_); -} - -void FLAC_Source::GetTitle(char *buf, int maxlen) -{ - strncpy(buf, title, maxlen-1); - buf[maxlen-1] = 0; -} - -void FLAC_Source::GetInfoString(char *buf, int maxlen) -{ - strncpy(buf, description, maxlen-1); - buf[maxlen-1] = 0; -} - -int FLAC_Source::Open(char *url, FLAC__bool *killswitch) -{ - const char *filename = url; /* @@@ right now we only handle files */ - - { - FILE *f = fopen(filename, "r"); - if(0 == f) - return 1; - fclose(f); - } - - (void)get_id3v1_tag_(filename, &tag); - - file_info_.length_in_msec = -1; - - if(!decoder_init_(filename)) - return 1; - - if(file_info_.abort_flag) { - cleanup(); - return 1; - } - - reservoir_samples_ = 0; - audio_error_ = false; - file_info_.is_playing = true; - file_info_.eof = false; - - return 0; -} - -int FLAC_Source::GetSamples(char *sample_buffer, int bytes, int *bps, int *nch, int *srate, FLAC__bool *killswitch) -{ - int return_bytes = 0; - - *bps = (int)file_info_.bits_per_sample; - *nch = (int)file_info_.channels; - *srate = (int)file_info_.sample_rate; - - if(!file_info_.eof) { - const unsigned channels = file_info_.channels; - const unsigned bytes_per_sample = (file_info_.bits_per_sample+7) / 8; - const unsigned wide_samples = bytes / channels / bytes_per_sample; -if(bytes&0x3)fprintf(stderr,"@@@ Got odd buffer size request\n"); - while(reservoir_samples_ < wide_samples) { - if(FLAC__file_decoder_get_state(decoder) == FLAC__FILE_DECODER_END_OF_FILE) { - file_info_.eof = true; - break; - } - else if(!FLAC__file_decoder_process_one_frame(decoder_)) - break; - } - if(reservoir_samples_ > 0) { - unsigned i, n = min(reservoir_samples_, wide_samples), delta; - FLAC__int16 output = (FLAC__int16*)sample_buffer; - - for(i = 0; i < n*channels; i++) - output[i] = reservoir_[i]; - delta = i; - for( ; i < reservoir_samples_*channels; i++) - reservoir[i-delta] = reservoir[i]; - reservoir_samples_ -= n; - - return_bytes = (int)(n * bytes_per_sample * channels); - } - else { - file_info_.eof = true; - } - } - return return_bytes; -} - -int FLAC_Source::SetPosition(int position) -{ - const double distance = (double)position * 1000.0 / (double)file_info_.length_in_msec; - unsigned target_sample = (unsigned)(distance * (double)file_info_.total_samples); - if(FLAC__file_decoder_seek_absolute(decoder_, (FLAC__uint64)target_sample)) { - file_info_.eof = false; - reservoir_samples_ = 0; - return 0; - } - else { - return 1; - } -} - -void FLAC_Source::cleanup() -{ - if(decoder_ && FLAC__file_decoder_get_state(decoder_) != FLAC__FILE_DECODER_UNINITIALIZED) - FLAC__file_decoder_finish(decoder_); - - reservoir_samples_ = 0; - audio_error_ = false; - file_info_.is_playing = false; - file_info_.eof = false; - file_info_.length_in_msec = -1; -} - - -/*********************************************************************** - * local routines - **********************************************************************/ - -FLAC__bool get_id3v1_tag_(const char *filename, id3v1_struct *tag) -{ - const char *temp; - FILE *f = fopen(filename, "rb"); - memset(tag, 0, sizeof(id3v1_struct)); - - /* set the title and description to the filename by default */ - temp = strrchr(filename, '/'); - if(!temp) - temp = filename; - else - temp++; - strcpy(tag->description, temp); - *strrchr(tag->description, '.') = '\0'; - strncpy(tag->title, tag->description, 30); tag->title[30] = '\0'; - - if(0 == f) - return false; - if(-1 == fseek(f, -128, SEEK_END)) { - fclose(f); - return false; - } - if(fread(tag->raw, 1, 128, f) < 128) { - fclose(f); - return false; - } - fclose(f); - if(strncmp(tag->raw, "TAG", 3)) - return false; - else { - char year_str[5]; - - memcpy(tag->title, tag->raw+3, 30); - memcpy(tag->artist, tag->raw+33, 30); - memcpy(tag->album, tag->raw+63, 30); - memcpy(year_str, tag->raw+93, 4); year_str[4] = '\0'; tag->year = atoi(year_str); - memcpy(tag->comment, tag->raw+97, 30); - tag->genre = (unsigned)((FLAC__byte)tag->raw[127]); - tag->track = (unsigned)((FLAC__byte)tag->raw[126]); - - sprintf(tag->description, "%s - %s", tag->artist, tag->title); - - return true; - } -} - -FLAC__bool decoder_init_(const char *filename) -{ - if(decoder_ == 0) - return false; - - FLAC__file_decoder_set_md5_checking(decoder, false); - FLAC__file_decoder_set_filename(decoder, filename); - FLAC__file_decoder_set_write_callback(decoder, write_callback_); - FLAC__file_decoder_set_metadata_callback(decoder, metadata_callback_); - FLAC__file_decoder_set_error_callback(decoder, error_callback_); - FLAC__file_decoder_set_client_data(decoder, &file_info_); - if(FLAC__file_decoder_init(decoder_) != FLAC__FILE_DECODER_OK) - return false; - - file_info_.abort_flag = false; - - if(!FLAC__file_decoder_process_metadata(decoder_)) - return false; - - return true; -} - -FLAC__StreamDecoderWriteStatus write_callback_(const FLAC__FileDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 *buffer[], void *client_data) -{ - file_info_struct *file_info = (file_info_struct *)client_data; - const unsigned bps = file_info->bits_per_sample, channels = file_info->channels, wide_samples = frame->header.blocksize; - unsigned wide_sample, sample, channel; - - (void)decoder; - - if(file_info->abort_flag) - return FLAC__STREAM_DECODER_WRITE_ABORT; - - FLAC__ASSERT(bps == 16); - - for(sample = reservoir_samples_*channels, wide_sample = 0; wide_sample < wide_samples; wide_sample++) - for(channel = 0; channel < channels; channel++, sample++) - reservoir_[sample] = (FLAC__int16)buffer[channel][wide_sample]; - - reservoir_samples_ += wide_samples; - - return FLAC__STREAM_DECODER_WRITE_CONTINUE; -} - -void metadata_callback_(const FLAC__FileDecoder *decoder, const FLAC__StreamMetaData *metadata, void *client_data) -{ - file_info_struct *file_info = (file_info_struct *)client_data; - (void)decoder; - if(metadata->type == FLAC__METADATA_TYPE_STREAMINFO) { - FLAC__ASSERT(metadata->data.stream_info.total_samples < 0x100000000); /* this plugin can only handle < 4 gigasamples */ - file_info->total_samples = (unsigned)(metadata->data.stream_info.total_samples&0xffffffff); - file_info->bits_per_sample = metadata->data.stream_info.bits_per_sample; - file_info->channels = metadata->data.stream_info.channels; - file_info->sample_rate = metadata->data.stream_info.sample_rate; - - if(file_info->bits_per_sample != 16) { - file_info->abort_flag = true; - return; - } - file_info->length_in_msec = file_info->total_samples * 10 / (file_info->sample_rate / 100); - } -} - -void error_callback_(const FLAC__FileDecoder *decoder, FLAC__StreamDecoderErrorStatus status, void *client_data) -{ - file_info_struct *file_info = (file_info_struct *)client_data; - (void)decoder; - if(status != FLAC__STREAM_DECODER_ERROR_LOST_SYNC) - file_info->abort_flag = true; -} - - -/*********************************************************************** - * C-level interface - **********************************************************************/ - -static int C_level__FLAC_is_mine_(char *filename) -{ - return 0; -} - -static WInputSource *C_level__FLAC_create_() -{ - return new FLAC_Source(); -} - -static WInputInfo *C_level__FLAC_create_info_() -{ - return new FLAC_Info(); -} - -input_source C_level__FLAC_source_ = { - IN_VER, - plugin_description_, - "FLAC;FLAC Audio File (*.FLAC)", - C_level__FLAC_is_mine_, - C_level__FLAC_create_, - C_level__FLAC_create_info_ -}; - -extern "C" -{ - __declspec (dllexport) int getInputSource(HINSTANCE hDllInstance, input_source **inStruct) - { - g_hDllInstance_ = hDllInstance; - *inStruct = &C_level__FLAC_source_; - return 1; - } -} |