diff --git a/darkice/tags/darkice-0_7/AUTHORS b/darkice/tags/darkice-0_7/AUTHORS new file mode 100644 index 0000000..fb766d8 --- /dev/null +++ b/darkice/tags/darkice-0_7/AUTHORS @@ -0,0 +1,10 @@ +DarkIce is being written by: + + Akos Maroy, + +with contributions by: + + Jim Crilly, + aNa|0Gue, + Robin P. Blanchard, + diff --git a/darkice/tags/darkice-0_7/COPYING b/darkice/tags/darkice-0_7/COPYING new file mode 100644 index 0000000..598598b --- /dev/null +++ b/darkice/tags/darkice-0_7/COPYING @@ -0,0 +1,345 @@ +All source code in the src directory is covered under the +GNU General Public License (GNU GPL). + + + + GNU GENERAL PUBLIC LICENSE + Version 2, June 1991 + + Copyright (C) 1989, 1991 Free Software Foundation, Inc. + 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + + Preamble + + The licenses for most software are designed to take away your +freedom to share and change it. By contrast, the GNU General Public +License is intended to guarantee your freedom to share and change free +software--to make sure the software is free for all its users. This +General Public License applies to most of the Free Software +Foundation's software and to any other program whose authors commit to +using it. (Some other Free Software Foundation software is covered by +the GNU Library General Public License instead.) You can apply it to +your programs, too. + + When we speak of free software, we are referring to freedom, not +price. Our General Public Licenses are designed to make sure that you +have the freedom to distribute copies of free software (and charge for +this service if you wish), that you receive source code or can get it +if you want it, that you can change the software or use pieces of it +in new free programs; and that you know you can do these things. + + To protect your rights, we need to make restrictions that forbid +anyone to deny you these rights or to ask you to surrender the rights. +These restrictions translate to certain responsibilities for you if you +distribute copies of the software, or if you modify it. + + For example, if you distribute copies of such a program, whether +gratis or for a fee, you must give the recipients all the rights that +you have. You must make sure that they, too, receive or can get the +source code. And you must show them these terms so they know their +rights. + + We protect your rights with two steps: (1) copyright the software, and +(2) offer you this license which gives you legal permission to copy, +distribute and/or modify the software. + + Also, for each author's protection and ours, we want to make certain +that everyone understands that there is no warranty for this free +software. If the software is modified by someone else and passed on, we +want its recipients to know that what they have is not the original, so +that any problems introduced by others will not reflect on the original +authors' reputations. + + Finally, any free program is threatened constantly by software +patents. We wish to avoid the danger that redistributors of a free +program will individually obtain patent licenses, in effect making the +program proprietary. To prevent this, we have made it clear that any +patent must be licensed for everyone's free use or not licensed at all. + + The precise terms and conditions for copying, distribution and +modification follow. + + GNU GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. This License applies to any program or other work which contains +a notice placed by the copyright holder saying it may be distributed +under the terms of this General Public License. The "Program", below, +refers to any such program or work, and a "work based on the Program" +means either the Program or any derivative work under copyright law: +that is to say, a work containing the Program or a portion of it, +either verbatim or with modifications and/or translated into another +language. (Hereinafter, translation is included without limitation in +the term "modification".) Each licensee is addressed as "you". + +Activities other than copying, distribution and modification are not +covered by this License; they are outside its scope. The act of +running the Program is not restricted, and the output from the Program +is covered only if its contents constitute a work based on the +Program (independent of having been made by running the Program). +Whether that is true depends on what the Program does. + + 1. You may copy and distribute verbatim copies of the Program's +source code as you receive it, in any medium, provided that you +conspicuously and appropriately publish on each copy an appropriate +copyright notice and disclaimer of warranty; keep intact all the +notices that refer to this License and to the absence of any warranty; +and give any other recipients of the Program a copy of this License +along with the Program. + +You may charge a fee for the physical act of transferring a copy, and +you may at your option offer warranty protection in exchange for a fee. + + 2. You may modify your copy or copies of the Program or any portion +of it, thus forming a work based on the Program, and copy and +distribute such modifications or work under the terms of Section 1 +above, provided that you also meet all of these conditions: + + a) You must cause the modified files to carry prominent notices + stating that you changed the files and the date of any change. + + b) You must cause any work that you distribute or publish, that in + whole or in part contains or is derived from the Program or any + part thereof, to be licensed as a whole at no charge to all third + parties under the terms of this License. + + c) If the modified program normally reads commands interactively + when run, you must cause it, when started running for such + interactive use in the most ordinary way, to print or display an + announcement including an appropriate copyright notice and a + notice that there is no warranty (or else, saying that you provide + a warranty) and that users may redistribute the program under + these conditions, and telling the user how to view a copy of this + License. (Exception: if the Program itself is interactive but + does not normally print such an announcement, your work based on + the Program is not required to print an announcement.) + +These requirements apply to the modified work as a whole. If +identifiable sections of that work are not derived from the Program, +and can be reasonably considered independent and separate works in +themselves, then this License, and its terms, do not apply to those +sections when you distribute them as separate works. But when you +distribute the same sections as part of a whole which is a work based +on the Program, the distribution of the whole must be on the terms of +this License, whose permissions for other licensees extend to the +entire whole, and thus to each and every part regardless of who wrote it. + +Thus, it is not the intent of this section to claim rights or contest +your rights to work written entirely by you; rather, the intent is to +exercise the right to control the distribution of derivative or +collective works based on the Program. + +In addition, mere aggregation of another work not based on the Program +with the Program (or with a work based on the Program) on a volume of +a storage or distribution medium does not bring the other work under +the scope of this License. + + 3. You may copy and distribute the Program (or a work based on it, +under Section 2) in object code or executable form under the terms of +Sections 1 and 2 above provided that you also do one of the following: + + a) Accompany it with the complete corresponding machine-readable + source code, which must be distributed under the terms of Sections + 1 and 2 above on a medium customarily used for software interchange; or, + + b) Accompany it with a written offer, valid for at least three + years, to give any third party, for a charge no more than your + cost of physically performing source distribution, a complete + machine-readable copy of the corresponding source code, to be + distributed under the terms of Sections 1 and 2 above on a medium + customarily used for software interchange; or, + + c) Accompany it with the information you received as to the offer + to distribute corresponding source code. (This alternative is + allowed only for noncommercial distribution and only if you + received the program in object code or executable form with such + an offer, in accord with Subsection b above.) + +The source code for a work means the preferred form of the work for +making modifications to it. For an executable work, complete source +code means all the source code for all modules it contains, plus any +associated interface definition files, plus the scripts used to +control compilation and installation of the executable. However, as a +special exception, the source code distributed need not include +anything that is normally distributed (in either source or binary +form) with the major components (compiler, kernel, and so on) of the +operating system on which the executable runs, unless that component +itself accompanies the executable. + +If distribution of executable or object code is made by offering +access to copy from a designated place, then offering equivalent +access to copy the source code from the same place counts as +distribution of the source code, even though third parties are not +compelled to copy the source along with the object code. + + 4. You may not copy, modify, sublicense, or distribute the Program +except as expressly provided under this License. Any attempt +otherwise to copy, modify, sublicense or distribute the Program is +void, and will automatically terminate your rights under this License. +However, parties who have received copies, or rights, from you under +this License will not have their licenses terminated so long as such +parties remain in full compliance. + + 5. You are not required to accept this License, since you have not +signed it. However, nothing else grants you permission to modify or +distribute the Program or its derivative works. These actions are +prohibited by law if you do not accept this License. Therefore, by +modifying or distributing the Program (or any work based on the +Program), you indicate your acceptance of this License to do so, and +all its terms and conditions for copying, distributing or modifying +the Program or works based on it. + + 6. Each time you redistribute the Program (or any work based on the +Program), the recipient automatically receives a license from the +original licensor to copy, distribute or modify the Program subject to +these terms and conditions. You may not impose any further +restrictions on the recipients' exercise of the rights granted herein. +You are not responsible for enforcing compliance by third parties to +this License. + + 7. If, as a consequence of a court judgment or allegation of patent +infringement or for any other reason (not limited to patent issues), +conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot +distribute so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you +may not distribute the Program at all. For example, if a patent +license would not permit royalty-free redistribution of the Program by +all those who receive copies directly or indirectly through you, then +the only way you could satisfy both it and this License would be to +refrain entirely from distribution of the Program. + +If any portion of this section is held invalid or unenforceable under +any particular circumstance, the balance of the section is intended to +apply and the section as a whole is intended to apply in other +circumstances. + +It is not the purpose of this section to induce you to infringe any +patents or other property right claims or to contest validity of any +such claims; this section has the sole purpose of protecting the +integrity of the free software distribution system, which is +implemented by public license practices. Many people have made +generous contributions to the wide range of software distributed +through that system in reliance on consistent application of that +system; it is up to the author/donor to decide if he or she is willing +to distribute software through any other system and a licensee cannot +impose that choice. + +This section is intended to make thoroughly clear what is believed to +be a consequence of the rest of this License. + + 8. If the distribution and/or use of the Program is restricted in +certain countries either by patents or by copyrighted interfaces, the +original copyright holder who places the Program under this License +may add an explicit geographical distribution limitation excluding +those countries, so that distribution is permitted only in or among +countries not thus excluded. In such case, this License incorporates +the limitation as if written in the body of this License. + + 9. The Free Software Foundation may publish revised and/or new versions +of the General Public License from time to time. Such new versions will +be similar in spirit to the present version, but may differ in detail to +address new problems or concerns. + +Each version is given a distinguishing version number. If the Program +specifies a version number of this License which applies to it and "any +later version", you have the option of following the terms and conditions +either of that version or of any later version published by the Free +Software Foundation. If the Program does not specify a version number of +this License, you may choose any version ever published by the Free Software +Foundation. + + 10. If you wish to incorporate parts of the Program into other free +programs whose distribution conditions are different, write to the author +to ask for permission. For software which is copyrighted by the Free +Software Foundation, write to the Free Software Foundation; we sometimes +make exceptions for this. Our decision will be guided by the two goals +of preserving the free status of all derivatives of our free software and +of promoting the sharing and reuse of software generally. + + NO WARRANTY + + 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY +FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN +OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES +PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED +OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS +TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE +PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, +REPAIR OR CORRECTION. + + 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR +REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, +INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING +OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED +TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY +YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER +PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE +POSSIBILITY OF SUCH DAMAGES. + + END OF TERMS AND CONDITIONS + + How to Apply These Terms to Your New Programs + + If you develop a new program, and you want it to be of the greatest +possible use to the public, the best way to achieve this is to make it +free software which everyone can redistribute and change under these terms. + + To do so, attach the following notices to the program. It is safest +to attach them to the start of each source file to most effectively +convey the exclusion of warranty; and each file should have at least +the "copyright" line and a pointer to where the full notice is found. + + + Copyright (C) + + 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 + + +Also add information on how to contact you by electronic and paper mail. + +If the program is interactive, make it output a short notice like this +when it starts in an interactive mode: + + Gnomovision version 69, Copyright (C) year name of author + Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. + This is free software, and you are welcome to redistribute it + under certain conditions; type `show c' for details. + +The hypothetical commands `show w' and `show c' should show the appropriate +parts of the General Public License. Of course, the commands you use may +be called something other than `show w' and `show c'; they could even be +mouse-clicks or menu items--whatever suits your program. + +You should also get your employer (if you work as a programmer) or your +school, if any, to sign a "copyright disclaimer" for the program, if +necessary. Here is a sample; alter the names: + + Yoyodyne, Inc., hereby disclaims all copyright interest in the program + `Gnomovision' (which makes passes at compilers) written by James Hacker. + + , 1 April 1989 + Ty Coon, President of Vice + +This General Public License does not permit incorporating your program into +proprietary programs. If your program is a subroutine library, you may +consider it more useful to permit linking proprietary applications with the +library. If this is what you want to do, use the GNU Library General +Public License instead of this License. diff --git a/darkice/tags/darkice-0_7/ChangeLog b/darkice/tags/darkice-0_7/ChangeLog new file mode 100644 index 0000000..f7217a8 --- /dev/null +++ b/darkice/tags/darkice-0_7/ChangeLog @@ -0,0 +1,57 @@ +19-10-2001: DarkIce 0.7 released + + o added support for FreeBSD + thanks to Robin P. Blanchard, + o added support for resampling mp3 streams + o DarkIce config file now may contain spaces and tabs as white space + o configure script enables build with or without lame / Ogg Vorbis + also possibility to specify alternate locations for these + +18-09-2001: DarkIce 0.6 released + + o added support for IceCast2 server with Ogg Vorbis streaming + Ogg Vorbis support thanks to aNa|0Gue + o added support for SUN Solaris + o removed long command line options (as these are extensions to UNIX) + o removed configure option to specify location of lame library + o removed configure option to compile static executable + +09-09-2001: DarkIce 0.5 released + + o added support for ShoutCast servers + o removed local copy of SGI STL, uses STL of the C++ compiler + o compiles with gcc3-c++ + o added man page darkice.cfg.5 + o bugfix: config files can have comments before the first section + +02-09-2001: DarkIce 0.4 released + + o support for external command line encoder removed, replaced + with using lame as a shared object or statically linked library + o added darkice man page + o created RPM packages + o DarkIce no longer reports an error if the sound card recording + sample rate could not be set to the exact specified amount + (e.g. the sound card reports 44101 Hz instead of 44100 Hz) + + +26-08-2001: DarkIce 0.3.1 released + + o support for unlimited time encoding + thanks to Jim Crilly, + + +20-12-2000: DarkIce 0.3 released + + o added POSIX real-time scheduling + + +18-11-2000: DarkIce 0.2 released + + o code cleanup + o first real tests made + o added verbosity command line option + + +13-11-2000: DarkIce 0.1 released + diff --git a/darkice/tags/darkice-0_7/INSTALL b/darkice/tags/darkice-0_7/INSTALL new file mode 100644 index 0000000..9c330dc --- /dev/null +++ b/darkice/tags/darkice-0_7/INSTALL @@ -0,0 +1,52 @@ +DarkIce installation notes +========================== + +DarkIce uses the following libraries (and associated header files): + +for capability to stream mp3 to IceCast 1.x and Shoutcast: +- libmp3lame + +for capability to stream Ogg Vorbis to IceCast 2: +- libogg +- libvoribs +- libvorbisenc + +To install libmp3lame, please refer to INSTALL.lame. +To install libogg, libvoribs and libvorbisenc, please look at INSTALL.vorbis. + + +Installing DarkIce +------------------ + +If you're reading this, you probably have downloaded and extracted the +DarkIce tarball. Go to the directory you extracted it, and try: + +./configure --help + +This will give you all the compile configuration options. + +On Solaris systems, for some reason the configure script does not +find the include file lame/lame.h if it uses the SUN Workshop C compiler +as a preprocessor for testing. Therefore you might consider setting: + +export CPP="gcc -E" + +This hack is not needed on other systems. + +If chosing the default compile options, issue the following commands: + +./configure +make +make install + +For the last step, you need to be root or have write permissions in the +target directories, usually directories under /usr/local. + +Now you should have DarkIce installed. For documentation, try + +man darkice + +To try out the program, try + +darkice -h + diff --git a/darkice/tags/darkice-0_7/INSTALL.lame b/darkice/tags/darkice-0_7/INSTALL.lame new file mode 100644 index 0000000..70f98fd --- /dev/null +++ b/darkice/tags/darkice-0_7/INSTALL.lame @@ -0,0 +1,52 @@ +Installing Lame +--------------- + +To install DarkIce, you need the Lame 3.89 or later libraries and +related header files already installed on your system. + +It is recommended that use install Lame to the usual system locations, +/usr/lib, /usr/include, so that DarkIce will find the header files and +libraries. Thus when configuring, add --prefix=/usr to the configure +options. + +Grab the latest lame source tarball from a download site found at +http://www.mp3dev.org/mp3/download/download.html +or from the DarkIce SourceForge project download area +http://sourceforge.net/project/showfiles.php?group_id=14111 + +I took lame lame3.89beta.tar.gz. Go to the directory where you saved it, +and issue the following commands: + +tar xfz lame3.89beta.tar.gz +cd lame-3.89 +./configure --with-fileio=lame --without-vorbis --disable-gtktest --enable-expopt=full --prefix=/usr +make +make install + +For the last step, you need to be root or have write permissions in the +target directories. + +You might consider using nasm if you're on a i386 system, with the +configure option --enable-nasmm, for maximum performance. + + +On RedHat Linux +--------------- + +Compiling Lame on RedHat Linux is a tricky issue, because of gcc 2.96 +packaged with this distributions 7.0 and 7.1. You either have to use +the comaptibility compiler package (compat-egcs and related packages, +providing gcc 2.91), or even better, gcc 3.0. + +It is recommended that you compile lame with gcc 3. For maximum performance, +use the nasm assembler to compile assembly optimizations into lame. +Try the following commands: + +tar xfz lame3.89beta.tar.gz +cd lame-3.89 +export CC=gcc3 +./configure --with-fileio=lame --without-vorbis --disable-gtktest --enable-nasm --enable-expopt=full --prefix=/usr +make +make install + + diff --git a/darkice/tags/darkice-0_7/INSTALL.vorbis b/darkice/tags/darkice-0_7/INSTALL.vorbis new file mode 100644 index 0000000..decadbc --- /dev/null +++ b/darkice/tags/darkice-0_7/INSTALL.vorbis @@ -0,0 +1,39 @@ +Installing Ogg Vorbis +--------------------- + +To install DarkIce, you need the Ogg Vorbis libraries (and related +header files: + +- libogg +- libvoribs +- libvorbisenc + +installed on your system. + +It is recommended that use install these to the usual system locations, +/usr/lib, /usr/include, so that DarkIce will find the header files and +libraries. Thus when configuring, add --prefix=/usr to the configure +options. + +Grab the latest Ogg Vorbis tarballs from +http://www.xiph.org/ogg/vorbis/download.html + +I took libogg-1.0rc2.tar.gz and libvorbis-1.0rc2.tar.gz. Go to the +directory where you saved them, and issue the following commands: + +tar xfz libogg-1.0rc2.tar.gz +cd libogg-1.0rc2 +./configure --prefix=/usr +make +make install +cd .. + +tar xfz libvorbis-1.0rc2.tar.gz +cd libvorbis-1.0rc2 +./configure --prefix=/usr +make +make install + +For the install steps, you need to be root or have write permissions in the +target directories. + diff --git a/darkice/tags/darkice-0_7/Makefile.am b/darkice/tags/darkice-0_7/Makefile.am new file mode 100644 index 0000000..ecff092 --- /dev/null +++ b/darkice/tags/darkice-0_7/Makefile.am @@ -0,0 +1,16 @@ +KDOC_DIR=kdoc + +SUBDIRS = src man + +sysconf_DATA = darkice.cfg + +EXTRA_DIST = $(KDOC_DIR) darkice.cfg INSTALL.lame INSTALL.vorbis + +$(KDOC_DIR): kdocs + +kdocs: src kdocs_clean + cd src; kdoc --private --strip-h-path --name DarkIce --outputdir ../$(KDOC_DIR)/ *.h + +kdocs_clean: + rm -rf $(KDOC_DIR) + diff --git a/darkice/tags/darkice-0_7/NEWS b/darkice/tags/darkice-0_7/NEWS new file mode 100644 index 0000000..5924b32 --- /dev/null +++ b/darkice/tags/darkice-0_7/NEWS @@ -0,0 +1,35 @@ +18-09-2001, Akos Maroy, darkeye@users.sourceforge.net + + Released version 0.6. See ChangeLog for changes. + + +09-09-2001, Akos Maroy, darkeye@users.sourceforge.net + + Released version 0.5. See ChangeLog for changes. + + +02-09-2001, Akos Maroy, darkeye@users.sourceforge.net + + Released version 0.4. See ChangeLog for changes. + + +26-08-2001, Akos Maroy, darkeye@users.sourceforge.net + + Released version 0.3.1. See ChangeLog for changes. + + +20-12-2000, Akos Maroy, darkeye@users.sourceforge.net + + Released version 0.3. See ChangeLog for changes. + + +18-11-2000, Akos Maroy, darkeye@users.sourceforge.net + + Released version 0.2. See ChangeLog for changes. + + +13-11-2000, Akos Maroy, darkeye@users.sourceforge.net + + Initial release. Supports the lame encoder. + + diff --git a/darkice/tags/darkice-0_7/README b/darkice/tags/darkice-0_7/README new file mode 100644 index 0000000..d901462 --- /dev/null +++ b/darkice/tags/darkice-0_7/README @@ -0,0 +1,40 @@ +DarkIce live audio streamer, http://darkice.sourceforge.net +Copyright (c) 2000-2001, Tyrell Hungary, http://tyrell.hu + + +Contents +-------- + +1. What is DarkIce? +2. Compiling and installing + + +1. What is DarkIce? +------------------- + +DarkIce is an IceCast, IceCast2 and ShoutCast live audio streamer. It +takes audio input from a sound card, encodes it into mp3 and/or Ogg Vorbis, +and sends the mp3 stream to one or more IceCast and/or ShoutCast servers, +the Ogg Vorbis stream to one or more IceCast2 servers. + + +2. Compiling and installing +--------------------------- + +On how to compile and install, please read the file INSTALL. If you're +impatient, try: + +./configure +make + +The executable built is src/darkice. +To install, try as root: + +make install + + +For documentation, try: + +man darkice + + diff --git a/darkice/tags/darkice-0_7/TODO b/darkice/tags/darkice-0_7/TODO new file mode 100644 index 0000000..26c2cb8 --- /dev/null +++ b/darkice/tags/darkice-0_7/TODO @@ -0,0 +1,9 @@ +o change Ref to follow inheritance +o make a master config file, and a small one ? +o add support for VBR encoding +o reconnect to server if connection is dropped +o add support for multiple servers for one stream ? +o libtoolize ? +o revisit real-time scheduling and one-thread-per-connection +o look into performance +o create proper error-reporting module diff --git a/darkice/tags/darkice-0_7/acinclude.m4 b/darkice/tags/darkice-0_7/acinclude.m4 new file mode 100644 index 0000000..f905328 --- /dev/null +++ b/darkice/tags/darkice-0_7/acinclude.m4 @@ -0,0 +1,55 @@ +dnl acinclude.m4. Change *this* file to add new or change macros. +dnl When changes have been made, delete aclocal.m4 and run +dnl "aclocal". +dnl +dnl DO NOT change aclocal.m4 ! +dnl + +dnl----------------------------------------------------------------------------- +dnl LA_SEARCH_FILE(variable, filename, PATH) +dnl Search "filename" in the specified "PATH", "variable" will +dnl contain the full pathname or the empty string +dnl PATH is space-separated list of directories. +dnl by Florian Bomers +dnl----------------------------------------------------------------------------- +AC_DEFUN(LA_SEARCH_FILE,[ + $1= + dnl hack: eliminate line feeds in $2 + for FILE in $2; do + for DIR in $3; do + dnl use PATH in order + if test ".$1"="." && test -f "$DIR/$FILE"; then + $1=$DIR + fi + done + done +]) + +dnl----------------------------------------------------------------------------- +dnl LA_SEARCH_LIB(lib-variable, include-variable, lib-filename, header-filename, prefix) +dnl looks for "lib-filename" and "header-filename" in the area of "prefix". +dnl if found, "lib-variable" and "include-variable" are set to the +dnl respective paths. +dnl prefix is a single path +dnl libs are searched in prefix, prefix/lib +dnl headers are searched in prefix, prefix/include, +dnl +dnl If one of them is not found, both "lib-variable", "include-variable" are +dnl set to the empty string. +dnl +dnl TODO: assert function call to verify lib +dnl +dnl by Florian Bomers +dnl----------------------------------------------------------------------------- +AC_DEFUN(LA_SEARCH_LIB,[ + dnl look for lib + LA_SEARCH_FILE($1, $3, $5 $5/lib ) + dnl look for header. + LA_SEARCH_FILE($2, $4, $5 $5/include ) + if test ".$1" = "." || test ".$2" = "."; then + $1= + $2= + fi +]) + + diff --git a/darkice/tags/darkice-0_7/configure.in b/darkice/tags/darkice-0_7/configure.in new file mode 100644 index 0000000..da64f3b --- /dev/null +++ b/darkice/tags/darkice-0_7/configure.in @@ -0,0 +1,106 @@ +dnl Process this file with autoconf to produce a configure script. +AC_INIT(src/DarkIce.cpp) +AM_INIT_AUTOMAKE(darkice, 0.7) + +AM_CONFIG_HEADER(config.h) + +AC_PROG_CXX +AC_PROG_INSTALL + +dnl AC_STDC_HEADERS +AC_HAVE_HEADERS(errno.h fcntl.h stdio.h stdlib.h string.h unistd.h limits.h) +AC_HAVE_HEADERS(signal.h time.h sys/time.h sys/types.h sys/wait.h) +AC_HAVE_HEADERS(netdb.h netinet/in.h sys/ioctl.h sys/socket.h sys/stat.h) +AC_HAVE_HEADERS(sched.h) +AC_HAVE_HEADERS(sys/soundcard.h sys/audio.h) +AC_HEADER_SYS_WAIT() + +AC_TYPE_PID_T() +AC_TYPE_SIZE_T() + +AC_CHECK_LIB( socket, socket) +AC_CHECK_LIB( nsl, gethostbyname) +AC_CHECK_LIB( rt, sched_getscheduler) + + +dnl----------------------------------------------------------------------------- +dnl link the lame library if requested +dnl----------------------------------------------------------------------------- +AC_SUBST( LAME_INCFLAGS) +AC_SUBST( LAME_LDFLAGS) + +AC_ARG_WITH( lame, +[ --with-lame use lame for encoding mp3 streams [yes] ], + USE_LAME=${withval}, USE_LAME="yes" ) +AC_ARG_WITH( lame-prefix, +[ --with-lame-prefix=DIR alternate location for lame [/usr] + look for libraries in LAME-PREFIX/lib, + for headers in LAME-PREFIX/include], + CONFIG_LAME_PREFIX="${withval}", CONFIG_LAME_PREFIX="/usr") + +if test "x${USE_LAME}" = "xyes" ; then + AC_MSG_CHECKING( [for lame library at ${CONFIG_LAME_PREFIX}] ) + LA_SEARCH_LIB( LAME_LIB_LOC, LAME_INC_LOC, libmp3lame.a, lame/lame.h, + ${CONFIG_LAME_PREFIX}) + if test "x${LAME_LIB_LOC}" != "x" ; then + AC_DEFINE( HAVE_LAME_LIB, 1, [build with lame library] ) + LAME_INCFLAGS="-I${LAME_INC_LOC}" + LAME_LDFLAGS="-L${LAME_LIB_LOC} -lmp3lame" + AC_MSG_RESULT( [found at ${CONFIG_LAME_PREFIX}] ) + else + AC_MSG_WARN( [not found, building without lame]) + fi +else + AC_MSG_RESULT( [building without lame] ) +fi + + +dnl----------------------------------------------------------------------------- +dnl link the ogg vorbis libraries if requested +dnl----------------------------------------------------------------------------- +AC_SUBST( VORBIS_INCFLAGS) +AC_SUBST( VORBIS_LDFLAGS) + +AC_ARG_WITH( vorbis, +[ --with-vorbis use Ogg Vorbis for encoding vorbis streams [yes] ], + USE_VORBIS=${withval}, USE_VORBIS="yes" ) +AC_ARG_WITH( vorbis-prefix, +[ --with-vorbis-prefix=DIR alternate location for vorbis [/usr] + look for libraries in VORBIS-PREFIX/lib, + for headers in VORBIS-PREFIX/include], + CONFIG_VORBIS_PREFIX="${withval}", CONFIG_VORBIS_PREFIX="/usr") + +if test "x${USE_VORBIS}" = "xyes" ; then + AC_MSG_CHECKING( [for vorbis libraries at ${CONFIG_VORBIS_PREFIX}] ) + LA_SEARCH_LIB( OGG_LIB_LOC, OGG_INC_LOC, libogg.a, ogg/ogg.h, + ${CONFIG_VORBIS_PREFIX}) + LA_SEARCH_LIB( VORBIS_LIB_LOC, VORBIS_INC_LOC, libvorbis.a, vorbis/codec.h, + ${CONFIG_VORBIS_PREFIX}) + LA_SEARCH_LIB( VORBISENC_LIB_LOC, VORBISENC_INC_LOC, + libvorbisenc.a, vorbis/vorbisenc.h, + ${CONFIG_VORBIS_PREFIX}) + + if test "x${OGG_LIB_LOC}" != "x" -a \ + "x${VORBIS_LIB_LOC}" != "x" -a \ + "x${VORBISENC_LIB_LOC}" != "x" ; then + + AC_DEFINE( HAVE_VORBIS_LIB, 1, [build with Ogg Vorbis library] ) + VORBIS_INCFLAGS="-I${OGG_INC_LOC}" + VORBIS_LDFLAGS="-L${OGG_LIB_LOC} -logg -lvorbis -lvorbisenc" + AC_MSG_RESULT( [found at ${CONFIG_VORBIS_PREFIX}] ) + else + AC_MSG_WARN( [not found, building without Ogg Vorbis]) + fi +else + AC_MSG_RESULT( [building without Ogg Vorbis] ) +fi + + +dnl make sure at least one of lame and vorbis present +if test "x${LAME_INCFLAGS}" = "x" -a "x${VORBIS_INCFLAGS}" = "x" ; then + AC_MSG_ERROR( [neither lame nor Ogg Vorbis configured]) +fi + + +AC_OUTPUT(Makefile src/Makefile man/Makefile) + diff --git a/darkice/tags/darkice-0_7/darkice.cfg b/darkice/tags/darkice-0_7/darkice.cfg new file mode 100644 index 0000000..c589443 --- /dev/null +++ b/darkice/tags/darkice-0_7/darkice.cfg @@ -0,0 +1,75 @@ +# sample DarkIce configuration file, edit for your needs before using +# see the darkice.cfg man page for details + +# this section describes general aspects of the live streaming session +[general] +duration = 60 # duration of encoding, in seconds. 0 means forever +bufferSecs = 5 # size of internal slip buffer, in seconds + +# this section describes the audio input that will be streamed +[input] +device = /dev/dsp # OSS DSP soundcard device for the audio input +sampleRate = 22050 # sample rate in Hz. try 11025, 22050 or 44100 +bitsPerSample = 16 # bits per sample. try 16 +channel = 2 # channels. 1 = mono, 2 = stereo + +# this section describes a streaming connection to an IceCast server +# there may be up to 8 of these sections, named [icecast-0] ... [icecast-7] +# these can be mixed with [icecast2-x] and [shoutcast-x] sections +[icecast-0] +bitrate = 96 # bitrate of the mp3 stream sent to the server +server = yp.yourserver.com + # host name of the server +port = 8000 # port of the IceCast server, usually 8000 +password = hackme # source password to the IceCast server +mountPoint = sample96 # mount point of this stream on the IceCast server +name = DarkIce trial + # name of the stream +description = This is only a trial + # description of the stream +url = http://www.yourserver.com + # URL related to the stream +genre = my own # genre of the stream +public = yes # advertise this stream? + +# this section describes a streaming connection to an IceCast2 server +# there may be up to 8 of these sections, named [icecast2-0] ... [icecast2-7] +# these can be mixed with [icecast-x] and [shoutcast-x] sections +[icecast2-0] +bitrate = 96 # bitrate of the mp3 stream sent to the server +server = yp.yourserver.com + # host name of the server +port = 8000 # port of the IceCast2 server, usually 8000 +password = hackme # source password to the IceCast2 server +mountPoint = sample96 # mount point of this stream on the IceCast2 server +name = DarkIce trial + # name of the stream +description = This is only a trial + # description of the stream +url = http://www.yourserver.com + # URL related to the stream +genre = my own # genre of the stream +public = yes # advertise this stream? + +# this section describes a streaming connection to a ShoutCast server +# there may be up to 8 of these sections, named [shoutcast-0] ... [shoutcast-7] +# these can be mixed with [icecast-x] and [icecast2-x] sections +[shoutcast-0] +bitrate = 96 # bitrate of the mp3 stream sent to the server +server = yp.yourserver.com + # host name of the server +port = 8001 # source port of the ShoutCast server, usually 8001 +password = hackme # source password to the ShoutCast server +name = DarkIce trial + # name of the stream +url = http://www.yourserver.com + # URL related to the stream +genre = my own # genre of the stream +public = yes # advertise this stream? +irc = irc.yourserver.com + # IRC info related to the stream +aim = aim here # AIM info related to the stream +icq = I see you too + # ICQ info related to the stream + + diff --git a/darkice/tags/darkice-0_7/install-sh b/darkice/tags/darkice-0_7/install-sh new file mode 100755 index 0000000..e9de238 --- /dev/null +++ b/darkice/tags/darkice-0_7/install-sh @@ -0,0 +1,251 @@ +#!/bin/sh +# +# install - install a program, script, or datafile +# This comes from X11R5 (mit/util/scripts/install.sh). +# +# Copyright 1991 by the Massachusetts Institute of Technology +# +# Permission to use, copy, modify, distribute, and sell this software and its +# documentation for any purpose is hereby granted without fee, provided that +# the above copyright notice appear in all copies and that both that +# copyright notice and this permission notice appear in supporting +# documentation, and that the name of M.I.T. not be used in advertising or +# publicity pertaining to distribution of the software without specific, +# written prior permission. M.I.T. makes no representations about the +# suitability of this software for any purpose. It is provided "as is" +# without express or implied warranty. +# +# Calling this script install-sh is preferred over install.sh, to prevent +# `make' implicit rules from creating a file called install from it +# when there is no Makefile. +# +# This script is compatible with the BSD install script, but was written +# from scratch. It can only install one file at a time, a restriction +# shared with many OS's install programs. + + +# set DOITPROG to echo to test this script + +# Don't use :- since 4.3BSD and earlier shells don't like it. +doit="${DOITPROG-}" + + +# put in absolute paths if you don't have them in your path; or use env. vars. + +mvprog="${MVPROG-mv}" +cpprog="${CPPROG-cp}" +chmodprog="${CHMODPROG-chmod}" +chownprog="${CHOWNPROG-chown}" +chgrpprog="${CHGRPPROG-chgrp}" +stripprog="${STRIPPROG-strip}" +rmprog="${RMPROG-rm}" +mkdirprog="${MKDIRPROG-mkdir}" + +transformbasename="" +transform_arg="" +instcmd="$mvprog" +chmodcmd="$chmodprog 0755" +chowncmd="" +chgrpcmd="" +stripcmd="" +rmcmd="$rmprog -f" +mvcmd="$mvprog" +src="" +dst="" +dir_arg="" + +while [ x"$1" != x ]; do + case $1 in + -c) instcmd="$cpprog" + shift + continue;; + + -d) dir_arg=true + shift + continue;; + + -m) chmodcmd="$chmodprog $2" + shift + shift + continue;; + + -o) chowncmd="$chownprog $2" + shift + shift + continue;; + + -g) chgrpcmd="$chgrpprog $2" + shift + shift + continue;; + + -s) stripcmd="$stripprog" + shift + continue;; + + -t=*) transformarg=`echo $1 | sed 's/-t=//'` + shift + continue;; + + -b=*) transformbasename=`echo $1 | sed 's/-b=//'` + shift + continue;; + + *) if [ x"$src" = x ] + then + src=$1 + else + # this colon is to work around a 386BSD /bin/sh bug + : + dst=$1 + fi + shift + continue;; + esac +done + +if [ x"$src" = x ] +then + echo "install: no input file specified" + exit 1 +else + true +fi + +if [ x"$dir_arg" != x ]; then + dst=$src + src="" + + if [ -d $dst ]; then + instcmd=: + chmodcmd="" + else + instcmd=mkdir + fi +else + +# Waiting for this to be detected by the "$instcmd $src $dsttmp" command +# might cause directories to be created, which would be especially bad +# if $src (and thus $dsttmp) contains '*'. + + if [ -f $src -o -d $src ] + then + true + else + echo "install: $src does not exist" + exit 1 + fi + + if [ x"$dst" = x ] + then + echo "install: no destination specified" + exit 1 + else + true + fi + +# If destination is a directory, append the input filename; if your system +# does not like double slashes in filenames, you may need to add some logic + + if [ -d $dst ] + then + dst="$dst"/`basename $src` + else + true + fi +fi + +## this sed command emulates the dirname command +dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'` + +# Make sure that the destination directory exists. +# this part is taken from Noah Friedman's mkinstalldirs script + +# Skip lots of stat calls in the usual case. +if [ ! -d "$dstdir" ]; then +defaultIFS=' +' +IFS="${IFS-${defaultIFS}}" + +oIFS="${IFS}" +# Some sh's can't handle IFS=/ for some reason. +IFS='%' +set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'` +IFS="${oIFS}" + +pathcomp='' + +while [ $# -ne 0 ] ; do + pathcomp="${pathcomp}${1}" + shift + + if [ ! -d "${pathcomp}" ] ; + then + $mkdirprog "${pathcomp}" + else + true + fi + + pathcomp="${pathcomp}/" +done +fi + +if [ x"$dir_arg" != x ] +then + $doit $instcmd $dst && + + if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi && + if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi && + if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi && + if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi +else + +# If we're going to rename the final executable, determine the name now. + + if [ x"$transformarg" = x ] + then + dstfile=`basename $dst` + else + dstfile=`basename $dst $transformbasename | + sed $transformarg`$transformbasename + fi + +# don't allow the sed command to completely eliminate the filename + + if [ x"$dstfile" = x ] + then + dstfile=`basename $dst` + else + true + fi + +# Make a temp file name in the proper directory. + + dsttmp=$dstdir/#inst.$$# + +# Move or copy the file name to the temp name + + $doit $instcmd $src $dsttmp && + + trap "rm -f ${dsttmp}" 0 && + +# and set any options; do chmod last to preserve setuid bits + +# If any of these fail, we abort the whole thing. If we want to +# ignore errors from any of these, just make sure not to ignore +# errors from the above "$doit $instcmd $src $dsttmp" command. + + if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi && + if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi && + if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi && + if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi && + +# Now rename the file to the real destination. + + $doit $rmcmd -f $dstdir/$dstfile && + $doit $mvcmd $dsttmp $dstdir/$dstfile + +fi && + + +exit 0 diff --git a/darkice/tags/darkice-0_7/man/Makefile.am b/darkice/tags/darkice-0_7/man/Makefile.am new file mode 100644 index 0000000..8406ddd --- /dev/null +++ b/darkice/tags/darkice-0_7/man/Makefile.am @@ -0,0 +1,4 @@ +man_MANS = darkice.1 darkice.cfg.5 + +EXTRA_DIST = ${man_MANS} + diff --git a/darkice/tags/darkice-0_7/man/darkice.1 b/darkice/tags/darkice-0_7/man/darkice.1 new file mode 100644 index 0000000..41140a5 --- /dev/null +++ b/darkice/tags/darkice-0_7/man/darkice.1 @@ -0,0 +1,101 @@ +.TH darkice 1 "September 18, 2001" "DarkIce" "DarkIce live audio streamer" +.SH NAME +darkice \- an icecast / shoutcast live audio streamer +.SH SYNOPSIS +.B darkice +[options] -c config.file +.SH DESCRIPTION +.PP +.B DarkIce +is an +.B IceCast +, +.B IceCast2 +and +.B ShoutCast +live audio streamer. It takes audio input from a +sound card, encodes it into mp3 and/or Ogg Vorbis, +and sends the mp3 stream to one or more +.B IceCast +and/or +.B ShoutCast +servers, the Ogg Vorbis stream to one or more +.B IceCast2 +servers. + +.B DarkIce +uses +.SM POSIX +real-time scheduling to keep up with sound card input. +.SM POSIX +real-time scheduling is only available if the program is run as root. +Therefore it is recommended that +.B DarkIce +is run as root. + +.B DarkIce +uses the +.B Lame +mp3 encoder as a library to encode audio intput to mp3, and uses the +.B Ogg Vorbis +library to encode into Ogg Vorbis. + +.SH OPTIONS +.TP +.BI "\-c " config.file +Specifies what configuration file to use. + +.TP +.BI "\-v " n +Sets the verbosity level, between 0 and 10. 0 is silent, 10 is loud. +Defaults to 1. + +.TP +.BI "\-h " +Prints the help page and exists. + + +.SH BUGS +.PP +Lots of bugs. + + +.SH "SEE ALSO" +darkice.cfg(5) + + +.SH AUTHOR +Akos Maroy +.I + + +.SH ACKNOWLEDGEMENTS +Some contributions by Jim Crilly +.I + +Ogg Vorbis encoding code based on the contribution of aNa|0Gue +.I + +BSD porting help from Robin P. Blanchard +.I + + +.SH LINKS +Project homepage: +.I http://darkice.sourceforge.net/ + +.B IceCast +homepage: +.I http://www.icecast.org/ + +.B ShoutCast +homepage: +.I http://www.shoutcast.com/ + +.B Lame +homepage: +.I http://www.mp3dev.org/mp3/ + +.B Ogg Vorbis +homepage: +.I http://www.xiph.org/ogg/vorbis/ diff --git a/darkice/tags/darkice-0_7/man/darkice.cfg.5 b/darkice/tags/darkice-0_7/man/darkice.cfg.5 new file mode 100644 index 0000000..a4187dd --- /dev/null +++ b/darkice/tags/darkice-0_7/man/darkice.cfg.5 @@ -0,0 +1,411 @@ +.TH darkice.cfg 5 "October 19, 2001" "DarkIce" "DarkIce live audio streamer" +.SH NAME +darkice.cfg \- configuration file for darkice +.SH DESCRIPTION +.PP +The configuration file consists of sections, with key = value pairs +separated with spaces and/or tabs inside each secion: + +.nf +[section1] +# this is a whole line comment +key = value +an ugly key name = long value # this end is a comment too + +[section2] +# this is a whole line comment in section 2 +key = value +an ugly key name = long value # this end is a comment too +.fi + +A proper +.B DarkIce +configuration file contains the following sections: +.nf +[general] +[input] +[icecast-0] ... [icecast-7] +[icecast2-0] ... [icecast2-7] +[shoutcast-0] ... [shoutcast-7] +.fi + +The order of the sections is not important. Sections [general] and [input] +are required, and at least one of [icecast-x], [icecast2-x] +or [shoutcast-x] is needed. + +In particular, the following sections and values are recognized: +.PP +.B [general] + +This section describes general operational parameters (required). + +Required values: + +.TP +.I duration +Time for DarkIce to run, in seconds. If 0, run forever. +.TP +.I bufferSecs +Data read from the sound card is buffered before sent to +the encoder. Each buffer will be able to hold this +many seconds of samples. + +.PP +.B [input] + +This section describes the input (required). + +Required values: + +.TP +.I device +OSS DSP audio device to record from (e.g. /dev/dsp) +.TP +.I sampleRate +The sample rate to record with, samples per second +(e.g. 44100 for 44.1kHz CD-quality audio, 22050 for 22kHz or 11025 +for 11kHz) +.TP +.I bitsPerSample +Number of bits to use for each sample (e.g. 8 bits or 16 bits) +.TP +.I channel +Number of channels to record (e.g. 1 for mono, 2 for stereo) + +.PP +.B [icecast-x] + +This section describes an output to an +.B IceCast +server, while encoding +with a lame encoder. There may be at most 8 outputs, numbered from 0 ... 7. +The number is included in the section name (e.g. [icecast-0] ... [icecast-7]). +The stream will be reachable at +.I http://:/ + +Required values: + +.TP +.I bitrate +Bit rate to encode to in kBits / sec (e.g. 96) +.TP +.I server +The +.B IceCast +server's name (e.g. yp.yourserver.com) +.TP +.I port +The port to connect to the IceCast server (e.g. 8000) +.TP +.I password +The password to use to connect to the +.B IceCast +server +.TP +.I mountPoint +Mount point for the stream on the server + +.PP +Optional values: + +.TP +.I sampleRate +The sample rate of the encoded mp3 output. If not specified, defaults +to the value of the input sample rate. +.TP +.I name +Name of the stream +.TP +.I description +Description of the stream +.TP +.I url +Url related to the stream +.TP +.I genre +Genre of the stream +.TP +.I public +"yes" or "no", wether the stream is public +.TP +.I remoteDumpFile +The file the +.B IceCast +server should dump the contents of +this stream on its side. +.TP +.I lowpass +Lowpass filter setting for the lame encoder. If not set, +the encoder's default behaviour is used +.TP +.I highpass +Highpass filter setting for the lame encoder. If not set, +the encoder's default behaviour is used + +.PP +.B [icecast2-x] + +This section describes an output to an +.B IceCast2 +server, while encoding +with the ogg vobis encoder. +There may be at most 8 outputs, numbered from 0 ... 7. +The number is included in the section name (e.g. [icecast2-0] ... [icecast2-7]). +The stream will be reachable at +.I http://:/ + +Required values: + +.TP +.I bitrate +Bit rate to encode to in kBits / sec (e.g. 96) +.TP +.I server +The +.B IceCast2 +server's name (e.g. yp.yourserver.com) +.TP +.I port +The port to connect to the IceCast server (e.g. 8000) +.TP +.I password +The password to use to connect to the +.B IceCast2 +server +.TP +.I mountPoint +Mount point for the stream on the server + +.PP +Optional values: + +.TP +.I name +Name of the stream +.TP +.I description +Description of the stream +.TP +.I url +Url related to the stream +.TP +.I genre +Genre of the stream +.TP +.I public +"yes" or "no", wether the stream is public + +.PP +.B [shoutcast-x] + +This section describes an output to a +.B ShoutCast +server, while encoding +with a lame encoder. There may be at most 8 outputs, numbered from 0 ... 7. +The number is included in the section name +(e.g. [shoutcast-0] ... [shoutcast-7]). +The stream will be reachable at +.I http://:/ + +Required values: + +.TP +.I bitrate +Bit rate to encode to in kBits / sec (e.g. 96) +.TP +.I server +The +.B ShoutCast +server's name (e.g. yp.yourserver.com) +.TP +.I port +The source port to connect to the ShoutCast server (e.g. 8001) +.TP +.I password +The password to use to connect to the +.B ShoutCast +server + +.PP +Optional values: + +.TP +.I sampleRate +The sample rate of the encoded mp3 output. If not specified, defaults +to the value of the input sample rate. +.TP +.I name +Name of the stream +.TP +.I url +Url related to the stream +.TP +.I genre +Genre of the stream +.TP +.I public +"yes" or "no", wether the stream is public +.TP +.I irc +IRC information related to the stream +.TP +.I aim +AIM information related to the stream +.TP +.I icq +ICQ information related to the stream +.TP +.I lowpass +Lowpass filter setting for the lame encoder. If not set, +the encoder's default behaviour is used +.TP +.I highpass +Highpass filter setting for the lame encoder. If not set, +the encoder's default behaviour is used + +.PP +A sample configuration file follows. This file makes +.B DarkIce +stream for 1 minute (60 seconds) from the audio device +.I /dev/dsp +at 22.05kHz, 16 bit stereo. +It will build up a connection to the +.B IceCast +server yp.yourserver.com on port 8000 with the password "hackme". +The stream will be encoded to 96 kb/s mp3, and will be reachable at +.I http://yp.yourserver.com:8000/live96 +to mp3 players. +The encoding session will be stored by +.B IceCast +in the file +.I /tmp/live96.mp3 +on the server side. + +.nf +[general] +duration = 60 +bufferSecs = 5 + +[input] +device = /dev/dsp +sampleRate = 22050 +bitsPerSample = 16 +channel = 2 + +[icecast-0] +bitrate = 96 +server = yp.yourserver.com +port = 8000 +password = hackme +mountPoint = live96 +name = DarkIce trial +description = This is only a trial +url = http://www.yourserver.com +genre = live +public = no +remoteDumpFile = /tmp/live96.mp3 +.fi + + +.PP +A bit more complicated sample follows. This one makes +.B DarkIce +stream for 1 hour (3600 seconds) from the audio device +.I /dev/dsp +at 44.1kHz, 16 bit stereo. + +It will build up a connection to an +.B IceCast +server yp.your-ice-server.com on port 8000 with the password "ice-hackme". +The sound for this stream will be cut at 10500 Hz from above. +The stream will be encoded to 96 kb/s mp3 and resampled to 22.05kHz. +The stream will be reachable at +.I http://yp.your-ice-server.com:8000/live96 +to mp3 players. +The encoding session will be stored by +.B IceCast +in the file +.I /tmp/live96.mp3 +on the server side. + +It will also connect to a +.I ShoutCast +server at yp.your-shout-server.com on port 8001 with the password "shout-hackme" +This stream will be encoded to 128 kb/s mp3, and will be reachable at +.I http://yp.your-shout-server.com:8000 +to mp3 players. + +.nf +[general] +duration = 3600 +bufferSecs = 5 + +[input] +device = /dev/dsp +sampleRate = 22050 +bitsPerSample = 16 +channel = 2 + +[icecast-0] +sampleRate = 22050 +bitrate = 96 +lowpass = 10500 +server = yp.your-ice-server.com +port = 8000 +password = ice-hackme +mountPoint = live96 +name = DarkIce trial +description = This is only a trial +url = http://www.yourserver.com +genre = live +public = yes +remoteDumpFile = /tmp/live96.mp3 + +[shoutcast-0] +bitrate = 128 +server = yp.your-shout-server.com +port = 8001 +password = shout-hackme +name = DarkIce trial +url = http://www.yourserver.com +genre = live +public = yes +irc = irc.yourserver.com +aim = aim here +icq = I see you too +.fi + + +.SH BUGS +.PP +Lots of bugs. + + +.SH "SEE ALSO" +darkice(1) + + +.SH AUTHOR +Akos Maroy +.I + + +.SH LINKS +Project homepage: +.I http://darkice.sourceforge.net/ + +.B IceCast +homepage: +.I http://www.icecast.org/ + +.B ShoutCast +homepage: +.I http://www.shoutcast.com/ + +.B Lame +homepage: +.I http://www.mp3dev.org/mp3/ + +.B Ogg Vorbis +homepage: +.I http://www.xiph.org/ogg/vorbis/ diff --git a/darkice/tags/darkice-0_7/missing b/darkice/tags/darkice-0_7/missing new file mode 100755 index 0000000..7789652 --- /dev/null +++ b/darkice/tags/darkice-0_7/missing @@ -0,0 +1,190 @@ +#! /bin/sh +# Common stub for a few missing GNU programs while installing. +# Copyright (C) 1996, 1997 Free Software Foundation, Inc. +# Franc,ois Pinard , 1996. + +# 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, 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. + +if test $# -eq 0; then + echo 1>&2 "Try \`$0 --help' for more information" + exit 1 +fi + +case "$1" in + + -h|--h|--he|--hel|--help) + echo "\ +$0 [OPTION]... PROGRAM [ARGUMENT]... + +Handle \`PROGRAM [ARGUMENT]...' for when PROGRAM is missing, or return an +error status if there is no known handling for PROGRAM. + +Options: + -h, --help display this help and exit + -v, --version output version information and exit + +Supported PROGRAM values: + aclocal touch file \`aclocal.m4' + autoconf touch file \`configure' + autoheader touch file \`config.h.in' + automake touch all \`Makefile.in' files + bison create \`y.tab.[ch]', if possible, from existing .[ch] + flex create \`lex.yy.c', if possible, from existing .c + lex create \`lex.yy.c', if possible, from existing .c + makeinfo touch the output file + yacc create \`y.tab.[ch]', if possible, from existing .[ch]" + ;; + + -v|--v|--ve|--ver|--vers|--versi|--versio|--version) + echo "missing - GNU libit 0.0" + ;; + + -*) + echo 1>&2 "$0: Unknown \`$1' option" + echo 1>&2 "Try \`$0 --help' for more information" + exit 1 + ;; + + aclocal) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`acinclude.m4' or \`configure.in'. You might want + to install the \`Automake' and \`Perl' packages. Grab them from + any GNU archive site." + touch aclocal.m4 + ;; + + autoconf) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`configure.in'. You might want to install the + \`Autoconf' and \`GNU m4' packages. Grab them from any GNU + archive site." + touch configure + ;; + + autoheader) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`acconfig.h' or \`configure.in'. You might want + to install the \`Autoconf' and \`GNU m4' packages. Grab them + from any GNU archive site." + files=`sed -n 's/^[ ]*A[CM]_CONFIG_HEADER(\([^)]*\)).*/\1/p' configure.in` + test -z "$files" && files="config.h" + touch_files= + for f in $files; do + case "$f" in + *:*) touch_files="$touch_files "`echo "$f" | + sed -e 's/^[^:]*://' -e 's/:.*//'`;; + *) touch_files="$touch_files $f.in";; + esac + done + touch $touch_files + ;; + + automake) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`Makefile.am', \`acinclude.m4' or \`configure.in'. + You might want to install the \`Automake' and \`Perl' packages. + Grab them from any GNU archive site." + find . -type f -name Makefile.am -print | + sed 's/\.am$/.in/' | + while read f; do touch "$f"; done + ;; + + bison|yacc) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified a \`.y' file. You may need the \`Bison' package + in order for those modifications to take effect. You can get + \`Bison' from any GNU archive site." + rm -f y.tab.c y.tab.h + if [ $# -ne 1 ]; then + eval LASTARG="\${$#}" + case "$LASTARG" in + *.y) + SRCFILE=`echo "$LASTARG" | sed 's/y$/c/'` + if [ -f "$SRCFILE" ]; then + cp "$SRCFILE" y.tab.c + fi + SRCFILE=`echo "$LASTARG" | sed 's/y$/h/'` + if [ -f "$SRCFILE" ]; then + cp "$SRCFILE" y.tab.h + fi + ;; + esac + fi + if [ ! -f y.tab.h ]; then + echo >y.tab.h + fi + if [ ! -f y.tab.c ]; then + echo 'main() { return 0; }' >y.tab.c + fi + ;; + + lex|flex) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified a \`.l' file. You may need the \`Flex' package + in order for those modifications to take effect. You can get + \`Flex' from any GNU archive site." + rm -f lex.yy.c + if [ $# -ne 1 ]; then + eval LASTARG="\${$#}" + case "$LASTARG" in + *.l) + SRCFILE=`echo "$LASTARG" | sed 's/l$/c/'` + if [ -f "$SRCFILE" ]; then + cp "$SRCFILE" lex.yy.c + fi + ;; + esac + fi + if [ ! -f lex.yy.c ]; then + echo 'main() { return 0; }' >lex.yy.c + fi + ;; + + makeinfo) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified a \`.texi' or \`.texinfo' file, or any other file + indirectly affecting the aspect of the manual. The spurious + call might also be the consequence of using a buggy \`make' (AIX, + DU, IRIX). You might want to install the \`Texinfo' package or + the \`GNU make' package. Grab either from any GNU archive site." + file=`echo "$*" | sed -n 's/.*-o \([^ ]*\).*/\1/p'` + if test -z "$file"; then + file=`echo "$*" | sed 's/.* \([^ ]*\) *$/\1/'` + file=`sed -n '/^@setfilename/ { s/.* \([^ ]*\) *$/\1/; p; q; }' $file` + fi + touch $file + ;; + + *) + echo 1>&2 "\ +WARNING: \`$1' is needed, and you do not seem to have it handy on your + system. You might have modified some files without having the + proper tools for further handling them. Check the \`README' file, + it often tells you about the needed prerequirements for installing + this package. You may also peek at any GNU archive site, in case + some other package would contain this missing \`$1' program." + exit 1 + ;; +esac + +exit 0 diff --git a/darkice/tags/darkice-0_7/mkinstalldirs b/darkice/tags/darkice-0_7/mkinstalldirs new file mode 100755 index 0000000..6b3b5fc --- /dev/null +++ b/darkice/tags/darkice-0_7/mkinstalldirs @@ -0,0 +1,40 @@ +#! /bin/sh +# mkinstalldirs --- make directory hierarchy +# Author: Noah Friedman +# Created: 1993-05-16 +# Public domain + +# $Id$ + +errstatus=0 + +for file +do + set fnord `echo ":$file" | sed -ne 's/^:\//#/;s/^://;s/\// /g;s/^#/\//;p'` + shift + + pathcomp= + for d + do + pathcomp="$pathcomp$d" + case "$pathcomp" in + -* ) pathcomp=./$pathcomp ;; + esac + + if test ! -d "$pathcomp"; then + echo "mkdir $pathcomp" + + mkdir "$pathcomp" || lasterr=$? + + if test ! -d "$pathcomp"; then + errstatus=$lasterr + fi + fi + + pathcomp="$pathcomp/" + done +done + +exit $errstatus + +# mkinstalldirs ends here diff --git a/darkice/tags/darkice-0_7/rpm/darkice.spec b/darkice/tags/darkice-0_7/rpm/darkice.spec new file mode 100644 index 0000000..8701f1c --- /dev/null +++ b/darkice/tags/darkice-0_7/rpm/darkice.spec @@ -0,0 +1,125 @@ +#------------------------------------------------------------------------------- +# +# Copyright (c) 2000 Tyrell Corporation. All rights reserved. +# +# Tyrell DarkIce +# +# File : darkice.spec +# Version : $Revision$ +# Author : $Author$ +# Location : $Source$ +# +# Abstract : +# +# Specification file to build RPM packages of DarkIce +# +# Copyright notice: +# +# 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. +# +#------------------------------------------------------------------------------- + +# ===================================================================== preamble +Summary : DarkIce live IceCast / ShoutCast streamer +Name: darkice +Vendor: Tyrell Hungary +Packager: Akos Maroy +Version: 0.7 +Release: 1 +Copyright: GPL +Group: Applications/Multimedia +Source: http://prdownloads.sourceforge.net/darkice/darkice-%{version}.tar.gz +URL: http://darkice.sourceforge.net/ +Provides: darkice +BuildRoot: %{_tmppath}/%{name}-%{version}-root +Prefix: /usr + +%description +DarkIce is an IceCast, IceCast2 and ShoutCast live audio streamer. It +takes audio input from a sound card, encodes it into mp3 and/or Ogg Vorbis, +and sends the mp3 stream to one or more IceCast and/or ShoutCast servers, +the Ogg Vorbis stream to one or more IceCast2 servers. + + + +# =================================================================== prep stage +%prep +%setup + + +# ================================================================== build stage +%build +%configure +make all + + +# ================================================================ install stage +%install +%makeinstall + + +# ========================================================== pre-install scripts +%pre + + +# ========================================================= post-install scripts +%post + + +# ======================================================================== clean +%clean +rm -rf $RPM_BUILD_ROOT +make clean + + +# =========================================================== main package files +%files +%defattr (-, root, root) +%doc COPYING ChangeLog README TODO +%config %{_sysconfdir}/darkice.cfg +%{_bindir}/darkice +%{_mandir}/man1/darkice.1* +%{_mandir}/man5/darkice.cfg.5* + + +# =================================================================== change log +# +# $Log$ +# Revision 1.8 2001/10/19 12:48:03 darkeye +# for new version +# +# Revision 1.7 2001/09/18 18:00:02 darkeye +# removed --enable-static configure option +# +# Revision 1.6 2001/09/18 17:35:15 darkeye +# for version 0.6 +# +# Revision 1.5 2001/09/13 05:06:41 darkeye +# removed references to SourceForget FTP sites, as they are phased out +# +# Revision 1.4 2001/09/09 12:26:33 darkeye +# updated to reflect that DarkIce is now both an IceCast and ShoutCast streamer +# +# Revision 1.3 2001/09/09 11:48:09 darkeye +# added man page darkice.cfg.5 +# +# Revision 1.2 2001/09/02 14:44:14 darkeye +# added system level configuration file +# +# Revision 1.1 2001/09/02 12:46:05 darkeye +# added RPM package creation scripts +# +# + diff --git a/darkice/tags/darkice-0_7/rpm/lame.spec b/darkice/tags/darkice-0_7/rpm/lame.spec new file mode 100644 index 0000000..0d2e538 --- /dev/null +++ b/darkice/tags/darkice-0_7/rpm/lame.spec @@ -0,0 +1,146 @@ +#------------------------------------------------------------------------------- +# +# Copyright (c) 2000 Tyrell Corporation. All rights reserved. +# +# Tyrell DarkIce +# +# File : lame.spec +# Version : $Revision$ +# Author : $Author$ +# Location : $Source$ +# +# Abstract : +# +# Specification file to build RPM packages of lame. +# Builds a proper lame executable on a RedHat 7.1 system. +# Based on the official lame RPM spec file by +# cefiar +# +# Copyright notice: +# +# 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. +# +#------------------------------------------------------------------------------- + +# ================================================================= local macros +%define name lame +%define ver 3.89 +%define quality beta +%define rel 2 +%define prefix /usr + + +# ===================================================================== preamble +Summary : LAME Ain't an MP3 Encoder +Name: %{name} +Version: %{ver}%{quality} +Release: %{rel} +Copyright: LGPL +Vendor: The LAME Project +Packager: Akos Maroy +URL: http://www.mp3dev.org/mp3/ +Group: Applications/Multimedia +Source: http://prdownloads.sourceforge.net/darkice/%{name}%{ver}%{quality}.tar.gz +BuildRoot: %{_tmppath}/%{name}-%{ver}-root +Prefix: %{prefix} +Provides: lame + +%description +LAME is an educational tool to be used for learning about MP3 encoding. The +goal of the LAME project is to use the open source model to improve the +psycho acoustics, noise shaping and speed of MP3. Another goal of the LAME +project is to use these improvements for the basis of a patent free audio +compression codec for the GNU project. + +This build is optimized for %{_target}. + +# ============================================================ devel sub-package +%package devel +Summary: Shared and static libraries for LAME. +Group: Development/Libraries +Requires: %{name} = %{version} + +%description devel +LAME is an educational tool to be used for learning about MP3 encoding. +This package contains both the shared and the static libraries from the +LAME project. + +You will also need to install the main lame package in order to install +these libraries. + +This build is optimized for %{_target}. + +# =================================================================== prep stage +%prep +%setup -n %{name}-%{ver} + + +# ================================================================== build stage +%build +export CC=gcc3 +export CFLAGS="-O9" +%configure --with-fileio=lame \ + --without-vorbis \ + --disable-gtktest \ + --enable-nasm \ + --enable-expopt=full +make + + +# ================================================================ install stage +%install +%makeinstall + + +# ======================================================================== clean +%clean +rm -rf $RPM_BUILD_ROOT +make clean + + +# =========================================================== main package files +%files +%defattr (-,root,root) +%doc LICENSE USAGE COPYING TODO README* +%doc doc/html +%{_bindir}/lame +%{_mandir}/man1/lame.1* +%{_libdir}/libmp3lame.so.* + + +# ====================================================== devel sub-package files +%files devel +%defattr (-,root,root) +%doc API HACKING STYLEGUIDE +%{_includedir}/lame/lame.h +%{_libdir}/libmp3lame.la +%{_libdir}/libmp3lame.a +%{_libdir}/libmp3lame.so + + +# =================================================================== change log +# +# $Log$ +# Revision 1.3 2001/09/13 05:06:41 darkeye +# removed references to SourceForget FTP sites, as they are phased out +# +# Revision 1.2 2001/09/09 09:06:26 darkeye +# lame RPM is now created with gcc3 and full optimizations +# +# Revision 1.1 2001/09/02 12:46:05 darkeye +# added RPM package creation scripts +# +# + diff --git a/darkice/tags/darkice-0_7/src/AudioEncoder.h b/darkice/tags/darkice-0_7/src/AudioEncoder.h new file mode 100644 index 0000000..7288968 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/AudioEncoder.h @@ -0,0 +1,402 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : AudioEncoder.h + Version : $Revision$ + Author : $Author$ + Location : $AudioEncoder$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef AUDIO_ENCODER_H +#define AUDIO_ENCODER_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Referable.h" +#include "Sink.h" +#include "AudioSource.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * An audio encoder + * + * @author $Author$ + * @version $Revision$ + */ +class AudioEncoder : public Sink, public virtual Referable +{ + private: + + /** + * Sample rate of the input. + */ + unsigned int inSampleRate; + + /** + * Number of bits per sample of the input. + */ + unsigned int inBitsPerSample; + + /** + * Number of channels of the input. + */ + unsigned int inChannel; + + /** + * Is the input big endian or little endian? + */ + bool inBigEndian; + + /** + * Bit rate of the output. (bits/sec) + */ + unsigned int outBitrate; + + /** + * Sample rate of the output. + */ + unsigned int outSampleRate; + + /** + * Number of channels of the output. + */ + unsigned int outChannel; + + /** + * Initialize the object. + * + * @param inSampleRate sample rate of the input. + * @param inBitsPerSample number of bits per sample of the input. + * @param inChannel number of channels of the input. + * @param inBigEndian shows if the input is big or little endian + * @param outBitrate bit rate of the output. + * @param outSampleRate sample rate of the output. + * @param outChannel number of channels of the output. + * @exception Exception + */ + inline void + init ( unsigned int inSampleRate, + unsigned int inBitsPerSample, + unsigned int inChannel, + bool inBigEndian, + unsigned int outBitrate, + unsigned int outSampleRate, + unsigned int outChannel ) throw ( Exception ) + { + this->inSampleRate = inSampleRate; + this->inBitsPerSample = inBitsPerSample; + this->inChannel = inChannel; + this->inBigEndian = inBigEndian; + this->outBitrate = outBitrate; + this->outSampleRate = outSampleRate; + this->outChannel = outChannel; + } + + /** + * De-iitialize the object. + * + * @exception Exception + */ + inline void + strip ( void ) throw ( Exception ) + { + } + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + AudioEncoder ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + /** + * Constructor. + * + * @param inSampleRate sample rate of the input. + * @param inBitsPerSample number of bits per sample of the input. + * @param inChannel number of channels of the input. + * @param inBigEndian shows if the input is big or little endian + * @param outBitrate bit rate of the output (bits/sec). + * @param outSampleRate sample rate of the output. + * If 0, inSampleRate is used. + * @param outChannel number of channels of the output. + * If 0, inChannel is used. + * @exception Exception + */ + inline + AudioEncoder ( unsigned int inSampleRate, + unsigned int inBitsPerSample, + unsigned int inChannel, + bool inBigEndian, + unsigned int outBitrate, + unsigned int outSampleRate = 0, + unsigned int outChannel = 0 ) + throw ( Exception ) + { + init ( inSampleRate, + inBitsPerSample, + inChannel, + inBigEndian, + outBitrate, + outSampleRate ? outSampleRate : inSampleRate, + outChannel ? outChannel : inChannel ); + } + + /** + * Constructor. + * + * @param as get input sample rate, bits per sample and channels + * from this AudioSource. + * @param outBitrate bit rate of the output (bits/sec). + * @param outSampleRate sample rate of the output. + * If 0, input sample rate is used. + * @param outChannel number of channels of the output. + * If 0, input channel is used. + * @exception Exception + */ + inline + AudioEncoder ( const AudioSource * as, + unsigned int outBitrate, + unsigned int outSampleRate = 0, + unsigned int outChannel = 0 ) + throw ( Exception) + { + init( as->getSampleRate(), + as->getBitsPerSample(), + as->getChannel(), + as->isBigEndian(), + outBitrate, + outSampleRate ? outSampleRate : as->getSampleRate(), + outChannel ? outChannel : as->getChannel() ); + } + + /** + * Copy constructor. + * + * @param encoder the AudioEncoder to copy. + */ + inline + AudioEncoder ( const AudioEncoder & encoder ) throw ( Exception ) + { + init ( encoder.inSampleRate, + encoder.inBitsPerSample, + encoder.inChannel, + encoder.inBigEndian, + encoder.outBitrate, + encoder.outSampleRate, + encoder.outChannel ); + } + + /** + * Assignment operator. + * + * @param encoder the AudioEncoder to assign this to. + * @return a reference to this AudioEncoder. + * @exception Exception + */ + inline virtual AudioEncoder & + operator= ( const AudioEncoder & encoder ) throw ( Exception ) + { + if ( this != &encoder ) { + strip(); + + init ( encoder.inSampleRate, + encoder.inBitsPerSample, + encoder.inChannel, + encoder.inBigEndian, + encoder.outBitrate, + encoder.outSampleRate, + encoder.outChannel ); + } + + return *this; + } + + + public: + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~AudioEncoder ( void ) throw ( Exception ) + { + strip(); + } + + /** + * Get the number of channels of the input. + * + * @return the number of channels of the input. + */ + inline int + getInChannel ( void ) const throw () + { + return inChannel; + } + + /** + * Tell if the input is big or little endian. + * + * @return true if the input is big endian, false if little endian. + */ + inline bool + isInBigEndian ( void ) const throw () + { + return inBigEndian; + } + + /** + * Get the sample rate of the input. + * + * @return the sample rate of the input. + */ + inline int + getInSampleRate ( void ) const throw () + { + return inSampleRate; + } + + /** + * Get the number of bits per sample of the input. + * + * @return the number of bits per sample of the input. + */ + inline int + getInBitsPerSample ( void ) const throw () + { + return inBitsPerSample; + } + + /** + * Get the number of channels of the output. + * + * @return the number of channels of the output. + */ + inline int + getOutChannel ( void ) const throw () + { + return outChannel; + } + + /** + * Get the sample rate of the output. + * + * @return the sample rate of the output. + */ + inline int + getOutSampleRate ( void ) const throw () + { + return outSampleRate; + } + + /** + * Get the bit rate of the output. (bits/sec) + * + * @return the bit rate of the output. + */ + inline int + getOutBitrate ( void ) const throw () + { + return outBitrate; + } + + /** + * Check wether encoding is in progress. + * + * @return true if encoding is in progress, false otherwise. + */ + virtual bool + isRunning ( void ) const throw () = 0; + + /** + * Start encoding. This function returns as soon as possible, + * with encoding started in the background. + * + * @return true if encoding has started, false otherwise. + * @exception Exception + */ + virtual bool + start ( void ) throw ( Exception ) = 0; + + /** + * Stop encoding. Stops the encoding running in the background. + * + * @exception Exception + */ + virtual void + stop ( void ) throw ( Exception ) = 0; +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* AUDIO_ENCODER_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.4 2001/09/18 14:57:19 darkeye + finalized Solaris port + + Revision 1.3 2001/09/14 19:31:06 darkeye + added IceCast2 / vorbis support + + Revision 1.2 2000/11/12 14:54:50 darkeye + added kdoc-style documentation comments + + Revision 1.1.1.1 2000/11/05 10:05:47 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/AudioSource.h b/darkice/tags/darkice-0_7/src/AudioSource.h new file mode 100644 index 0000000..a08f631 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/AudioSource.h @@ -0,0 +1,272 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : AudioSource.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef AUDIO_SOURCE_H +#define AUDIO_SOURCE_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Source.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * Audio data input + * + * @author $Author$ + * @version $Revision$ + */ +class AudioSource : public Source +{ + private: + + /** + * Number of channels of the audio source + * (e.g. 1 for mono, 2 for stereo, etc.) + */ + unsigned int channel; + + /** + * Samples per second (e.g. 44100 for 44.1kHz CD quality) + */ + unsigned int sampleRate; + + /** + * Bits per sample (e.g. 8 bits, 16 bits, etc.) + */ + unsigned int bitsPerSample; + + /** + * Initialize the object. + * + * @param sampleRate samples per second. + * @param bitsPerSample bits per sample. + * @param channel number of channels of the audio source. + * @exception Exception + */ + inline void + init ( unsigned int sampleRate, + unsigned int bitsPerSample, + unsigned int channel ) throw ( Exception ) + { + this->sampleRate = sampleRate; + this->bitsPerSample = bitsPerSample; + this->channel = channel; + } + + /** + * De-initialize the object. + * + * @exception Exception + */ + inline void + strip ( void ) throw ( Exception ) + { + } + + + protected: + + /** + * Constructor. + * Because all values have defaults, this is also the default + * constructor. + * + * @param sampleRate samples per second (e.g. 44100 for 44.1kHz). + * @param bitsPerSample bits per sample (e.g. 16 bits). + * @param channel number of channels of the audio source + * (e.g. 1 for mono, 2 for stereo, etc.). + * @exception Exception + */ + inline + AudioSource ( unsigned int sampleRate = 44100, + unsigned int bitsPerSample = 16, + unsigned int channel = 2 ) + throw ( Exception ) + { + init ( sampleRate, bitsPerSample, channel); + } + + /** + * Copy Constructor. + * + * @param source the object to copy. + * @exception Exception + */ + inline + AudioSource ( const AudioSource & as ) throw ( Exception ) + : Source( as ) + { + init ( as.sampleRate, as.bitsPerSample, as.channel); + } + + /** + * Assignment operator. + * + * @param as the object to assign to this one. + * @return a reference to this object. + * @exception Exception + */ + inline virtual AudioSource & + operator= ( const AudioSource & as ) throw ( Exception ) + { + if ( this != &as ) { + strip(); + Source::operator=( as ); + init ( as.sampleRate, as.bitsPerSample, as.channel); + } + + return *this; + } + + + public: + + /** + * Destructor. + * + * @exception Exception + */ + virtual inline + ~AudioSource ( void ) throw ( Exception ) + { + } + + /** + * Get the number of channels for this AudioSource. + * + * @return the number of channels. + */ + inline unsigned int + getChannel ( void ) const throw () + { + return channel; + } + + /** + * Tell if the data from this source comes in big or little endian. + * + * @return true if the data is big endian, false if little endian + */ + virtual bool + isBigEndian ( void ) const throw () = 0; + + /** + * Get the sample rate per seconds for this AudioSource. + * + * @return the sample rate per seconds. + */ + inline unsigned int + getSampleRate ( void ) const throw () + { + return sampleRate; + } + + + /** + * Get the number of bits per sample for this AudioSource. + * + * @return the number of bits per sample. + */ + inline unsigned int + getBitsPerSample ( void ) const throw () + { + return bitsPerSample; + } +}; + + +/* ================================================= external data structures */ + +/*------------------------------------------------------------------------------ + * Determine the kind of audio device based on the system + *----------------------------------------------------------------------------*/ +#if defined( HAVE_SYS_SOUNDCARD_H ) + +// we have an OSS DSP sound source device available +#define SUPPORT_OSS_DSP +#include "OssDspSource.h" +typedef class OssDspSource DspSource; + +#elif defined( HAVE_SYS_AUDIO_H ) + +// we have a Solaris DSP sound device available +#define SUPPORT_SOLARIS_DSP +#include "SolarisDspSource.h" +typedef class SolarisDspSource DspSource; + +#else + +// there was no DSP audio system found +#error No DSP audio input device found on system + +#endif + + +/* ====================================================== function prototypes */ + + + +#endif /* AUDIO_SOURCE_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.5 2001/09/18 14:57:19 darkeye + finalized Solaris port + + Revision 1.4 2001/09/11 15:05:21 darkeye + added Solaris support + + Revision 1.3 2000/11/12 13:31:40 darkeye + added kdoc-style documentation comments + + Revision 1.2 2000/11/05 17:37:24 darkeye + removed clone() functions + + Revision 1.1.1.1 2000/11/05 10:05:47 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/BufferedSink.cpp b/darkice/tags/darkice-0_7/src/BufferedSink.cpp new file mode 100644 index 0000000..b69668b --- /dev/null +++ b/darkice/tags/darkice-0_7/src/BufferedSink.cpp @@ -0,0 +1,392 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : BufferedSink.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + the buffer is filled like this: + + buffer bufferEnd + | | + +----------+--------------------------+--------------+ + |<---- valid data -------->| + outp inp + + buffer bufferEnd + | | + +----------------+--------------+--------------------+ + -- valid data -->| |--- valid data -----> + inp outp + + + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_STRING_H +#include +#else +#error need string.h +#endif + + +#include "Exception.h" +#include "BufferedSink.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Initialize the object + *----------------------------------------------------------------------------*/ +void +BufferedSink :: init ( Sink * sink, + unsigned int size, + unsigned int chunkSize ) throw ( Exception ) +{ + if ( !sink ) { + throw Exception( __FILE__, __LINE__, "no sink"); + } + + this->sink = sink; // create a reference + this->chunkSize = chunkSize ? chunkSize : 1; + this->bufferSize = size; + // make bufferSize a multiple of chunkSize + this->bufferSize -= this->bufferSize % this->chunkSize; + this->peak = 0; + this->misalignment = 0; + this->buffer = new unsigned char[bufferSize]; + this->bufferEnd = buffer + bufferSize; + this->inp = buffer; + this->outp = buffer; +} + + +/*------------------------------------------------------------------------------ + * Copy Constructor + *----------------------------------------------------------------------------*/ +BufferedSink :: BufferedSink ( const BufferedSink & buffer ) + throw ( Exception ) +{ + init( buffer.sink.get(), buffer.bufferSize, buffer.chunkSize); + + this->peak = buffer.peak; + this->misalignment = buffer.misalignment; + memcpy( this->buffer, buffer.buffer, this->bufferSize); +} + + +/*------------------------------------------------------------------------------ + * De-initalize the object + *----------------------------------------------------------------------------*/ +void +BufferedSink :: strip ( void ) throw ( Exception ) +{ + if ( isOpen() ) { + close(); + } + + sink = 0; // delete the reference + delete buffer; +} + + +/*------------------------------------------------------------------------------ + * Assignment operator + *----------------------------------------------------------------------------*/ +BufferedSink & +BufferedSink :: operator= ( const BufferedSink & buffer ) + throw ( Exception ) +{ + if ( this != &buffer ) { + strip(); + Sink::operator=( buffer ); + init( buffer.sink.get(), buffer.bufferSize, buffer.chunkSize); + + this->peak = buffer.peak; + this->misalignment = buffer.misalignment; + memcpy( this->buffer, buffer.buffer, this->bufferSize); + } + + return *this; +} + + +/*------------------------------------------------------------------------------ + * Store bufferSize bytes into the buffer + * All data is consumed. The return value is less then bufferSize only + * if the BufferedSink's internal buffer is smaller than bufferSize, + * thus can't hold that much + * The data to be stored is treated as parts with chunkSize size + * Only full chunkSize sized parts are stored + *----------------------------------------------------------------------------*/ +unsigned int +BufferedSink :: store ( const void * buffer, + unsigned int bufferSize ) throw ( Exception ) +{ + const unsigned char * buf; + unsigned int size; + unsigned int i; + unsigned char * oldInp; + + if ( !buffer ) { + throw Exception( __FILE__, __LINE__, "buffer is null"); + } + + if ( !bufferSize ) { + return 0; + } + + oldInp = inp; + buf = (const unsigned char *) buffer; + + // adjust so it is a multiple of chunkSize + bufferSize -= bufferSize % chunkSize; + + // cut the front of the supplied buffer if it wouldn't fit + if ( bufferSize > this->bufferSize ) { + size = this->bufferSize - 1; + size -= size % chunkSize; // keep it a multiple of chunkSize + buf += bufferSize - size; + } else { + size = bufferSize; + } + + // copy the data into the buffer + i = bufferEnd - inp; + if ( (i % chunkSize) != 0 ) { + throw Exception( __FILE__, __LINE__, "copy quantity not aligned", i); + } + + if ( size <= i ) { + // the place between inp and bufferEnd is + // big enough to hold the data + + memcpy( inp, buf, size); + inp = slidePointer( inp, size); + + // adjust outp, lose the data that was overwritten, if any + if ( outp > oldInp && outp <= inp ) { + outp = slidePointer( inp, chunkSize); + } + + } else { + // the place between inp and bufferEnd is not + // big enough to hold the data + // writing will take place in two turns, once from + // inp -> bufferEnd, then from buffer -> + + memcpy( inp, buf, i); + i = size - i; + if ( (i % chunkSize) != 0 ) { + throw Exception(__FILE__, __LINE__, "copy quantity not aligned", i); + } + memcpy( this->buffer, buf, i); + inp = slidePointer( this->buffer, i); + + // adjust outp, lose the data that was overwritten, if any + if ( outp <= oldInp ) { + if ( outp < inp ) { + outp = slidePointer( inp, chunkSize); + } + } else { + outp = slidePointer( inp, chunkSize); + } + } + + updatePeak(); + + if ( ((inp - this->buffer) % chunkSize) != 0 ) { + throw Exception( __FILE__, __LINE__, + "inp not aligned", inp - this->buffer); + } + if ( ((outp - this->buffer) % chunkSize) != 0 ) { + throw Exception( __FILE__, __LINE__, + "outp not aligned", outp - this->buffer); + } + + return size; +} + + +/*------------------------------------------------------------------------------ + * Write some data to the sink + * if len == 0, try to flush the buffer + *----------------------------------------------------------------------------*/ +unsigned int +BufferedSink :: write ( const void * buf, + unsigned int len ) throw ( Exception ) +{ + unsigned int length; + unsigned int soFar; + unsigned char * b = (unsigned char *) buf; + + if ( !buf ) { + throw Exception( __FILE__, __LINE__, "buf is null"); + } + + if ( !isOpen() ) { + return 0; + } + + if ( !align() ) { + return 0; + } + + // make it a multiple of chunkSize + len -= len % chunkSize; + + // try to write data from the buffer first, if any + if ( inp != outp ) { + unsigned int size = 0; + unsigned int total = 0; + + if ( outp > inp ) { + // valuable data is between outp -> bufferEnd and buffer -> inp + // try to write the outp -> bufferEnd + // the rest will be written in the next if + + size = bufferEnd - outp - 1; + size -= size % chunkSize; + soFar = 0; + + while ( outp > inp && soFar < size && sink->canWrite( 0, 0) ) { + length = sink->write( outp + soFar, size - soFar); + outp = slidePointer( outp, length); + soFar += length; + } + + total += soFar; + } + + if ( outp < inp ) { + // valuable data is between outp and inp + // if the previous if wrote all data from the end + // this part will write the rest + + size = inp - outp; + soFar = 0; + + while ( soFar < size && sink->canWrite( 0, 0) ) { + length = sink->write( outp + soFar, size - soFar); + outp = slidePointer( outp, length); + soFar += length; + } + + total += soFar; + } + + while ( (outp - buffer) % chunkSize ) { + slidePointer( outp, 1); + } + + // calulate the misalignment to chunkSize boundaries + misalignment = (chunkSize - (total % chunkSize)) % chunkSize; + } + + if ( !align() ) { + return 0; + } + + // the internal buffer is empty, try to write the fresh data + soFar = 0; + if ( inp != outp ) { + while ( soFar < len && sink->canWrite( 0, 0) ) { + soFar += sink->write( b + soFar, len - soFar); + } + } + length = soFar; + + // calulate the misalignment to chunkSize boundaries + misalignment = (chunkSize - (length % chunkSize)) % chunkSize; + + if ( length < len ) { + // if not all fresh could be written, store the remains + + store( b + length, len - length); + } + + // tell them we ate everything up to chunkSize alignment + return len; +} + + +/*------------------------------------------------------------------------------ + * Close the sink, lose all pending data + *----------------------------------------------------------------------------*/ +void +BufferedSink :: close ( void ) throw ( Exception ) +{ + if ( !isOpen() ) { + return; + } + + flush(); + sink->close(); + inp = outp = buffer; +} + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.5 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.4 2000/11/11 12:33:13 darkeye + added kdoc-style documentation + + Revision 1.3 2000/11/10 20:16:21 darkeye + first real tests with multiple streaming + + Revision 1.2 2000/11/05 14:08:27 darkeye + changed builting to an automake / autoconf environment + + Revision 1.1.1.1 2000/11/05 10:05:48 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/BufferedSink.h b/darkice/tags/darkice-0_7/src/BufferedSink.h new file mode 100644 index 0000000..7dc33b7 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/BufferedSink.h @@ -0,0 +1,412 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : BufferedSink.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef BUFFERED_SINK_H +#define BUFFERED_SINK_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Ref.h" +#include "Reporter.h" +#include "Sink.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * A Sink First-In First-Out buffer. + * This buffer can always be written to, it overwrites any + * data contained if needed. + * The class is not thread-safe. + * + * @author $Author$ + * @version $Revision$ + */ +class BufferedSink : public Sink, public virtual Reporter +{ + private: + + /** + * The buffer. + */ + unsigned char * buffer; + + /** + * The end of the buffer. + */ + unsigned char * bufferEnd; + + /** + * The size of the buffer. + */ + unsigned int bufferSize; + + /** + * The highest usage of the buffer. + */ + unsigned int peak; + + /** + * All data written to this BufferedSink is handled by chuncks + * of this size. + */ + unsigned int chunkSize; + + /** + * Number of bytes the underlying stream is misaligned with + * chunkSize. (It needs this many bytes more to be aligned.) + */ + unsigned int misalignment; + + /** + * Start of free territory in buffer. + */ + unsigned char * inp; + + /** + * Start of sensible data in buffer. + */ + unsigned char * outp; + + + /** + * The underlying Sink. + */ + Ref sink; + + /** + * Initialize the object. + * + * @param sink the Sink to attach this BufferedSink to. + * @param size the size of the internal buffer to use. + * @param chunkSize size of chunks to handle data in. + * @exception Exception + */ + void + init ( Sink * sink, + unsigned int size, + unsigned int chunkSize ) throw ( Exception ); + + /** + * De-initialize the object. + * + * @exception Exception + */ + void + strip ( void ) throw ( Exception ); + + /** + * Slide a pointer in the internal buffer by offset. If the pointer + * would reach beyond the end of the buffer, it goes wraps around. + * + * @param p the pointer to slide. + * @param offset the amount to slide with. + * @return pointer p + offset, wrapped around if needed. + */ + inline unsigned char * + slidePointer ( + unsigned char * p, + unsigned int offset ) throw () + { + p += offset; + while ( p >= bufferEnd ) { + p -= bufferSize; + } + + return p; + } + + /** + * Update the peak buffer usage indicator. + * + * @see #peak + */ + inline void + updatePeak ( void ) throw () + { + unsigned int u; + + u = outp <= inp ? inp - outp : (bufferEnd - outp) + (inp - buffer); + if ( peak < u ) { + reportEvent( 4, "BufferedSink, new peak:", peak); + reportEvent( 4, "BufferedSink, remaining:", bufferSize - peak); + peak = u; + } + } + + /** + * If the underlying Sink is misaligned on chunkSize, write as + * many 0s as needed to get it aligned. + * + * @see #misalignment + * @see #chunkSize + */ + inline bool + align ( void ) + { + char b[] = { 0 }; + + while ( misalignment ) { + if ( sink->canWrite( 0, 0) ) { + unsigned int ret; + + if ( !(ret = sink->write( b, 1)) ) { + return false; + } + --misalignment; + + } else { + return false; + } + } + + return true; + } + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + BufferedSink ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + /** + * Get the size of the buffer. + * + * @return the size of the buffer. + */ + inline unsigned int + getSize ( void ) const throw () + { + return bufferSize; + } + + /** + * Store data in the internal buffer. If there is not enough space, + * discard all in the buffer and the beginning of the supplied + * buffer if needed. + * + * @param buffer the data to store. + * @param bufferSize the amount of data to store in bytes. + * @return number of bytes really stored. + */ + unsigned int + store ( const void * buffer, + unsigned int bufferSize ) throw ( Exception ); + + + public: + + /** + * Constructor by an underlying Sink, buffer size and chunk size. + * + * @param sink the Sink to attach this BufferSink to. + * @param size the size of the buffer to use for buffering. + * @param chunkSize hanlde all data in write() as chunks of + * chunkSize + * @exception Exception + */ + inline + BufferedSink ( Sink * sink, + unsigned int size, + unsigned int chunkSize = 1 ) throw ( Exception ) + { + init( sink, size, chunkSize); + } + + /** + * Copy constructor. + * + * @param buffer the object to copy. + * @exception Exception + */ + BufferedSink ( const BufferedSink & buffer ) throw ( Exception ); + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~BufferedSink ( void ) throw ( Exception ) + { + strip(); + } + + /** + * Assignment operator. + * + * @param bs the object to assign to this one. + * @return a reference to this object. + * @exception Exception + */ + virtual BufferedSink & + operator= ( const BufferedSink & bs ) throw ( Exception ); + + /** + * Get the peak usage of the internal buffer. + * + * @return the peak usage of the internal buffer. + */ + inline unsigned int + getPeak ( void ) const throw () + { + return peak; + } + + /** + * Open the BufferedSink. Opens the underlying Sink. + * + * @return true if opening was successful, false otherwise. + * @exception Exception + */ + inline virtual bool + open ( void ) throw ( Exception ) + { + return sink->open(); + } + + /** + * Check if a BufferedSink is open. + * + * @return true if the BufferedSink is open, false otherwise. + */ + inline virtual bool + isOpen ( void ) const throw () + { + return sink->isOpen(); + } + + /** + * Check if the BufferedSink is ready to accept data. + * Always returns true immediately. + * + * @param sec the maximum seconds to block. + * @param usec micro seconds to block after the full seconds. + * @return true + * @exception Exception + */ + inline virtual bool + canWrite ( unsigned int sec, + unsigned int usec ) throw ( Exception ) + { + return true; + } + + /** + * Write data to the BufferedSink. + * Always reads the maximum number of chunkSize chunks buf + * holds. If the data can not be written to the underlying + * stream, it is buffered. If the buffer overflows, the oldest + * data is discarded. + * + * @param buf the data to write. + * @param len number of bytes to write from buf. + * @return the number of bytes written (may be less than len). + * @exception Exception + */ + virtual unsigned int + write ( const void * buf, + unsigned int len ) throw ( Exception ); + + /** + * Flush all data that was written to the BufferedSink to the + * underlying Sink. + * + * @exception Exception + */ + inline virtual void + flush ( void ) throw ( Exception ) + { + unsigned char b[0]; + + write( b, 0); + } + + /** + * Close the BufferedSink. Closes the underlying Sink. + * + * @exception Exception + */ + virtual void + close ( void ) throw ( Exception ); +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* BUFFERED_SINK_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.5 2000/11/15 18:08:42 darkeye + added multiple verbosity-level event reporting and verbosity command + line option + + Revision 1.4 2000/11/11 12:33:13 darkeye + added kdoc-style documentation + + Revision 1.3 2000/11/10 20:16:21 darkeye + first real tests with multiple streaming + + Revision 1.2 2000/11/05 17:37:24 darkeye + removed clone() functions + + Revision 1.1.1.1 2000/11/05 10:05:48 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/CastSink.cpp b/darkice/tags/darkice-0_7/src/CastSink.cpp new file mode 100644 index 0000000..4a916ec --- /dev/null +++ b/darkice/tags/darkice-0_7/src/CastSink.cpp @@ -0,0 +1,151 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : CastSink.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#include "Util.h" +#include "Exception.h" +#include "CastSink.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Initialize the object + *----------------------------------------------------------------------------*/ +void +CastSink :: init ( TcpSocket * socket, + const char * password, + unsigned int bitRate, + const char * name, + const char * url, + const char * genre, + bool isPublic, + unsigned int bufferDuration ) + throw ( Exception ) +{ + this->socket = socket; + this->password = Util::strDup( password); + this->bitRate = bitRate; + this->name = name ? Util::strDup( name) : 0; + this->url = url ? Util::strDup( url) : 0; + this->genre = genre ? Util::strDup( genre) : 0; + this->isPublic = isPublic; + this->bufferDuration = bufferDuration; + + bufferedSink = new BufferedSink( socket, + (bitRate * 1024 / 8) * bufferDuration); + +} + + +/*------------------------------------------------------------------------------ + * De-initialize the object + *----------------------------------------------------------------------------*/ +void +CastSink :: strip ( void ) throw ( Exception ) +{ + if ( isOpen() ) { + close(); + } + + delete[] password; + if ( name ) { + delete[] name; + } + if ( url ) { + delete[] url; + } + if ( genre ) { + delete[] genre; + } +} + + +/*------------------------------------------------------------------------------ + * Open the connection + *----------------------------------------------------------------------------*/ +bool +CastSink :: open ( void ) throw ( Exception ) +{ + if ( isOpen() ) { + return false; + } + + if ( !bufferedSink->open() ) { + return false; + } + + if ( !sendLogin() ) { + close(); + return false; + } + + return true; +} + + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.5 2001/09/09 11:27:31 darkeye + added support for ShoutCast servers + + Revision 1.4 2001/08/29 21:08:30 darkeye + made some description options in the darkice config file optional + + Revision 1.3 2000/11/12 14:54:50 darkeye + added kdoc-style documentation comments + + Revision 1.2 2000/11/10 20:14:11 darkeye + added support for remote dump file + + Revision 1.1.1.1 2000/11/05 10:05:48 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/CastSink.h b/darkice/tags/darkice-0_7/src/CastSink.h new file mode 100644 index 0000000..817e3fd --- /dev/null +++ b/darkice/tags/darkice-0_7/src/CastSink.h @@ -0,0 +1,470 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : CastSink.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef CAST_SINK_H +#define CAST_SINK_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Ref.h" +#include "Sink.h" +#include "TcpSocket.h" +#include "BufferedSink.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * Data output to a ShoutCast / IceCast / etc. server + * This is an abstract class. A subclass should override at least + * the sendLogin() function. + * + * @author $Author$ + * @version $Revision$ + */ +class CastSink : public Sink +{ + private: + + /** + * The socket connection to the server. + */ + Ref socket; + + /** + * The BufferedSink encapsulating the socket connection to the server. + */ + Ref bufferedSink; + + /** + * Duration of the BufferedSink buffer in seconds. + */ + unsigned int bufferDuration; + + /** + * Password to the server. + */ + char * password; + + /** + * Name of the stream. + */ + char * name; + + /** + * URL associated with the stream. + */ + char * url; + + /** + * Genre of the stream. + */ + char * genre; + + /** + * Bitrate of the stream (e.g. mp3 bitrate). + */ + unsigned int bitRate; + + /** + * Is the stream public? + */ + bool isPublic; + + /** + * Initalize the object. + * + * @param socket socket connection to the server. + * @param password password to the server. + * @param name name of the stream. + * @param url URL associated with the stream. + * @param genre genre of the stream. + * @param bitRate bitrate of the stream (e.g. mp3 bitrate). + * @param isPublic is the stream public? + * @param bufferDuration duration of the BufferedSink buffer + * in seconds. + * @exception Exception + */ + void + init ( TcpSocket * socket, + const char * password, + unsigned int bitRate, + const char * name, + const char * url, + const char * genre, + bool isPublic, + unsigned int bufferDuration ) + throw ( Exception ); + + /** + * De-initalize the object. + * + * @exception Exception + */ + void + strip ( void ) throw ( Exception ); + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + CastSink ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + /** + * Log in to the server using the socket avialable. + * + * @return true if login was successful, false otherwise. + * @exception Exception + */ + virtual bool + sendLogin ( void ) throw ( Exception ) = 0; + + /** + * Get the Sink underneath this CastSink. + * + * @return pointer to the Sink underneath this CastSink. + */ + inline Sink * + getSink ( void ) const throw () + { + return bufferedSink.get(); + } + + /** + * Get the TcpSocket underneath this CastSink. + * + * @return pointer to the TcpSocket underneath this CastSink. + */ + inline TcpSocket * + getSocket ( void ) const throw () + { + return socket.get(); + } + + + public: + + /** + * Constructor. + * + * @param socket socket connection to the server. + * @param password password to the server. + * @param name name of the stream. + * @param url URL associated with the stream. + * @param genre genre of the stream. + * @param bitRate bitrate of the stream (e.g. mp3 bitrate). + * @param isPublic is the stream public? + * @param bufferDuration duration of the BufferedSink buffer + * in seconds. + * @exception Exception + */ + inline + CastSink ( TcpSocket * socket, + const char * password, + unsigned int bitRate, + const char * name = 0, + const char * url = 0, + const char * genre = 0, + bool isPublic = false, + unsigned int bufferDuration = 10 ) + throw ( Exception ) + { + init( socket, + password, + bitRate, + name, + url, + genre, + isPublic, + bufferDuration ); + } + + /** + * Copy constructor. + * + * @param cs the CastSink to copy. + */ + inline + CastSink( const CastSink & cs ) throw ( Exception ) + : Sink( cs ) + { + init( cs.socket.get(), + cs.password, + cs.bitRate, + cs.name, + cs.url, + cs.genre, + cs.isPublic, + cs.bufferDuration ); + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~CastSink( void ) throw ( Exception ) + { + strip(); + } + + /** + * Assignment operator. + * + * @param cs the CastSink to assign this to. + * @return a reference to this CastSink. + * @exception Exception + */ + inline virtual CastSink & + operator= ( const CastSink & cs ) throw ( Exception ) + { + if ( this != &cs ) { + strip(); + Sink::operator=( cs ); + init( cs.socket.get(), + cs.password, + cs.bitRate, + cs.name, + cs.url, + cs.genre, + cs.isPublic, + cs.bufferDuration ); + } + return *this; + } + + /** + * Open the CastSink. + * Logs in to the server. + * + * @return true if opening was successfull, false otherwise. + * @exception Exception + */ + virtual bool + open ( void ) throw ( Exception ); + + /** + * Check if the CastSink is open. + * + * @return true if the CastSink is open, false otherwise. + */ + inline virtual bool + isOpen ( void ) const throw () + { + return bufferedSink->isOpen(); + } + + /** + * Check if the CastSink is ready to accept data. + * Blocks until the specified time for data to be available. + * + * @param sec the maximum seconds to block. + * @param usec micro seconds to block after the full seconds. + * @return true if the CastSink is ready to accept data, + * false otherwise. + * @exception Exception + */ + inline virtual bool + canWrite ( unsigned int sec, + unsigned int usec ) throw ( Exception ) + { + return getSink()->canWrite( sec, usec); + } + + /** + * Write data to the CastSink. + * + * @param buf the data to write. + * @param len number of bytes to write from buf. + * @return the number of bytes written (may be less than len). + * @exception Exception + */ + inline virtual unsigned int + write ( const void * buf, + unsigned int len ) throw ( Exception ) + { + return getSink()->write( buf, len); + } + + /** + * Flush all data that was written to the CastSink to the server. + * + * @exception Exception + */ + inline virtual void + flush ( void ) throw ( Exception ) + { + return getSink()->flush(); + } + + /** + * Close the CastSink. + * + * @exception Exception + */ + inline virtual void + close ( void ) throw ( Exception ) + { + return getSink()->close(); + } + + /** + * Get the password to the server. + * + * @return the password to the server. + */ + inline const char * + getPassword ( void ) const throw () + { + return password; + } + + /** + * Get the name of the stream. + * + * @return the name of the stream. + */ + inline const char * + getName ( void ) const throw () + { + return name; + } + + /** + * Get the URL associated with the stream. + * + * @return the URL associated with the stream. + */ + inline const char * + getUrl ( void ) const throw () + { + return url; + } + + /** + * Get the genre of the stream. + * + * @return the genre of the stream. + */ + inline const char * + getGenre ( void ) const throw () + { + return genre; + } + + /** + * Get the bitrate of the stream (e.g. mp3 bitrate). + * + * @return the bitrate of the stream (e.g. mp3 bitrate). + */ + inline unsigned int + getBitRate ( void ) const throw () + { + return bitRate; + } + + /** + * Get wether this stream is public. + * + * @return true if the stream is public, false otherwise. + */ + inline bool + getIsPublic ( void ) const throw () + { + return isPublic; + } + + /** + * Get the duration of the BufferedSink buffer in seconds. + * + * @return the the duration of the BufferedSink buffer in seconds. + */ + inline unsigned int + getBufferDuration ( void ) const throw () + { + return bufferDuration; + } +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* CAST_SINK_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.6 2001/09/09 11:27:31 darkeye + added support for ShoutCast servers + + Revision 1.5 2001/08/29 21:08:30 darkeye + made some description options in the darkice config file optional + + Revision 1.4 2000/11/12 14:54:50 darkeye + added kdoc-style documentation comments + + Revision 1.3 2000/11/10 20:14:11 darkeye + added support for remote dump file + + Revision 1.2 2000/11/05 17:37:24 darkeye + removed clone() functions + + Revision 1.1.1.1 2000/11/05 10:05:48 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Config.cpp b/darkice/tags/darkice-0_7/src/Config.cpp new file mode 100644 index 0000000..a60d433 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Config.cpp @@ -0,0 +1,203 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell Config + + File : Config.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include + +#include + + +#include "Config.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/*------------------------------------------------------------------------------ + * Max line size + *----------------------------------------------------------------------------*/ +#define LINE_SIZE 256 + + +/*------------------------------------------------------------------------------ + * string containing all white space characters + *----------------------------------------------------------------------------*/ +#define WHITE_SPACE_STR " \t" + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Get a value for a key + *----------------------------------------------------------------------------*/ +const ConfigSection * +Config :: get ( const char * key ) const throw ( Exception ) +{ + if ( !key ) { + throw Exception( __FILE__, __LINE__, "no key"); + } + + TableType::const_iterator it = table.find( key); + if ( it == table.end() ) { + return 0; + } + return &(it->second); +} + + +/*------------------------------------------------------------------------------ + * Add a configuration line + *----------------------------------------------------------------------------*/ +bool +Config :: addLine ( const char * line ) throw ( Exception ) +{ + if ( !line ) { + throw Exception( __FILE__, __LINE__, "no line"); + } + + std::string::size_type ix; + std::string str( line); + + /* delete everything after the first # */ + if ( (ix = str.find( '#')) != str.npos ) { + str.erase( ix); + } + /* eat up all white space from the front */ + if ( (ix = str.find_first_not_of( WHITE_SPACE_STR)) != str.npos ) { + str.erase( 0, ix); + } + /* eat up all white space from the end */ + if ( (ix = str.find_last_not_of( WHITE_SPACE_STR)) != str.npos ) { + str.erase( ix + 1); + } + + if ( !str.length() ) { + return true; + } + if ( str[0] == '[' && str[str.size()-1] == ']' ) { + // a new section starts + + std::string section( str, 1, str.size()-2); + ConfigSection cSection; + std::pair + element( section, cSection); + std::pair res; + + res = table.insert( element); + + currentSection = section; + return res.second; + } else { + // it's a line for the current section + + TableType::iterator it = table.find( currentSection); + if ( it == table.end() ) { + throw Exception( __FILE__, __LINE__, "no current section"); + } + + return it->second.addLine( line); + } +} + + +/*------------------------------------------------------------------------------ + * Add a configuration line + *----------------------------------------------------------------------------*/ +void +Config :: read ( istream & is ) throw ( Exception ) +{ + char line[LINE_SIZE]; + unsigned int num; + + for ( num = 0; !is.fail() && !is.eof(); ++num ) { + is.getline( line, LINE_SIZE); + if ( is.eof() ) { + break; + } else if ( is.fail() ) { + throw Exception( __FILE__, __LINE__, "line too long", num); + } + + addLine( line); + } +} + + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.6 2001/10/19 09:20:09 darkeye + config file now may contain tabs also as white space + + Revision 1.5 2001/09/09 11:26:43 darkeye + full line comments skipped earlier: commens allowed before the first secion + + Revision 1.4 2001/09/05 20:11:15 darkeye + removed dependency on locally stored SGI STL header files + now compiler-supplied C++ library STL header files are used + compiles under GNU C++ 3 + hash_map (an SGI extension to STL) replaced with map + std:: namespace prefix added to all STL class references + + Revision 1.3 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.2 2000/11/13 18:46:50 darkeye + added kdoc-style documentation comments + + Revision 1.1 2000/11/08 17:29:50 darkeye + added configuration file reader + + Revision 1.2 2000/11/05 14:08:27 darkeye + changed builting to an automake / autoconf environment + + Revision 1.1.1.1 2000/11/05 10:05:49 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Config.h b/darkice/tags/darkice-0_7/src/Config.h new file mode 100644 index 0000000..d59922d --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Config.h @@ -0,0 +1,237 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell Config + + File : Config.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef CONFIG_H +#define CONFIG_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include +#include + +#include + +#include "Referable.h" +#include "ConfigSection.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * A configuration file representation. The file is of the syntax: + * + *
+ *  [section1]
+ *  # this is a whole line comment
+ *  key = value
+ *  an ugly key name = long value    # this end is a comment too
+ *
+ *  [section2]
+ *  # this is a whole line comment in section 2
+ *  key = value
+ *  an ugly key name = long value    # this end is a comment too
+ *  
+ * + * also empty lines are ignored and all white space is removed + * from the front and end of keys / values + * + * Knwon problem: you can't use '#' in any part of a key / value pair + * + * @author $Author$ + * @version $Revision$ + */ +class Config : public virtual Referable +{ + private: + + /** + * Type declaration of the hash table type. + */ + typedef std::map TableType; + + /** + * Hash table holding the configuration sections. + * + * @see ConfigSection + */ + TableType table; + + /** + * Hash table holding the configuration sections. + * + * @see ConfigSection + */ + std::string currentSection; + + + protected: + + + public: + + /** + * Default constructor. + * + * @exception Exception + */ + inline + Config ( void ) throw ( Exception ) + { + } + + /** + * Constructor based on an input stream. + * + * @param is configuration will be read from this input stream + * until end of stream is reached. + * @exception Exception + */ + inline + Config ( istream & is ) throw ( Exception ) + { + read( is ); + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~Config ( void ) throw ( Exception ) + { + } + + +/* TODO + + inline + Config ( const Config & di ) throw ( Exception ) + { + } + + + inline Config & + operator= ( const Config * di ) throw ( Exception ) + { + } +*/ + + /** + * Delete the configuration information stored in the object. + * Resets the object to a clean state. + * + * @exception Exception + */ + inline virtual void + reset ( void ) throw ( Exception ) + { + table.clear(); + currentSection = ""; + } + + /** + * Read a line of confiugration information. + * + * @param line the line to read. + * @return true if the line was correct, false otherwise. + * @exception Exception + */ + virtual bool + addLine ( const char * line ) throw ( Exception ); + + /** + * Read a line of confiugration information. + * + * @param line the line to read. + * @return true if the line was correct, false otherwise. + * @exception Exception + */ + virtual void + read ( istream & is ) throw ( Exception ); + + /** + * Get a ConfigSection by name. + * + * @param key the name of the ConfigSection + * @return the ConfigSection requested, or NULL if it doesn't exists. + * @exception Exception + */ + virtual const ConfigSection * + get ( const char * key ) const throw ( Exception ); +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* CONFIG_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.4 2001/09/05 20:11:15 darkeye + removed dependency on locally stored SGI STL header files + now compiler-supplied C++ library STL header files are used + compiles under GNU C++ 3 + hash_map (an SGI extension to STL) replaced with map + std:: namespace prefix added to all STL class references + + Revision 1.3 2000/11/13 18:46:50 darkeye + added kdoc-style documentation comments + + Revision 1.2 2000/11/09 22:07:19 darkeye + added constructor with istream + + Revision 1.1 2000/11/08 17:29:50 darkeye + added configuration file reader + + Revision 1.1.1.1 2000/11/05 10:05:50 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/ConfigSection.cpp b/darkice/tags/darkice-0_7/src/ConfigSection.cpp new file mode 100644 index 0000000..28effd6 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/ConfigSection.cpp @@ -0,0 +1,213 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell ConfigSection + + File : ConfigSection.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include + +#include + + +#include "ConfigSection.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/*------------------------------------------------------------------------------ + * string containing all white space characters + *----------------------------------------------------------------------------*/ +#define WHITE_SPACE_STR " \t" + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Add a key / value pair + *----------------------------------------------------------------------------*/ +bool +ConfigSection :: add ( const char * key, + const char * value ) throw ( Exception ) +{ + if ( !key || !value ) { + throw Exception( __FILE__, __LINE__, "no key or value"); + } + + std::pair element( key, value); + std::pair res; + + res = table.insert( element); + + return res.second; +} + + +/*------------------------------------------------------------------------------ + * Get a value for a key + *----------------------------------------------------------------------------*/ +const char * +ConfigSection :: get ( const char * key ) const throw ( Exception ) +{ + if ( !key ) { + throw Exception( __FILE__, __LINE__, "no key"); + } + + TableType::const_iterator it = table.find( key); + if ( it == table.end() ) { + return 0; + } + return it->second.c_str(); +} + + +/*------------------------------------------------------------------------------ + * Get a value for a key, in the key does not exist, throw an exception + *----------------------------------------------------------------------------*/ +const char * +ConfigSection :: getForSure ( const char * key, + const char * message1 = 0, + const char * message2 = 0, + int code = 0 ) const + throw ( Exception ) +{ + const char * value; + + if ( !(value = get( key)) ) { + throw Exception( __FILE__, __LINE__, key, message1, message2, code); + } + + return value; +} + + +/*------------------------------------------------------------------------------ + * Add a configuration line + *----------------------------------------------------------------------------*/ +bool +ConfigSection :: addLine ( const char * line ) throw ( Exception ) +{ + if ( !line ) { + throw Exception( __FILE__, __LINE__, "no line"); + } + + std::string::size_type ix; + std::string str( line); + + /* delete everything after the first # */ + if ( (ix = str.find( '#')) != str.npos ) { + str.erase( ix); + } + /* eat up all white space from the front */ + if ( (ix = str.find_first_not_of( WHITE_SPACE_STR)) != str.npos ) { + str.erase( 0, ix); + } + /* eat up all white space from the end */ + if ( (ix = str.find_last_not_of( WHITE_SPACE_STR)) != str.npos ) { + str.erase( ix + 1); + } + if ( !str.length() ) { + return true; + } + + /* find the '=' delimiter between key and value */ + if ( (ix = str.find( '=')) == str.npos ) { + return false; + } + + std::string key( str, 0, ix); + std::string value( str, ix + 1); + + /* eat up all white space from the front of value */ + if ( (ix = value.find_first_not_of( WHITE_SPACE_STR)) != value.npos ) { + value.erase( 0, ix); + } + /* eat up all white space from the end of key */ + if ( (ix = key.find_last_not_of( WHITE_SPACE_STR)) != key.npos ) { + key.erase( ix + 1); + } + + /* now add the new key / value pair */ + return add( key.c_str(), value.c_str()); +} + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.7 2001/10/19 09:20:09 darkeye + config file now may contain tabs also as white space + + Revision 1.6 2001/09/09 11:26:43 darkeye + full line comments skipped earlier: commens allowed before the first secion + + Revision 1.5 2001/09/05 20:11:15 darkeye + removed dependency on locally stored SGI STL header files + now compiler-supplied C++ library STL header files are used + compiles under GNU C++ 3 + hash_map (an SGI extension to STL) replaced with map + std:: namespace prefix added to all STL class references + + Revision 1.4 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.3 2000/11/13 18:46:50 darkeye + added kdoc-style documentation comments + + Revision 1.2 2000/11/09 22:08:17 darkeye + added function getForSure + + Revision 1.1 2000/11/08 17:29:50 darkeye + added configuration file reader + + Revision 1.2 2000/11/05 14:08:27 darkeye + changed builting to an automake / autoconf environment + + Revision 1.1.1.1 2000/11/05 10:05:49 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/ConfigSection.h b/darkice/tags/darkice-0_7/src/ConfigSection.h new file mode 100644 index 0000000..a20dc47 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/ConfigSection.h @@ -0,0 +1,212 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell ConfigSection + + File : ConfigSection.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef CONFIG_SECTION_H +#define CONFIG_SECTION_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include +#include + +#include "Referable.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * A configuration file representation. The file is of the syntax: + * + *
+ *  # this is a whole line comment
+ *  key = value
+ *  an ugly key name = long value    # this end is a comment too
+ *  
+ * + * also empty lines are ignored and all white space is removed + * from the front and end of keys / values + * + * Knwon problem: you can't use '#' in any part of a key / value pair + * + * @author $Author$ + * @version $Revision$ + */ +class ConfigSection : public virtual Referable +{ + private: + + /** + * Type of the hash table used in this class. + */ + typedef std::map TableType; + + /** + * Hash table holding the configuration information. + */ + TableType table; + + + protected: + + + public: + + /** + * Default constructor. + * + * @exception Exception + */ + inline + ConfigSection ( void ) throw ( Exception ) + { + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~ConfigSection ( void ) throw ( Exception ) + { + } + + +/* TODO + + inline + ConfigSection ( const ConfigSection & di ) throw ( Exception ) + { + } + + + inline ConfigSection & + operator= ( const ConfigSection * di ) throw ( Exception ) + { + } +*/ + + /** + * Add a key / value pair to the configuration information. + * + * @param key the key to add the value by + * @param value the value to add for the key + * @return true if adding was successful, false otherwise + * @exception Exception + */ + virtual bool + add ( const char * key, + const char * value ) throw ( Exception ); + + /** + * Get a value for a key. + * + * @param key the key to get the value for + * @return the value for the key, or NULL if the key doesn't exist. + * @exception Exception + */ + virtual const char * + get ( const char * key ) const throw ( Exception ); + + /** + * Get a value for a key, or throw an Exception. + * + * @param key the key to get the value for + * @param message1 message part 1 of the Exception to be thrown. + * @param message2 message part 2 of the Exception to be thrown. + * @param code error code of the Exception to be thrown. + * @return the value for the key. The return value is never NULL. + * @exception Exception + */ + virtual const char * + getForSure ( const char * key, + const char * message1 = 0, + const char * message2 = 0, + int code = 0 ) const + throw ( Exception ); + + /** + * Add a line of configuration information. + * + * @param line the line to add. + * @return true if a new key was added, false otherwise. + * @exception Exception + */ + virtual bool + addLine ( const char * line ) throw ( Exception ); +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* CONFIG_SECTION_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.4 2001/09/05 20:11:15 darkeye + removed dependency on locally stored SGI STL header files + now compiler-supplied C++ library STL header files are used + compiles under GNU C++ 3 + hash_map (an SGI extension to STL) replaced with map + std:: namespace prefix added to all STL class references + + Revision 1.3 2000/11/13 18:46:50 darkeye + added kdoc-style documentation comments + + Revision 1.2 2000/11/09 22:08:17 darkeye + added function getForSure + + Revision 1.1 2000/11/08 17:29:50 darkeye + added configuration file reader + + Revision 1.1.1.1 2000/11/05 10:05:50 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Connector.cpp b/darkice/tags/darkice-0_7/src/Connector.cpp new file mode 100644 index 0000000..95d38ef --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Connector.cpp @@ -0,0 +1,359 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : Connector.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#include "Exception.h" +#include "Connector.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Initialize the object + *----------------------------------------------------------------------------*/ +void +Connector :: init ( Source * source ) throw ( Exception ) +{ + this->source = source; + this->sinks = 0; + this->numSinks = 0; +} + + +/*------------------------------------------------------------------------------ + * De-initialize the object + *----------------------------------------------------------------------------*/ +void +Connector :: strip ( void ) throw ( Exception ) +{ + source = 0; + + if ( sinks ) { + unsigned int u; + + for ( u = 0; u < numSinks; ++u ) { + sinks[u] = 0; + } + + delete[] sinks; + } +} + + +/*------------------------------------------------------------------------------ + * Constructor + *----------------------------------------------------------------------------*/ +Connector :: Connector ( const Connector & connector ) throw ( Exception ) +{ + unsigned int u; + + init( connector.source.get()); + + for ( u = 0; u < connector.numSinks; ++u ) { + attach( connector.sinks[u].get() ); + } +} + + +/*------------------------------------------------------------------------------ + * Assignment operator + *----------------------------------------------------------------------------*/ +Connector & +Connector :: operator= ( const Connector & connector ) throw ( Exception ) +{ + if ( this != &connector ) { + unsigned int u; + + /* first free everything */ + strip(); + + /* then fill in */ + init( connector.source.get() ); + + for ( u = 0; u < connector.numSinks; ++u ) { + attach( connector.sinks[u].get() ); + } + } + + return *this; +} + + +/*------------------------------------------------------------------------------ + * Attach a sink to the connector + *----------------------------------------------------------------------------*/ +void +Connector :: attach ( Sink * sink ) throw ( Exception ) +{ + if ( !sinks ) { + + numSinks = 1; + sinks = new Ref[1]; + sinks[0] = sink; + + } else { + + unsigned int u; + Ref * s = new Ref[numSinks + 1]; + + for ( u = 0; u < numSinks; ++u ) { + s[u] = sinks[u].get(); + } + + s[numSinks] = sink; + delete[] sinks; + sinks = s; + ++numSinks; + } +} + + +/*------------------------------------------------------------------------------ + * Detach a sink to the connector + *----------------------------------------------------------------------------*/ +bool +Connector :: detach ( Sink * sink ) throw ( Exception ) +{ + if ( numSinks == 0 ) { + + return false; + + } else if ( numSinks == 1 ) { + + sinks[0] = 0; + delete[] sinks; + sinks = 0; + + return true; + + } else { + + unsigned int u; + unsigned int v; + unsigned int ix; + Ref * s; + + ix = numSinks; + for ( u = 0; u < numSinks; ++u ) { + + if ( sinks[u].get() == sink ) { + ix = u; + break; + } + } + + if ( ix == numSinks ) { + return false; + } + + s = new Ref[numSinks - 1]; + for ( u = 0, v = 0; u < numSinks; ++u ) { + + if ( u != ix ) { + s[v++] = sinks[u]; + } + } + + sinks[ix] = 0; + delete[] sinks; + sinks = s; + --numSinks; + + return true; + } +} + + +/*------------------------------------------------------------------------------ + * Open the source and all the sinks if needed + *----------------------------------------------------------------------------*/ +bool +Connector :: open ( void ) throw ( Exception ) +{ + unsigned int u; + + if ( !source->isOpen() ) { + if ( !source->open() ) { + return false; + } + } + + for ( u = 0; u < numSinks; ++u ) { + if ( !sinks[u]->isOpen() ) { + if ( !sinks[u]->open() ) { + break; + } + } + } + + /* if not all could be opened, close those that were */ + if ( u < numSinks ) { + unsigned int v; + + for ( v = 0; v < u; ++v ) { + sinks[v]->close(); + } + + source->close(); + + return false; + } + + return true; +} + + +/*------------------------------------------------------------------------------ + * Transfer some data from the source to the sink + *----------------------------------------------------------------------------*/ +unsigned int +Connector :: transfer ( unsigned long bytes, + unsigned int bufSize, + unsigned int sec, + unsigned int usec ) throw ( Exception ) +{ + unsigned int u; + unsigned long b; + unsigned char buf[bufSize]; + + if ( numSinks == 0 ) { + return 0; + } + + if ( bufSize == 0 ) { + return 0; + } + + reportEvent( 6, "Connector :: tranfer, bytes", bytes); + + for ( b = 0; !bytes || b < bytes; ) { + unsigned int d = 0; + unsigned int e = 0; + + if ( source->canRead( sec, usec) ) { + d = source->read( buf, bufSize); + + /* check for EOF */ + if ( d == 0 ) { + reportEvent( 3, "Connector :: transfer, EOF"); + break; + } + + for ( u = 0; u < numSinks; ++u ) { + + if ( sinks[u]->canWrite( sec, usec) ) { + e = sinks[u]->write( buf, d); + } else { + sinks[u]->close(); + detach( sinks[u].get() ); + /* with the call to detach, numSinks gets 1 lower, + * and the next sink comes to sinks[u] */ + --u; + + reportEvent( 5, + "Connector :: transfer, sink removed, remaining", u); + + if ( numSinks == 0 ) { + reportEvent( 4, "Connector :: transfer, no more sinks"); + break; + } + } + } + + b += d; + } else { + reportEvent( 3, "Connector :: transfer, can't read"); + break; + } + } + + return b; +} + + +/*------------------------------------------------------------------------------ + * Close the source and all the sinks if needed + *----------------------------------------------------------------------------*/ +void +Connector :: close ( void ) throw ( Exception ) +{ + unsigned int u; + + source->close(); + for ( u = 0; u < numSinks; ++u ) { + sinks[u]->close(); + } +} + + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.6 2001/08/26 20:44:30 darkeye + removed external command-line encoder support + replaced it with a shared-object support for lame with the possibility + of static linkage + + Revision 1.5 2001/08/26 08:43:13 darkeye + added support for unlimited time encoding + + Revision 1.4 2000/11/15 18:37:37 darkeye + changed the transferable number of bytes to unsigned long + + Revision 1.3 2000/11/15 18:08:43 darkeye + added multiple verbosity-level event reporting and verbosity command + line option + + Revision 1.2 2000/11/13 18:46:50 darkeye + added kdoc-style documentation comments + + Revision 1.1.1.1 2000/11/05 10:05:49 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Connector.h b/darkice/tags/darkice-0_7/src/Connector.h new file mode 100644 index 0000000..903e999 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Connector.h @@ -0,0 +1,282 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : Connector.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef CONNECTOR_H +#define CONNECTOR_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Referable.h" +#include "Ref.h" +#include "Reporter.h" +#include "Source.h" +#include "Sink.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * Connects a source to one or more sinks. + * + * @author $Author$ + * @version $Revision$ + */ +class Connector : public virtual Referable, public virtual Reporter +{ + private: + + /** + * The source to read from. + */ + Ref source; + + /** + * The sinks to connect the source to. + */ + Ref * sinks; + + /** + * Total number of sinks. + */ + unsigned int numSinks; + + /** + * Initialize the object. + * + * @param source the source to read from. + * @exception Exception + */ + void + init ( Source * source ) throw ( Exception ); + + /** + * De-initialize the object. + * + * @exception Exception + */ + void + strip ( void ) throw ( Exception ); + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + Connector ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + + public: + + /** + * Constructor based on a Source. + * + * @param source the source to connect to the sinks. + * @exception Exception + */ + inline + Connector ( Source * source ) throw ( Exception ) + { + init( source); + } + + /** + * Constructor based on a Source and a Sink. + * + * @param source the source to connect to the sinks. + * @param sink a sink to connect to the source. + * @exception Exception + */ + inline + Connector ( Source * source, + Sink * sink ) throw ( Exception ) + { + init( source); + attach( sink); + } + + /** + * Copy constructor. + * + * @param connector the object to copy. + * @exception Exception + */ + Connector ( const Connector & connector ) throw ( Exception ); + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~Connector( void ) throw ( Exception ) + { + strip(); + } + + /** + * Assignment operator. + * + * @param connector the object to assign to this one. + * @return a reference to this object. + * @exception Exception + */ + virtual Connector & + operator= ( const Connector & connector ) throw ( Exception ); + + /** + * Get the number of Sinks in the Connector. + * + * @return the number of Sinks in the Connector. + * @exception Exception + */ + inline unsigned int + getNumSinks ( void ) const throw () + { + return numSinks; + } + + /** + * Attach a Sink to the Source of this Connector. + * + * @param sink the Sink to attach. + * @exception Exception + */ + void + attach ( Sink * sink ) throw ( Exception ); + + /** + * Detach an already attached Sink from the Source of this Connector. + * + * @param sink the Sink to detach. + * @return true if the detachment was successful, false otherwise. + * @exception Exception + */ + bool + detach ( Sink * sink ) throw ( Exception ); + + /** + * Open the connector. Opens the Source and the Sinks if necessary. + * + * @return true if opening was successful, false otherwise. + * @exception Exception + */ + bool + open ( void ) throw ( Exception ); + + /** + * Transfer a given amount of data from the Source to all the + * Sinks attached. + * If an attached Sink closes or encounteres an error during the + * process, it is detached and the function carries on with the + * rest of the Sinks. If no Sinks remain, or an error is encountered + * with the Source, the function returns prematurely. + * + * @param bytes the amount of data to transfer, in bytes. + * If 0, transfer forever. + * @param bufSize the size of the buffer to use for transfering. + * This amount of data is read from the Source and + * written to each Sink on each turn. + * @param sec the number of seconds to wait for the Source to have + * data available in each turn, and the number of seconds + * to wait for the Sinks to accept data. + * @param usec the number of micros seconds to wait for the Source to + * have data available in each turn, and the number of + * micro seconds to wait for the Sinks to accept data. + * @return the number of bytes read from the Source. + * @exception Exception + */ + unsigned int + transfer ( unsigned long bytes, + unsigned int bufSize, + unsigned int sec, + unsigned int usec ) throw ( Exception ); + + /** + * Close the Connector. The Source and all Sinks are closed. + * + * @exception Exception + */ + void + close ( void ) throw ( Exception ); +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* CONNECTOR_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.5 2001/08/26 20:44:30 darkeye + removed external command-line encoder support + replaced it with a shared-object support for lame with the possibility + of static linkage + + Revision 1.4 2000/11/15 18:37:37 darkeye + changed the transferable number of bytes to unsigned long + + Revision 1.3 2000/11/15 18:08:43 darkeye + added multiple verbosity-level event reporting and verbosity command + line option + + Revision 1.2 2000/11/13 18:46:50 darkeye + added kdoc-style documentation comments + + Revision 1.1.1.1 2000/11/05 10:05:49 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/DarkIce.cpp b/darkice/tags/darkice-0_7/src/DarkIce.cpp new file mode 100644 index 0000000..86e873f --- /dev/null +++ b/darkice/tags/darkice-0_7/src/DarkIce.cpp @@ -0,0 +1,686 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : DarkIce.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_STDLIB_H +#include +#else +#error need stdlib.h +#endif + +#ifdef HAVE_UNISTD_H +#include +#else +#error need unistd.h +#endif + +#ifdef HAVE_SYS_TYPES_H +#include +#else +#error need sys/types.h +#endif + +#ifdef HAVE_SYS_WAIT_H +#include +#else +#error need sys/wait.h +#endif + +#ifdef HAVE_ERRNO_H +#include +#else +#error need errno.h +#endif + +#ifdef HAVE_SCHED_H +#include +#else +#error need sched.h +#endif + + + +#include "Util.h" +#include "IceCast.h" +#include "IceCast2.h" +#include "ShoutCast.h" +#include "DarkIce.h" + +#ifdef HAVE_LAME_LIB +#include "LameLibEncoder.h" +#endif + +#ifdef HAVE_VORBIS_LIB +#include "VorbisLibEncoder.h" +#endif + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/*------------------------------------------------------------------------------ + * Make sure wait-related stuff is what we expect + *----------------------------------------------------------------------------*/ +#ifndef WEXITSTATUS +# define WEXITSTATUS(stat_val) ((unsigned)(stat_val) >> 8) +#endif +#ifndef WIFEXITED +# define WIFEXITED(stat_val) (((stat_val) & 255) == 0) +#endif + + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Initialize the object + *----------------------------------------------------------------------------*/ +void +DarkIce :: init ( const Config & config ) throw ( Exception ) +{ + unsigned int bufferSecs; + const ConfigSection * cs; + const char * str; + unsigned int sampleRate; + unsigned int bitsPerSample; + unsigned int channel; + const char * device; + + // the [general] section + if ( !(cs = config.get( "general")) ) { + throw Exception( __FILE__, __LINE__, "no section [general] in config"); + } + str = cs->getForSure( "duration", " missing in section [general]"); + duration = Util::strToL( str); + str = cs->getForSure( "bufferSecs", " missing in section [general]"); + bufferSecs = Util::strToL( str); + + + // the [input] section + if ( !(cs = config.get( "input")) ) { + throw Exception( __FILE__, __LINE__, "no section [general] in config"); + } + + str = cs->getForSure( "sampleRate", " missing in section [input]"); + sampleRate = Util::strToL( str); + str = cs->getForSure( "bitsPerSample", " missing in section [input]"); + bitsPerSample = Util::strToL( str); + str = cs->getForSure( "channel", " missing in section [input]"); + channel = Util::strToL( str); + device = cs->getForSure( "device", " missing in section [input]"); + + dsp = new DspSource( device, + sampleRate, + bitsPerSample, + channel ); + encConnector = new Connector( dsp.get()); + + noAudioOuts = 0; + configIceCast( config, bufferSecs); + configIceCast2( config, bufferSecs); + configShoutCast( config, bufferSecs); +} + + +/*------------------------------------------------------------------------------ + * Look for the IceCast stream outputs in the config file + *----------------------------------------------------------------------------*/ +void +DarkIce :: configIceCast ( const Config & config, + unsigned int bufferSecs ) + throw ( Exception ) +{ + // look for IceCast encoder output streams, + // sections [icecast-0], [icecast-1], ... + char stream[] = "icecast- "; + size_t streamLen = Util::strLen( stream); + unsigned int u; + + for ( u = 0; u < maxOutput; ++u ) { + const ConfigSection * cs; + + // ugly hack to change the section name to "stream0", "stream1", etc. + stream[streamLen-1] = '0' + u; + + if ( !(cs = config.get( stream)) ) { + break; + } + +#ifndef HAVE_LAME_LIB + throw Exception( __FILE__, __LINE__, + "DarkIce not compiled with lame support, " + "thus can't connect to IceCast 1.x, stream: ", + stream); +#else + + const char * str; + + unsigned int sampleRate = 0; + unsigned int bitrate = 0; + const char * server = 0; + unsigned int port = 0; + const char * password = 0; + const char * mountPoint = 0; + const char * remoteDumpFile = 0; + const char * name = 0; + const char * description = 0; + const char * url = 0; + const char * genre = 0; + bool isPublic = false; + unsigned int lowpass = 0; + unsigned int highpass = 0; + + str = cs->get( "sampleRate"); + sampleRate = str ? Util::strToL( str) : dsp->getSampleRate(); + str = cs->getForSure("bitrate", " missing in section ", stream); + bitrate = Util::strToL( str); + server = cs->getForSure( "server", " missing in section ", stream); + str = cs->getForSure( "port", " missing in section ", stream); + port = Util::strToL( str); + password = cs->getForSure("password"," missing in section ",stream); + mountPoint = cs->getForSure( "mountPoint", + " missing in section ", + stream); + remoteDumpFile = cs->get( "remoteDumpFile"); + name = cs->get( "name"); + description = cs->get("description"); + url = cs->get( "url"); + genre = cs->get( "genre"); + str = cs->get( "public"); + isPublic = str ? (Util::strEq( str, "yes") ? true : false) : false; + str = cs->get( "lowpass"); + lowpass = str ? Util::strToL( str) : 0; + str = cs->get( "highpass"); + highpass = str ? Util::strToL( str) : 0; + + // go on and create the things + + // encoder related stuff + unsigned int bs = bufferSecs * + (dsp->getBitsPerSample() / 8) * + dsp->getChannel() * + dsp->getSampleRate(); + reportEvent( 6, "using buffer size", bs); + + // streaming related stuff + audioOuts[u].socket = new TcpSocket( server, port); + audioOuts[u].server = new IceCast( audioOuts[u].socket.get(), + password, + mountPoint, + bitrate, + name, + description, + url, + genre, + isPublic, + remoteDumpFile ); + + audioOuts[u].encoder = new LameLibEncoder( audioOuts[u].server.get(), + dsp.get(), + bitrate, + sampleRate, + dsp->getChannel(), + lowpass, + highpass ); + + encConnector->attach( audioOuts[u].encoder.get()); +#endif // HAVE_LAME_LIB + } + + noAudioOuts += u; +} + + +/*------------------------------------------------------------------------------ + * Look for the IceCast2 stream outputs in the config file + *----------------------------------------------------------------------------*/ +void +DarkIce :: configIceCast2 ( const Config & config, + unsigned int bufferSecs ) + throw ( Exception ) +{ + // look for IceCast2 encoder output streams, + // sections [icecast2-0], [icecast2-1], ... + char stream[] = "icecast2- "; + size_t streamLen = Util::strLen( stream); + unsigned int u; + + for ( u = 0; u < maxOutput; ++u ) { + const ConfigSection * cs; + + // ugly hack to change the section name to "stream0", "stream1", etc. + stream[streamLen-1] = '0' + u; + + if ( !(cs = config.get( stream)) ) { + break; + } + +#ifndef HAVE_VORBIS_LIB + throw Exception( __FILE__, __LINE__, + "DarkIce not compiled with Ogg Vorbis support, " + "thus can't connect to IceCast 2, stream: ", + stream); +#else + + const char * str; + + unsigned int bitrate = 0; + const char * server = 0; + unsigned int port = 0; + const char * password = 0; + const char * mountPoint = 0; + const char * name = 0; + const char * description = 0; + const char * url = 0; + const char * genre = 0; + bool isPublic = false; + + str = cs->getForSure("bitrate", " missing in section ", stream); + bitrate = Util::strToL( str); + server = cs->getForSure( "server", " missing in section ", stream); + str = cs->getForSure( "port", " missing in section ", stream); + port = Util::strToL( str); + password = cs->getForSure("password"," missing in section ",stream); + mountPoint = cs->getForSure( "mountPoint", + " missing in section ", + stream); + name = cs->get( "name"); + description = cs->get("description"); + url = cs->get( "url"); + genre = cs->get( "genre"); + str = cs->get( "public"); + isPublic = str ? (Util::strEq( str, "yes") ? true : false) : false; + + // go on and create the things + + // encoder related stuff + unsigned int bs = bufferSecs * + (dsp->getBitsPerSample() / 8) * + dsp->getChannel() * + dsp->getSampleRate(); + reportEvent( 6, "using buffer size", bs); + + // streaming related stuff + audioOuts[u].socket = new TcpSocket( server, port); + audioOuts[u].server = new IceCast2( audioOuts[u].socket.get(), + password, + mountPoint, + bitrate, + name, + description, + url, + genre, + isPublic ); + + audioOuts[u].encoder = new VorbisLibEncoder( audioOuts[u].server.get(), + dsp.get(), + bitrate, + dsp->getSampleRate(), + dsp->getChannel() ); + + encConnector->attach( audioOuts[u].encoder.get()); +#endif // HAVE_VORBIS_LIB + } + + noAudioOuts += u; +} + + +/*------------------------------------------------------------------------------ + * Look for the ShoutCast stream outputs in the config file + *----------------------------------------------------------------------------*/ +void +DarkIce :: configShoutCast ( const Config & config, + unsigned int bufferSecs ) + throw ( Exception ) +{ + // look for IceCast encoder output streams, + // sections [shoutcast-0], [shoutcast-1], ... + char stream[] = "shoutcast- "; + size_t streamLen = Util::strLen( stream); + unsigned int u; + + for ( u = 0; u < maxOutput; ++u ) { + const ConfigSection * cs; + + // ugly hack to change the section name to "stream0", "stream1", etc. + stream[streamLen-1] = '0' + u; + + if ( !(cs = config.get( stream)) ) { + break; + } + +#ifndef HAVE_LAME_LIB + throw Exception( __FILE__, __LINE__, + "DarkIce not compiled with lame support, " + "thus can't connect to ShoutCast, stream: ", + stream); +#else + + const char * str; + + unsigned int sampleRate = 0; + unsigned int bitrate = 0; + const char * server = 0; + unsigned int port = 0; + const char * password = 0; + const char * name = 0; + const char * url = 0; + const char * genre = 0; + bool isPublic = false; + unsigned int lowpass = 0; + unsigned int highpass = 0; + const char * irc = 0; + const char * aim = 0; + const char * icq = 0; + + str = cs->get( "sampleRate"); + sampleRate = str ? Util::strToL( str) : dsp->getSampleRate(); + str = cs->getForSure("bitrate", " missing in section ", stream); + bitrate = Util::strToL( str); + server = cs->getForSure( "server", " missing in section ", stream); + str = cs->getForSure( "port", " missing in section ", stream); + port = Util::strToL( str); + password = cs->getForSure("password"," missing in section ",stream); + name = cs->get( "name"); + url = cs->get( "url"); + genre = cs->get( "genre"); + str = cs->get( "public"); + isPublic = str ? (Util::strEq( str, "yes") ? true : false) : false; + str = cs->get( "lowpass"); + lowpass = str ? Util::strToL( str) : 0; + str = cs->get( "highpass"); + highpass = str ? Util::strToL( str) : 0; + irc = cs->get( "irc"); + aim = cs->get( "aim"); + icq = cs->get( "icq"); + + // go on and create the things + + // encoder related stuff + unsigned int bs = bufferSecs * + (dsp->getBitsPerSample() / 8) * + dsp->getChannel() * + dsp->getSampleRate(); + reportEvent( 6, "using buffer size", bs); + + // streaming related stuff + audioOuts[u].socket = new TcpSocket( server, port); + audioOuts[u].server = new ShoutCast( audioOuts[u].socket.get(), + password, + bitrate, + name, + url, + genre, + isPublic, + irc, + aim, + icq ); + + audioOuts[u].encoder = new LameLibEncoder( audioOuts[u].server.get(), + dsp.get(), + bitrate, + sampleRate, + dsp->getChannel(), + lowpass, + highpass ); + + encConnector->attach( audioOuts[u].encoder.get()); +#endif // HAVE_LAME_LIB + } + + noAudioOuts += u; +} + + +/*------------------------------------------------------------------------------ + * Set POSIX real-time scheduling, if super-user + *----------------------------------------------------------------------------*/ +void +DarkIce :: setRealTimeScheduling ( void ) throw ( Exception ) +{ + uid_t euid; + + euid = geteuid(); + + if ( euid == 0 ) { + int high_priority; + struct sched_param param; + + /* store the old scheduling parameters */ + if ( (origSchedPolicy = sched_getscheduler(0)) == -1 ) { + throw Exception( __FILE__, __LINE__, "sched_getscheduler", errno); + } + + if ( sched_getparam( 0, ¶m) == -1 ) { + throw Exception( __FILE__, __LINE__, "sched_getparam", errno); + } + origSchedPriority = param.sched_priority; + + /* set SCHED_FIFO with max - 1 priority */ + if ( (high_priority = sched_get_priority_max(SCHED_FIFO)) == -1 ) { + throw Exception(__FILE__,__LINE__,"sched_get_priority_max",errno); + } + reportEvent( 8, "scheduler high priority", high_priority); + + param.sched_priority = high_priority - 1; + + if ( sched_setscheduler( 0, SCHED_FIFO, ¶m) == -1 ) { + throw Exception( __FILE__, __LINE__, "sched_setscheduler", errno); + } + + /* ask the new priortiy and report it */ + if ( sched_getparam( 0, ¶m) == -1 ) { + throw Exception( __FILE__, __LINE__, "sched_getparam", errno); + } + + reportEvent( 1, + "Using POSIX real-time scheduling, priority", + param.sched_priority ); + } else { + reportEvent( 1, + "Not running as super-user, unable to use POSIX real-time scheduling" ); + reportEvent( 1, + "It is recommended that you run this program as super-user"); + } +} + + +/*------------------------------------------------------------------------------ + * Set the original scheduling of the process, the one prior to the + * setRealTimeScheduling call. + * WARNING: make sure you don't call this before setRealTimeScheduling!! + *----------------------------------------------------------------------------*/ +void +DarkIce :: setOriginalScheduling ( void ) throw ( Exception ) +{ + uid_t euid; + + euid = geteuid(); + + if ( euid == 0 ) { + struct sched_param param; + + if ( sched_getparam( 0, ¶m) == -1 ) { + throw Exception( __FILE__, __LINE__, "sched_getparam", errno); + } + + param.sched_priority = origSchedPriority; + + if ( sched_setscheduler( 0, origSchedPolicy, ¶m) == -1 ) { + throw Exception( __FILE__, __LINE__, "sched_setscheduler", errno); + } + + reportEvent( 5, "reverted to original scheduling"); + } +} + + +/*------------------------------------------------------------------------------ + * Run the encoder + *----------------------------------------------------------------------------*/ +bool +DarkIce :: encode ( void ) throw ( Exception ) +{ + unsigned int len; + unsigned long bytes; + + if ( !encConnector->open() ) { + throw Exception( __FILE__, __LINE__, "can't open connector"); + } + + bytes = dsp->getSampleRate() * + (dsp->getBitsPerSample() / 8UL) * + dsp->getChannel() * + duration; + + len = encConnector->transfer( bytes, 4096, 1, 0 ); + + reportEvent( 1, len, "bytes transfered to the encoders"); + + encConnector->close(); + + return true; +} + + +/*------------------------------------------------------------------------------ + * Run + *----------------------------------------------------------------------------*/ +int +DarkIce :: run ( void ) throw ( Exception ) +{ + reportEvent( 3, "encoding"); + setRealTimeScheduling(); + encode(); + setOriginalScheduling(); + reportEvent( 3, "encoding ends"); + + return 0; +} + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.21 2001/10/19 12:39:42 darkeye + created configure options to compile with or without lame / Ogg Vorbis + + Revision 1.20 2001/10/19 09:03:39 darkeye + added support for resampling mp3 streams + + Revision 1.19 2001/09/14 19:31:06 darkeye + added IceCast2 / vorbis support + + Revision 1.18 2001/09/11 15:05:21 darkeye + added Solaris support + + Revision 1.17 2001/09/09 11:27:31 darkeye + added support for ShoutCast servers + + Revision 1.16 2001/09/05 20:11:15 darkeye + removed dependency on locally stored SGI STL header files + now compiler-supplied C++ library STL header files are used + compiles under GNU C++ 3 + hash_map (an SGI extension to STL) replaced with map + std:: namespace prefix added to all STL class references + + Revision 1.15 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.14 2001/08/29 21:08:30 darkeye + made some description options in the darkice config file optional + + Revision 1.13 2001/08/26 20:44:30 darkeye + removed external command-line encoder support + replaced it with a shared-object support for lame with the possibility + of static linkage + + Revision 1.12 2000/12/20 12:36:47 darkeye + added POSIX real-time scheduling + + Revision 1.11 2000/11/18 11:13:27 darkeye + removed direct reference to cout, except from main.cpp + all class use the Reporter interface to report events + + Revision 1.10 2000/11/17 15:50:48 darkeye + added -Wall flag to compiler and eleminated new warnings + + Revision 1.9 2000/11/15 18:37:37 darkeye + changed the transferable number of bytes to unsigned long + + Revision 1.8 2000/11/15 18:08:43 darkeye + added multiple verbosity-level event reporting and verbosity command + line option + + Revision 1.7 2000/11/13 19:38:55 darkeye + moved command line parameter parsing from DarkIce.cpp to main.cpp + + Revision 1.6 2000/11/13 18:46:50 darkeye + added kdoc-style documentation comments + + Revision 1.5 2000/11/10 20:16:21 darkeye + first real tests with multiple streaming + + Revision 1.4 2000/11/09 22:09:46 darkeye + added multiple outputs + added configuration reading + added command line processing + + Revision 1.3 2000/11/08 17:29:50 darkeye + added configuration file reader + + Revision 1.2 2000/11/05 14:08:27 darkeye + changed builting to an automake / autoconf environment + + Revision 1.1.1.1 2000/11/05 10:05:49 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/DarkIce.h b/darkice/tags/darkice-0_7/src/DarkIce.h new file mode 100644 index 0000000..39c841f --- /dev/null +++ b/darkice/tags/darkice-0_7/src/DarkIce.h @@ -0,0 +1,339 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : DarkIce.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef DARK_ICE_H +#define DARK_ICE_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_UNISTD_H +#include +#else +#error need unistd.h +#endif + +#include + +#include "Referable.h" +#include "Reporter.h" +#include "Exception.h" +#include "Ref.h" +#include "AudioSource.h" +#include "BufferedSink.h" +#include "Connector.h" +#include "AudioEncoder.h" +#include "TcpSocket.h" +#include "CastSink.h" +#include "Config.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * Program main object. + * + * @author $Author$ + * @version $Revision$ + */ +class DarkIce : public virtual Referable, public virtual Reporter +{ + private: + + /** + * The maximum number of supported outputs. + */ + static const unsigned int maxOutput = 24; + + /** + * Type describing each lame library output. + */ + typedef struct { + Ref encoder; + Ref socket; + Ref server; + } Output; + + /** + * The outputs. + */ + Output audioOuts[maxOutput]; + + /** + * Number of lame library outputs. + */ + unsigned int noAudioOuts; + + /** + * Duration of playing, in seconds. + */ + unsigned int duration; + + /** + * The dsp to record from. + */ + Ref dsp; + + /** + * The encoding Connector, connecting the dsp to the encoders. + */ + Ref encConnector; + + /** + * Original scheduling policy + */ + int origSchedPolicy; + + /** + * Original scheduling priority + */ + int origSchedPriority; + + /** + * Initialize the object. + * + * @param config the config Object to read initialization + * information from. + * @exception Exception + */ + void + init ( const Config & config ) throw ( Exception ); + + /** + * Look for the icecast stream outputs from the config file. + * Called from init() + * + * @param config the config Object to read initialization + * information from. + * @exception Exception + */ + void + configIceCast ( const Config & config, + unsigned int bufferSecs ) throw ( Exception ); + + /** + * Look for the icecast2 stream outputs from the config file. + * Called from init() + * + * @param config the config Object to read initialization + * information from. + * @exception Exception + */ + void + configIceCast2 ( const Config & config, + unsigned int bufferSecs ) throw ( Exception ); + + /** + * Look for the shoutcast stream outputs from the config file. + * Called from init() + * + * @param config the config Object to read initialization + * information from. + * @exception Exception + */ + void + configShoutCast ( const Config & config, + unsigned int bufferSecs ) throw ( Exception ); + + /** + * Set POSIX real-time scheduling for the encoding process, + * if user permissions enable it. + * + * @exception Exception + */ + void + setRealTimeScheduling ( void ) throw ( Exception ); + + /** + * Set the scheduling that was before setting real-time scheduling. + * This function must be called _only_ after setRealTimeScheduling. + * + * @exception Exception + */ + void + setOriginalScheduling ( void ) throw ( Exception ); + + /** + * Start encoding. Spawns all encoders, opens the dsp and + * starts sending data to the encoders. + * + * @return if encoding was successful. + * @exception Exception + */ + bool + encode ( void ) throw ( Exception ); + + /** + * Start shouting. fork()-s a process for each output, reads + * the output of the encoders and sends them to an IceCast server. + * + * @return if shouting was successful. + * @exception Exception + */ + bool + shout ( unsigned int ) throw ( Exception ); + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + DarkIce ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + + public: + + /** + * Constructor based on a configuration object. + * + * @param config the config Object to read initialization + * information from. + * @exception Exception + */ + inline + DarkIce ( const Config & config ) throw ( Exception ) + { + init( config); + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~DarkIce ( void ) throw ( Exception ) + { + } + +/* TODO + + inline + DarkIce ( const DarkIce & di ) throw ( Exception ) + { + } + + + inline DarkIce & + operator= ( const DarkIce * di ) throw ( Exception ) + { + } +*/ + + /** + * Run the process of recording / encoding / sending to the servers. + * + * @return 0 on success + * @exception Exception + */ + virtual int + run ( void ) throw ( Exception ); + +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* DARK_ICE_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.12 2001/09/14 19:31:06 darkeye + added IceCast2 / vorbis support + + Revision 1.11 2001/09/11 15:05:21 darkeye + added Solaris support + + Revision 1.10 2001/09/09 11:27:31 darkeye + added support for ShoutCast servers + + Revision 1.9 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.8 2001/08/26 20:44:30 darkeye + removed external command-line encoder support + replaced it with a shared-object support for lame with the possibility + of static linkage + + Revision 1.7 2000/12/20 12:36:47 darkeye + added POSIX real-time scheduling + + Revision 1.6 2000/11/15 18:08:43 darkeye + added multiple verbosity-level event reporting and verbosity command + line option + + Revision 1.5 2000/11/13 19:38:55 darkeye + moved command line parameter parsing from DarkIce.cpp to main.cpp + + Revision 1.4 2000/11/13 18:46:50 darkeye + added kdoc-style documentation comments + + Revision 1.3 2000/11/10 20:16:21 darkeye + first real tests with multiple streaming + + Revision 1.2 2000/11/09 22:09:46 darkeye + added multiple outputs + added configuration reading + added command line processing + + Revision 1.1.1.1 2000/11/05 10:05:50 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Exception.cpp b/darkice/tags/darkice-0_7/src/Exception.cpp new file mode 100644 index 0000000..1aca29f --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Exception.cpp @@ -0,0 +1,223 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : Exception.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_STRING_H +#include +#else +#error need string.h +#endif + + +#include "Exception.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Constructor + *----------------------------------------------------------------------------*/ +Exception :: Exception ( const char * file, + unsigned int line, + const char * description1, + const char * description2, + int code = 0 ) throw () +{ + size_t len = 0; + + if ( description1 ) { + len += strlen( description1); + } + if ( description2 ) { + len += strlen( description2); + } + + if ( len ) { + char str[len+1]; + + str[0] = '\0'; + if ( description1 ) { + strcat( str, description1); + } + if ( description2 ) { + strcat( str, description2); + } + + init( file, line, str, code); + + } else { + + init( file, line, 0, code); + } +} + + +/*------------------------------------------------------------------------------ + * Constructor + *----------------------------------------------------------------------------*/ +Exception :: Exception ( const char * file, + unsigned int line, + const char * description1, + const char * description2, + const char * description3, + int code = 0 ) throw () +{ + size_t len = 0; + + if ( description1 ) { + len += strlen( description1); + } + if ( description2 ) { + len += strlen( description2); + } + if ( description3 ) { + len += strlen( description3); + } + + if ( len ) { + char str[len+1]; + + str[0] = '\0'; + if ( description1 ) { + strcat( str, description1); + } + if ( description2 ) { + strcat( str, description2); + } + if ( description3 ) { + strcat( str, description3); + } + + init( file, line, str, code); + + } else { + + init( file, line, 0, code); + } +} + + +/*------------------------------------------------------------------------------ + * Initialize the class + *----------------------------------------------------------------------------*/ +void +Exception :: init ( const char * file, + unsigned int line, + const char * description = 0, + int code = 0 ) throw () +{ + if ( !file ) { + this->file = 0; + } else { + size_t len; + + len = strlen( file ) + 1; + this->file = new char[len]; + if ( this->file ) { + memcpy( this->file, file, len); + } + } + + if ( !description ) { + this->description = 0; + } else { + size_t len; + + len = strlen( description ) + 1; + this->description = new char[len]; + if ( this->description ) { + memcpy( this->description, description, len); + } + } + + this->line = line; + this->code = code; +} + + +/*------------------------------------------------------------------------------ + * De-initialize the class + *----------------------------------------------------------------------------*/ +void +Exception :: strip ( void ) throw () +{ + if ( description ) { + delete[] description; + } + + if ( file ) { + delete[] file; + } +} + + + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.5 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.4 2000/11/11 12:33:13 darkeye + added kdoc-style documentation + + Revision 1.3 2000/11/09 22:05:44 darkeye + added multiple-string constructors + + Revision 1.2 2000/11/05 14:08:27 darkeye + changed builting to an automake / autoconf environment + + Revision 1.1.1.1 2000/11/05 10:05:50 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Exception.h b/darkice/tags/darkice-0_7/src/Exception.h new file mode 100644 index 0000000..5fd6125 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Exception.h @@ -0,0 +1,322 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : Exception.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef EXCEPTION_H +#define EXCEPTION_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * An exception class. + * + * This class should not depend on any other class + * should not throw any exceptions itself. + * + * Typical usage: + * + *
+ *  throw Exception( __FILE__, __LINE__, "describe the exception", code);
+ *  
+ * + * @author $Author$ + * @version $Revision$ + */ +class Exception +{ + private: + + /** + * Source file the exception was thrown in. + */ + char * file; + + /** + * Line number in the source file the exception was thrown in. + */ + unsigned int line; + + /** + * Textual description of the exception. + */ + char * description; + + /** + * Numerical error code. + */ + int code; + + /** + * Initalize the object. + * + * @param file the source file the exception was thrown in. + * @param line the line in the source file. + * @param description textual description of the exception. + * @param code numerical error code. + */ + void + init ( const char * file, + unsigned int line, + const char * description, + int code ) throw (); + + /** + * De-initalize the object. + */ + void + strip () throw (); + + + protected: + + + public: + + /** + * Default constructor. + */ + inline + Exception ( void ) throw () + { + init( 0, 0, 0, 0); + } + + /** + * Copy constructor. + */ + inline + Exception ( const Exception & e ) throw () + { + init( e.file, e.line, e.description, e.code); + } + + /** + * Construct by a description and error code. + * + * @param description textual description of the exception. + * @param code numerical error code. + */ + inline + Exception ( const char * description, + int code = 0 ) throw () + { + init( 0, 0, description, code); + } + + /** + * Construct by source file information, a description and error code. + * + * @param file the source file the exception was thrown in. + * @param line the line in the source file. + * @param description textual description of the exception. + * @param code numerical error code. + */ + inline + Exception ( const char * file, + unsigned int line, + const char * description = 0, + int code = 0 ) throw () + { + init( file, line, description, code); + } + + /** + * Construct by source file information, a description and error code. + * The description is constructed from two strings, any of which + * may be NULL. + * + * @param file the source file the exception was thrown in. + * @param line the line in the source file. + * @param description1 textual description of the exception part 1. + * @param description2 textual description of the exception part 2. + * @param code numerical error code. + */ + Exception ( const char * file, + unsigned int line, + const char * description1, + const char * description2, + int code = 0 ) throw (); + + /** + * Construct by source file information, a description and error code. + * The description is constructed from three strings, any of + * which may be NULL. + * + * @param file the source file the exception was thrown in. + * @param line the line in the source file. + * @param description1 textual description of the exception part 1. + * @param description2 textual description of the exception part 2. + * @param description3 textual description of the exception part 3. + * @param code numerical error code. + */ + Exception ( const char * file, + unsigned int line, + const char * description1, + const char * description2, + const char * description3, + int code = 0 ) throw (); + + /** + * Desctructor. + */ + inline + ~Exception ( void ) throw () + { + strip(); + } + + /** + * Assignment operator. + * + * @param e the Exception to assign this to. + * @return a reference to this Exception. + */ + inline Exception & + operator= ( const Exception & e ) throw () + { + if ( this != &e ) { + strip(); + init( e.file, e.line, e.description, e.code); + } + + return *this; + } + + /** + * Return the textual description of the Exception. + * + * @return the textual description of the Exception. + */ + inline const char * + getDescription( void ) const throw () + { + return description; + } + + /** + * Return the line number in the source file this Exception was + * thrown in. + * + * @return the line number in the source file this Exception was + * thrown in. + */ + inline unsigned int + getLine ( void ) const throw () + { + return line; + } + + /** + * Return the source file this Exception was thrown in. + * + * @return the source file this Exception was thrown in. + */ + inline const char * + getFile ( void ) const throw () + { + return file; + } + + /** + * Return the numerical code of the Exception. + * + * @return the numerical code of the Exception. + */ + inline int + getCode ( void ) const throw () + { + return code; + } +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + +/** + * Print an Exception to an ostream. + * + * @param os the output stream to print to. + * @param e the Exception to print. + * @return a reference to the supplied output stream. + */ +inline ostream & +operator<< ( ostream & os, + const Exception & e ) +{ + os << e.getFile() << ":" << e.getLine() << ": " + << e.getDescription() << " [" << e.getCode() << "]"; + + return os; +} + + + +#endif /* EXCEPTION_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.5 2000/11/17 15:33:54 darkeye + bug fix: ostream << operator overload didn't return the ostream + + Revision 1.4 2000/11/11 12:33:13 darkeye + added kdoc-style documentation + + Revision 1.3 2000/11/09 22:05:44 darkeye + added multiple-string constructors + + Revision 1.2 2000/11/05 14:08:27 darkeye + changed builting to an automake / autoconf environment + + Revision 1.1.1.1 2000/11/05 10:05:50 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/IceCast.cpp b/darkice/tags/darkice-0_7/src/IceCast.cpp new file mode 100644 index 0000000..2e6d97b --- /dev/null +++ b/darkice/tags/darkice-0_7/src/IceCast.cpp @@ -0,0 +1,240 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : IceCast.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_STDIO_H +#include +#else +#error need stdio.h +#endif + +#ifdef HAVE_STRING_H +#include +#else +#error need string.h +#endif + + +#include "Exception.h" +#include "Source.h" +#include "Sink.h" +#include "Util.h" +#include "IceCast.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/*------------------------------------------------------------------------------ + * Size of string conversion buffer + *----------------------------------------------------------------------------*/ +#define STRBUF_SIZE 32 + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Initialize the object + *----------------------------------------------------------------------------*/ +void +IceCast :: init ( const char * mountPoint, + const char * description, + const char * remoteDumpFile ) + throw ( Exception ) +{ + this->mountPoint = Util::strDup( mountPoint); + this->description = description ? Util::strDup( description) : 0; + this->remoteDumpFile = remoteDumpFile ? Util::strDup( remoteDumpFile) : 0; +} + + +/*------------------------------------------------------------------------------ + * De-initialize the object + *----------------------------------------------------------------------------*/ +void +IceCast :: strip ( void ) throw ( Exception ) +{ + delete[] mountPoint; + if ( description ) { + delete[] description; + } + if ( remoteDumpFile ) { + delete[] remoteDumpFile; + } +} + + +/*------------------------------------------------------------------------------ + * Log in to the IceCast server + *----------------------------------------------------------------------------*/ +bool +IceCast :: sendLogin ( void ) throw ( Exception ) +{ + Sink * sink = getSink(); + Source * source = getSocket(); + const char * str; + char resp[STRBUF_SIZE]; + unsigned int len; + + if ( !source->isOpen() ) { + return false; + } + if ( !sink->isOpen() ) { + return false; + } + + /* send the request, a string like: + * "SOURCE /\n" */ + str = "SOURCE "; + sink->write( str, strlen( str)); + str = getPassword(); + sink->write( str, strlen( str)); + str = " /"; + sink->write( str, strlen( str)); + str = getMountPoint(); + sink->write( str, strlen( str)); + + /* send the x-audiocast headers */ + str = "\nx-audiocast-bitrate: "; + sink->write( str, strlen( str)); + if ( snprintf( resp, STRBUF_SIZE, "%d", getBitRate()) == -1 ) { + throw Exception( __FILE__, __LINE__, "snprintf overflow"); + } + sink->write( resp, strlen( resp)); + + str = "\nx-audiocast-public: "; + sink->write( str, strlen( str)); + str = getIsPublic() ? "yes" : "no"; + sink->write( str, strlen( str)); + + if ( getName() ) { + str = "\nx-audiocast-name: "; + sink->write( str, strlen( str)); + str = getName(); + sink->write( str, strlen( str)); + } + + if ( getDescription() ) { + str = "\nx-audiocast-description: "; + sink->write( str, strlen( str)); + str = getDescription(); + sink->write( str, strlen( str)); + } + + if ( getUrl() ) { + str = "\nx-audiocast-url: "; + sink->write( str, strlen( str)); + str = getUrl(); + sink->write( str, strlen( str)); + } + + if ( getGenre() ) { + str = "\nx-audiocast-genre: "; + sink->write( str, strlen( str)); + str = getGenre(); + sink->write( str, strlen( str)); + } + + if ( getRemoteDumpFile() ) { + str = "\nx-audiocast-dumpfile: "; + sink->write( str, strlen( str)); + str = getRemoteDumpFile(); + sink->write( str, strlen( str)); + } + + str = "\n\n"; + sink->write( str, strlen( str)); + sink->flush(); + + /* read the anticipated response: "OK" */ + len = source->read( resp, STRBUF_SIZE); + if ( len < 2 || resp[0] != 'O' || resp[1] != 'K' ) { + return false; + } + + /* suck anything that the other side has to say */ + while ( source->canRead( 0, 0) && + (len = source->read( resp, STRBUF_SIZE)) ) { + ; + } + + + return true; +} + + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.8 2001/09/14 19:31:06 darkeye + added IceCast2 / vorbis support + + Revision 1.7 2001/09/09 11:27:31 darkeye + added support for ShoutCast servers + + Revision 1.6 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.5 2001/08/29 21:08:30 darkeye + made some description options in the darkice config file optional + + Revision 1.4 2000/11/12 14:54:50 darkeye + added kdoc-style documentation comments + + Revision 1.3 2000/11/10 20:14:11 darkeye + added support for remote dump file + + Revision 1.2 2000/11/05 14:08:28 darkeye + changed builting to an automake / autoconf environment + + Revision 1.1.1.1 2000/11/05 10:05:52 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/IceCast.h b/darkice/tags/darkice-0_7/src/IceCast.h new file mode 100644 index 0000000..143b4c7 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/IceCast.h @@ -0,0 +1,284 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : IceCast.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef ICE_CAST_H +#define ICE_CAST_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Sink.h" +#include "TcpSocket.h" +#include "CastSink.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * Class representing output to an IceCast server with + * x-audiocast login + * + * @author $Author$ + * @version $Revision$ + */ +class IceCast : public CastSink +{ + private: + + /** + * Mount point of the stream on the server. + */ + char * mountPoint; + + /** + * Remote dump file if any. + */ + char * remoteDumpFile; + + /** + * Description of the stream. + */ + char * description; + + /** + * Initalize the object. + * + * @param mountPoint mount point of the stream on the server. + * @param remoteDumpFile remote dump file (may be NULL). + * @param description description of the stream. + * @exception Exception + */ + void + init ( const char * mountPoint, + const char * description, + const char * remoteDumpFile ) + throw ( Exception ); + + /** + * De-initalize the object. + * + * @exception Exception + */ + void + strip ( void ) throw ( Exception ); + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + IceCast ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + /** + * Log in to the server using the socket avialable. + * + * @return true if login was successful, false otherwise. + * @exception Exception + */ + virtual bool + sendLogin ( void ) throw ( Exception ); + + + public: + + /** + * Constructor. + * + * @param socket socket connection to the server. + * @param password password to the server. + * @param mountPoint mount point of the stream on the server. + * @param remoteDumpFile remote dump file (may be NULL). + * @param name name of the stream. + * @param description description of the stream. + * @param url URL associated with the stream. + * @param genre genre of the stream. + * @param bitRate bitrate of the stream (e.g. mp3 bitrate). + * @param isPublic is the stream public? + * @param bufferDuration duration of the BufferedSink buffer + * in seconds. + * @exception Exception + */ + inline + IceCast ( TcpSocket * socket, + const char * password, + const char * mountPoint, + unsigned int bitRate, + const char * name = 0, + const char * description = 0, + const char * url = 0, + const char * genre = 0, + bool isPublic = false, + const char * remoteDumpFile = 0, + unsigned int bufferDuration = 10 ) + throw ( Exception ) + : CastSink( socket, + password, + bitRate, + name, + url, + genre, + isPublic, + bufferDuration ) + { + init( mountPoint, description, remoteDumpFile); + } + + /** + * Copy constructor. + * + * @param cs the IceCast to copy. + */ + inline + IceCast( const IceCast & cs ) throw ( Exception ) + : CastSink( cs ) + { + init( cs.getMountPoint(), + cs.getDescription(), + cs.getRemoteDumpFile() ); + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~IceCast( void ) throw ( Exception ) + { + strip(); + } + + /** + * Assignment operator. + * + * @param cs the IceCast to assign this to. + * @return a reference to this IceCast. + * @exception Exception + */ + inline virtual IceCast & + operator= ( const IceCast & cs ) throw ( Exception ) + { + if ( this != &cs ) { + strip(); + CastSink::operator=( cs ); + init( cs.getMountPoint(), + cs.getDescription(), + cs.getRemoteDumpFile() ); + } + return *this; + } + + /** + * Get the mount point of the stream on the server. + * + * @return the mount point of the stream on the server. + */ + inline const char * + getMountPoint ( void ) const throw () + { + return mountPoint; + } + + /** + * Get the remote dump file if any. + * + * @return the remote dump file. May be NULL. + */ + inline const char * + getRemoteDumpFile ( void ) const throw () + { + return remoteDumpFile; + } + + /** + * Get the description of the stream. + * + * @return the description of the stream. + */ + inline const char * + getDescription ( void ) const throw () + { + return description; + } + +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* ICE_CAST_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.6 2001/09/09 11:27:31 darkeye + added support for ShoutCast servers + + Revision 1.5 2001/08/29 21:08:30 darkeye + made some description options in the darkice config file optional + + Revision 1.4 2000/11/12 14:54:50 darkeye + added kdoc-style documentation comments + + Revision 1.3 2000/11/10 20:14:11 darkeye + added support for remote dump file + + Revision 1.2 2000/11/05 17:37:24 darkeye + removed clone() functions + + Revision 1.1.1.1 2000/11/05 10:05:52 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/IceCast2.cpp b/darkice/tags/darkice-0_7/src/IceCast2.cpp new file mode 100644 index 0000000..207a0cb --- /dev/null +++ b/darkice/tags/darkice-0_7/src/IceCast2.cpp @@ -0,0 +1,197 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : IceCast2.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_STDIO_H +#include +#else +#error need stdio.h +#endif + +#ifdef HAVE_STRING_H +#include +#else +#error need string.h +#endif + + +#include "Exception.h" +#include "Source.h" +#include "Sink.h" +#include "Util.h" +#include "IceCast2.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/*------------------------------------------------------------------------------ + * Size of string conversion buffer + *----------------------------------------------------------------------------*/ +#define STRBUF_SIZE 32 + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Initialize the object + *----------------------------------------------------------------------------*/ +void +IceCast2 :: init ( const char * mountPoint, + const char * description ) + throw ( Exception ) +{ + this->mountPoint = Util::strDup( mountPoint); + this->description = description ? Util::strDup( description) : 0; +} + + +/*------------------------------------------------------------------------------ + * De-initialize the object + *----------------------------------------------------------------------------*/ +void +IceCast2 :: strip ( void ) throw ( Exception ) +{ + delete[] mountPoint; + if ( description ) { + delete[] description; + } +} + + +/*------------------------------------------------------------------------------ + * Log in to the IceCast2 server + *----------------------------------------------------------------------------*/ +bool +IceCast2 :: sendLogin ( void ) throw ( Exception ) +{ + Sink * sink = getSink(); + Source * source = getSocket(); + const char * str; + char resp[STRBUF_SIZE]; + + if ( !source->isOpen() ) { + return false; + } + if ( !sink->isOpen() ) { + return false; + } + + /* send the request, a string like: + * "SOURCE ICE/1.0" */ + str = "SOURCE /"; + sink->write( str, strlen( str)); + str = getMountPoint(); + sink->write( str, strlen( str)); + str = " ICE/1.0"; + sink->write( str, strlen( str)); + + /* send the ice- headers */ + str = "\nice-password: "; + sink->write( str, strlen(str)); + str = getPassword(); + sink->write( str, strlen(str)); + + str = "\nice-bitrate: "; + sink->write( str, strlen( str)); + if ( snprintf( resp, STRBUF_SIZE, "%d", getBitRate()) == -1 ) { + throw Exception( __FILE__, __LINE__, "snprintf overflow"); + } + sink->write( resp, strlen( resp)); + + str = "\nice-public: "; + sink->write( str, strlen( str)); + str = getIsPublic() ? "yes" : "no"; + sink->write( str, strlen( str)); + + if ( getName() ) { + str = "\nice-name: "; + sink->write( str, strlen( str)); + str = getName(); + sink->write( str, strlen( str)); + } + + if ( getDescription() ) { + str = "\nice-description: "; + sink->write( str, strlen( str)); + str = getDescription(); + sink->write( str, strlen( str)); + } + + if ( getUrl() ) { + str = "\nice-url: "; + sink->write( str, strlen( str)); + str = getUrl(); + sink->write( str, strlen( str)); + } + + if ( getGenre() ) { + str = "\nice-genre: "; + sink->write( str, strlen( str)); + str = getGenre(); + sink->write( str, strlen( str)); + } + + str = "\n\n"; + sink->write( str, strlen( str)); + sink->flush(); + + return true; +} + + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.1 2001/09/14 19:31:06 darkeye + added IceCast2 / vorbis support + + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/IceCast2.h b/darkice/tags/darkice-0_7/src/IceCast2.h new file mode 100644 index 0000000..cc9095d --- /dev/null +++ b/darkice/tags/darkice-0_7/src/IceCast2.h @@ -0,0 +1,249 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : IceCast2.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef ICE_CAST2_H +#define ICE_CAST2_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Sink.h" +#include "TcpSocket.h" +#include "CastSink.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * Class representing output to an IceCast2 server with + * ice login + * + * @author $Author$ + * @version $Revision$ + */ +class IceCast2 : public CastSink +{ + private: + + /** + * Mount point of the stream on the server. + */ + char * mountPoint; + + /** + * Description of the stream. + */ + char * description; + + /** + * Initalize the object. + * + * @param mountPoint mount point of the stream on the server. + * @param remoteDumpFile remote dump file (may be NULL). + * @param description description of the stream. + * @exception Exception + */ + void + init ( const char * mountPoint, + const char * description ) + throw ( Exception ); + + /** + * De-initalize the object. + * + * @exception Exception + */ + void + strip ( void ) throw ( Exception ); + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + IceCast2 ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + /** + * Log in to the server using the socket avialable. + * + * @return true if login was successful, false otherwise. + * @exception Exception + */ + virtual bool + sendLogin ( void ) throw ( Exception ); + + + public: + + /** + * Constructor. + * + * @param socket socket connection to the server. + * @param password password to the server. + * @param mountPoint mount point of the stream on the server. + * @param name name of the stream. + * @param description description of the stream. + * @param url URL associated with the stream. + * @param genre genre of the stream. + * @param bitRate bitrate of the stream (e.g. mp3 bitrate). + * @param isPublic is the stream public? + * @param bufferDuration duration of the BufferedSink buffer + * in seconds. + * @exception Exception + */ + inline + IceCast2 ( TcpSocket * socket, + const char * password, + const char * mountPoint, + unsigned int bitRate, + const char * name = 0, + const char * description = 0, + const char * url = 0, + const char * genre = 0, + bool isPublic = false, + unsigned int bufferDuration = 10 ) + throw ( Exception ) + : CastSink( socket, + password, + bitRate, + name, + url, + genre, + isPublic, + bufferDuration ) + { + init( mountPoint, description); + } + + /** + * Copy constructor. + * + * @param cs the IceCast2 to copy. + */ + inline + IceCast2( const IceCast2 & cs ) throw ( Exception ) + : CastSink( cs ) + { + init( cs.getMountPoint(), + cs.getDescription() ); + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~IceCast2( void ) throw ( Exception ) + { + strip(); + } + + /** + * Assignment operator. + * + * @param cs the IceCast2 to assign this to. + * @return a reference to this IceCast2. + * @exception Exception + */ + inline virtual IceCast2 & + operator= ( const IceCast2 & cs ) throw ( Exception ) + { + if ( this != &cs ) { + strip(); + CastSink::operator=( cs ); + init( cs.getMountPoint(), + cs.getDescription() ); + } + return *this; + } + + /** + * Get the mount point of the stream on the server. + * + * @return the mount point of the stream on the server. + */ + inline const char * + getMountPoint ( void ) const throw () + { + return mountPoint; + } + + /** + * Get the description of the stream. + * + * @return the description of the stream. + */ + inline const char * + getDescription ( void ) const throw () + { + return description; + } + +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* ICE_CAST2_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.1 2001/09/14 19:31:06 darkeye + added IceCast2 / vorbis support + + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/LameLibEncoder.cpp b/darkice/tags/darkice-0_7/src/LameLibEncoder.cpp new file mode 100644 index 0000000..52c946c --- /dev/null +++ b/darkice/tags/darkice-0_7/src/LameLibEncoder.cpp @@ -0,0 +1,452 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : LameLibEncoder.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +// compile the whole file only if lame support configured in +#ifdef HAVE_LAME_LIB + + +#include "Exception.h" +#include "Util.h" +#include "LameLibEncoder.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Open an encoding session + *----------------------------------------------------------------------------*/ +bool +LameLibEncoder :: open ( void ) + throw ( Exception ) +{ + if ( isOpen() ) { + close(); + } + + lameGlobalFlags = lame_init(); + + // ugly lame returns -1 in a pointer on allocation errors + if ( !lameGlobalFlags || ((int)lameGlobalFlags) == -1 ) { + throw Exception( __FILE__, __LINE__, + "lame lib init error", + (int) lameGlobalFlags); + } + + if ( 0 > lame_set_num_channels( lameGlobalFlags, getInChannel()) ) { + throw Exception( __FILE__, __LINE__, + "lame lib setting channels error", + getInChannel() ); + } + + if ( 0 > lame_set_mode( lameGlobalFlags, + getInChannel() == 1 ? MONO : JOINT_STEREO) ) { + throw Exception( __FILE__, __LINE__, + "lame lib setting mode error", + JOINT_STEREO ); + } + + reportEvent( 5, "set lame mode", lame_get_mode( lameGlobalFlags)); + + reportEvent( 5, + "set lame channels", + lame_get_num_channels( lameGlobalFlags)); + + if ( 0 > lame_set_in_samplerate( lameGlobalFlags, getInSampleRate()) ) { + throw Exception( __FILE__, __LINE__, + "lame lib setting input sample rate error", + getInSampleRate() ); + } + + reportEvent( 5, + "set lame in sample rate", + lame_get_in_samplerate( lameGlobalFlags)); + + if ( 0 > lame_set_out_samplerate( lameGlobalFlags, getOutSampleRate()) ) { + throw Exception( __FILE__, __LINE__, + "lame lib setting output sample rate error", + getOutSampleRate() ); + } + + reportEvent( 5, + "set lame out sample rate", + lame_get_out_samplerate( lameGlobalFlags)); + + if ( 0 > lame_set_brate( lameGlobalFlags, getOutBitrate()) ) { + throw Exception( __FILE__, __LINE__, + "lame lib setting output bit rate error", + getOutBitrate() ); + } + + reportEvent( 5, "set lame bit rate", lame_get_brate( lameGlobalFlags)); + + if ( lowpass ) { + if ( 0 > lame_set_lowpassfreq( lameGlobalFlags, lowpass) ) { + throw Exception( __FILE__, __LINE__, + "lame lib setting lowpass frequency error", + lowpass ); + } + + reportEvent( 5, + "set lame lowpass frequency", + lame_get_lowpassfreq( lameGlobalFlags)); + } + + if ( highpass ) { + if ( 0 > lame_set_highpassfreq( lameGlobalFlags, highpass) ) { + throw Exception( __FILE__, __LINE__, + "lame lib setting highpass frequency error", + lowpass ); + } + + reportEvent( 5, + "set lame highpass frequency", + lame_get_highpassfreq( lameGlobalFlags)); + } + + // not configurable lame settings + + if ( 0 > lame_set_quality( lameGlobalFlags, 2) ) { + throw Exception( __FILE__, __LINE__, + "lame lib setting quality error", + 2 ); + } + + reportEvent( 5, "set lame quality", lame_get_quality( lameGlobalFlags)); + + if ( 0 > lame_set_exp_nspsytune( lameGlobalFlags, 1) ) { + throw Exception( __FILE__, __LINE__, + "lame lib setting psycho acoustic model error"); + } + + reportEvent( 5, + "set lame psycho acoustic model", + lame_get_exp_nspsytune( lameGlobalFlags)); + + if ( 0 > lame_set_error_protection( lameGlobalFlags, 1) ) { + throw Exception( __FILE__, __LINE__, + "lame lib setting error protection error", + 1 ); + } + + reportEvent( 5, + "set lame error protection", + lame_get_error_protection( lameGlobalFlags)); + + // let lame init its own params based on our settings + if ( 0 > lame_init_params( lameGlobalFlags) ) { + throw Exception( __FILE__, __LINE__, + "lame lib initializing params error" ); + } + + lame_print_config( lameGlobalFlags); + + // open the underlying sink + if ( !sink->open() ) { + throw Exception( __FILE__, __LINE__, + "lame lib opening underlying sink error"); + } + + return true; +} + +/*------------------------------------------------------------------------------ + * Convert an unsigned char buffer holding 8 bit PCM values with channels + * interleaved to two short int buffers (one for each channel) + *----------------------------------------------------------------------------*/ +void +LameLibEncoder :: conv8 ( unsigned char * pcmBuffer, + unsigned int lenPcmBuffer, + short int * leftBuffer, + short int * rightBuffer, + unsigned int channels ) +{ + if ( channels == 1 ) { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + unsigned short int value; + + value = pcmBuffer[i++]; + leftBuffer[j] = (short int) value; + ++j; + } + } else { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + unsigned short int value; + + value = pcmBuffer[i++]; + leftBuffer[j] = (short int) value; + value = pcmBuffer[i++]; + rightBuffer[j] = (short int) value; + ++j; + } + } +} + + +/*------------------------------------------------------------------------------ + * Convert an unsigned char buffer holding 16 bit PCM values with channels + * interleaved to two short int buffers (one for each channel) + *----------------------------------------------------------------------------*/ +void +LameLibEncoder :: conv16 ( unsigned char * pcmBuffer, + unsigned int lenPcmBuffer, + short int * leftBuffer, + short int * rightBuffer, + unsigned int channels ) +{ + if ( isInBigEndian() ) { + if ( channels == 1 ) { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + unsigned short int value; + + value = pcmBuffer[i++] << 8; + value |= pcmBuffer[i++]; + leftBuffer[j] = (short int) value; + ++j; + } + } else { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + unsigned short int value; + + value = pcmBuffer[i++] << 8; + value |= pcmBuffer[i++]; + leftBuffer[j] = (short int) value; + value = pcmBuffer[i++] << 8; + value |= pcmBuffer[i++]; + rightBuffer[j] = (short int) value; + ++j; + } + } + } else { + if ( channels == 1 ) { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + unsigned short int value; + + value = pcmBuffer[i++]; + value |= pcmBuffer[i++] << 8; + leftBuffer[j] = (short int) value; + ++j; + } + } else { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + unsigned short int value; + + value = pcmBuffer[i++]; + value |= pcmBuffer[i++] << 8; + leftBuffer[j] = (short int) value; + value = pcmBuffer[i++]; + value |= pcmBuffer[i++] << 8; + rightBuffer[j] = (short int) value; + ++j; + } + } + } +} + + +/*------------------------------------------------------------------------------ + * Write data to the encoder + *----------------------------------------------------------------------------*/ +unsigned int +LameLibEncoder :: write ( const void * buf, + unsigned int len ) throw ( Exception ) +{ + if ( !isOpen() ) { + return 0; + } + + unsigned int bitsPerSample = getInBitsPerSample(); + unsigned int channels = getInChannel(); + + if ( channels != 1 && channels != 2 ) { + throw Exception( __FILE__, __LINE__, + "unsupported number of channels for the encoder", + channels ); + } + + unsigned int sampleSize = (bitsPerSample / 8) * channels; + unsigned char * b = (unsigned char*) buf; + unsigned int processed = len - (len % sampleSize); + unsigned int nSamples = processed / sampleSize; + short int leftBuffer[nSamples]; + short int rightBuffer[nSamples]; + + if ( bitsPerSample == 8 ) { + conv8( b, processed, leftBuffer, rightBuffer, channels); + } else if ( bitsPerSample == 16 ) { + conv16( b, processed, leftBuffer, rightBuffer, channels); + } else { + throw Exception( __FILE__, __LINE__, + "unsupported number of bits per sample for the encoder", + bitsPerSample ); + } + + // data chunk size estimate according to lame documentation + unsigned int mp3Size = (unsigned int) (1.25 * nSamples + 7200); + unsigned char mp3Buf[mp3Size]; + int ret; + + ret = lame_encode_buffer( lameGlobalFlags, + leftBuffer, + channels == 2 ? rightBuffer : leftBuffer, + nSamples, + mp3Buf, + mp3Size ); + + if ( ret < 0 ) { + reportEvent( 3, "lame encoding error", ret); + return 0; + } + + unsigned int written = sink->write( mp3Buf, ret); + // just let go data that could not be written + if ( written < (unsigned int) ret ) { + reportEvent( 2, + "couldn't write all from encoder to underlying sink", + ret - written); + } + + return processed; +} + + +/*------------------------------------------------------------------------------ + * Flush the data from the encoder + *----------------------------------------------------------------------------*/ +void +LameLibEncoder :: flush ( void ) + throw ( Exception ) +{ + if ( !isOpen() ) { + return; + } + + // data chunk size estimate according to lame documentation + unsigned int mp3Size = 7200; + unsigned char mp3Buf[mp3Size]; + int ret; + + ret = lame_encode_flush( lameGlobalFlags, mp3Buf, mp3Size ); + + unsigned int written = sink->write( mp3Buf, ret); + // just let go data that could not be written + if ( written < (unsigned int) ret ) { + reportEvent( 2, + "couldn't write all from encoder to underlying sink", + ret - written); + } + + sink->flush(); +} + + +/*------------------------------------------------------------------------------ + * Close the encoding session + *----------------------------------------------------------------------------*/ +void +LameLibEncoder :: close ( void ) throw ( Exception ) +{ + if ( isOpen() ) { + flush(); + lame_close( lameGlobalFlags); + lameGlobalFlags = 0; + } +} + + +#endif // HAVE_LAME_LIB + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.8 2001/10/19 12:39:42 darkeye + created configure options to compile with or without lame / Ogg Vorbis + + Revision 1.7 2001/09/18 14:57:19 darkeye + finalized Solaris port + + Revision 1.6 2001/09/15 11:35:08 darkeye + minor fixes + + Revision 1.5 2001/09/02 09:54:12 darkeye + fixed typos in CVS substition keywords + + Revision 1.4 2001/08/31 20:09:05 darkeye + added funcitons conv8() and conv16() + + Revision 1.3 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.2 2001/08/29 21:06:16 darkeye + added real support for 8 / 16 bit mono / stereo input + (8 bit input still has to be spread on 16 bit words) + + Revision 1.1 2001/08/26 20:44:30 darkeye + removed external command-line encoder support + replaced it with a shared-object support for lame with the possibility + of static linkage + + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/LameLibEncoder.h b/darkice/tags/darkice-0_7/src/LameLibEncoder.h new file mode 100644 index 0000000..b3758de --- /dev/null +++ b/darkice/tags/darkice-0_7/src/LameLibEncoder.h @@ -0,0 +1,492 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : LameLibEncoder.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef LAME_LIB_ENCODER_H +#define LAME_LIB_ENCODER_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_LAME_LIB +#include +#else +#error configure with lame +#endif + + +#include "Ref.h" +#include "Exception.h" +#include "Reporter.h" +#include "AudioEncoder.h" +#include "Sink.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * A class representing the lame encoder linked as a shared object or as + * a static library. + * + * @author $Author$ + * @version $Revision$ + */ +class LameLibEncoder : public AudioEncoder, public virtual Reporter +{ + private: + + /** + * Lame library global flags + */ + lame_global_flags * lameGlobalFlags; + + /** + * The Sink to dump mp3 data to + */ + Ref sink; + + /** + * Highpass filter. Sound frequency in Hz, from where up the + * input is cut. + */ + unsigned int lowpass; + + /** + * Lowpass filter. Sound frequency in Hz, from where down the + * input is cut. + */ + unsigned int highpass; + + /** + * Initialize the object. + * + * @param sink the sink to send mp3 output to + * @param lowpass frequency threshold for the lowpass filter. + * Input above this frequency is cut. + * If 0, lame's default values are used, + * which depends on the out sample rate. + * @param highpass frequency threshold for the highpass filter. + * Input below this frequency is cut. + * If 0, lame's default values are used, + * which depends on the out sample rate. + * @exception Exception + */ + inline void + init ( Sink * sink, + unsigned int lowpass, + unsigned int highpass ) throw ( Exception ) + { + this->sink = sink; + this->lowpass = lowpass; + this->highpass = highpass; + + if ( getInBitsPerSample() != 16 && getInBitsPerSample() != 8 ) { + throw Exception( __FILE__, __LINE__, + "specified bits per sample not supported", + getInBitsPerSample() ); + } + + if ( getInChannel() != getOutChannel() ) { + throw Exception( __FILE__, __LINE__, + "different in and out channels not supported"); + } + } + + /** + * De-initialize the object. + * + * @exception Exception + */ + inline void + strip ( void ) throw ( Exception ) + { + } + + /** + * Convert a char buffer holding 8 bit PCM values to a short buffer + * + * @param pcmBuffer buffer holding 8 bit PCM audio values, + * channels are interleaved + * @param lenPcmBuffer length of pcmBuffer + * @param leftBuffer put the left channel here (must be big enough) + * @param rightBuffer put the right channel here (if mono, not + * touched, must be big enough) + * @param channels number of channels (1 = mono, 2 = stereo) + */ + void + conv8 ( unsigned char * pcmBuffer, + unsigned int lenPcmBuffer, + short int * leftBuffer, + short int * rightBuffer, + unsigned int channels ); + + /** + * Convert a char buffer holding 16 bit PCM values to a short buffer + * + * @param pcmBuffer buffer holding 16 bit PCM audio values, + * channels are interleaved + * @param lenPcmBuffer length of pcmBuffer + * @param leftBuffer put the left channel here (must be big enough) + * @param rightBuffer put the right channel here (if mono, not + * touched, must be big enough) + * @param channels number of channels (1 = mono, 2 = stereo) + */ + void + conv16 ( unsigned char * pcmBuffer, + unsigned int lenPcmBuffer, + short int * leftBuffer, + short int * rightBuffer, + unsigned int channels ); + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + LameLibEncoder ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + + public: + + /** + * Constructor. + * + * @param sink the sink to send mp3 output to + * @param inSampleRate sample rate of the input. + * @param inBitsPerSample number of bits per sample of the input. + * @param inChannel number of channels of the input. + * @param outBitrate bit rate of the output (bits/sec). + * @param outSampleRate sample rate of the output. + * If 0, inSampleRate is used. + * @param outChannel number of channels of the output. + * If 0, inChannel is used. + * @param lowpass frequency threshold for the lowpass filter. + * Input above this frequency is cut. + * If 0, lame's default values are used, + * which depends on the out sample rate. + * @param highpass frequency threshold for the highpass filter. + * Input below this frequency is cut. + * If 0, lame's default values are used, + * which depends on the out sample rate. + * @exception Exception + */ + inline + LameLibEncoder ( Sink * sink, + unsigned int inSampleRate, + unsigned int inBitsPerSample, + unsigned int inChannel, + unsigned int outBitrate, + unsigned int outSampleRate = 0, + unsigned int outChannel = 0, + unsigned int lowpass = 0, + unsigned int highpass = 0 ) + throw ( Exception ) + + : AudioEncoder ( inSampleRate, + inBitsPerSample, + inChannel, + outBitrate, + outSampleRate, + outChannel ) + { + init( sink, lowpass, highpass ); + } + + /** + * Constructor. + * + * @param sink the sink to send mp3 output to + * @param as get input sample rate, bits per sample and channels + * from this AudioSource. + * @param outBitrate bit rate of the output (bits/sec). + * @param outSampleRate sample rate of the output. + * If 0, input sample rate is used. + * @param outChannel number of channels of the output. + * If 0, input channel is used. + * @param lowpass frequency threshold for the lowpass filter. + * Input above this frequency is cut. + * If 0, lame's default values are used, + * which depends on the out sample rate. + * @param highpass frequency threshold for the highpass filter. + * Input below this frequency is cut. + * If 0, lame's default values are used, + * which depends on the out sample rate. + * @exception Exception + */ + inline + LameLibEncoder ( Sink * sink, + const AudioSource * as, + unsigned int outBitrate, + unsigned int outSampleRate = 0, + unsigned int outChannel = 0, + unsigned int lowpass = 0, + unsigned int highpass = 0 ) + throw ( Exception ) + + : AudioEncoder ( as, + outBitrate, + outSampleRate, + outChannel ) + { + init( sink, lowpass, highpass ); + } + + /** + * Copy constructor. + * + * @param encoder the LameLibEncoder to copy. + */ + inline + LameLibEncoder ( const LameLibEncoder & encoder ) + throw ( Exception ) + : AudioEncoder( encoder ) + { + init( encoder.sink.get(), encoder.lowpass, encoder.highpass ); + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~LameLibEncoder ( void ) throw ( Exception ) + { + if ( isOpen() ) { + close(); + } + strip(); + } + + /** + * Assignment operator. + * + * @param encoder the LameLibEncoder to assign this to. + * @return a reference to this LameLibEncoder. + * @exception Exception + */ + inline virtual LameLibEncoder & + operator= ( const LameLibEncoder & encoder ) throw ( Exception ) + { + if ( this != &encoder ) { + strip(); + AudioEncoder::operator=( encoder); + init( encoder.sink.get(), encoder.lowpass, encoder.highpass ); + } + + return *this; + } + + /** + * Get the version string of the underlying lame library. + * + * @return the version string of the underlying lame library. + */ + inline const char * + getLameVersion( void ) + { + return get_lame_version(); + } + + /** + * Check wether encoding is in progress. + * + * @return true if encoding is in progress, false otherwise. + */ + inline virtual bool + isRunning ( void ) const throw () + { + return isOpen(); + } + + /** + * Start encoding. This function returns as soon as possible, + * with encoding started in the background. + * + * @return true if encoding has started, false otherwise. + * @exception Exception + */ + inline virtual bool + start ( void ) throw ( Exception ) + { + return open(); + } + + /** + * Stop encoding. Stops the encoding running in the background. + * + * @exception Exception + */ + inline virtual void + stop ( void ) throw ( Exception ) + { + return close(); + } + + /** + * Open an encoding session. + * + * @return true if opening was successfull, false otherwise. + * @exception Exception + */ + virtual bool + open ( void ) throw ( Exception ); + + /** + * Check if the encoding session is open. + * + * @return true if the encoding session is open, false otherwise. + */ + inline virtual bool + isOpen ( void ) const throw () + { + return lameGlobalFlags != 0; + } + + /** + * Check if the encoder is ready to accept data. + * + * @param sec the maximum seconds to block. + * @param usec micro seconds to block after the full seconds. + * @return true if the encoder is ready to accept data, + * false otherwise. + * @exception Exception + */ + inline virtual bool + canWrite ( unsigned int sec, + unsigned int usec ) throw ( Exception ) + { + if ( !isOpen() ) { + return false; + } + + return true; + } + + /** + * Write data to the encoder. + * Buf is expected to be a sequence of big-endian 16 bit values, + * with left and right channels interleaved. Len is the number of + * bytes, must be a multiple of 4. + * + * @param buf the data to write. + * @param len number of bytes to write from buf. + * @return the number of bytes written (may be less than len). + * @exception Exception + */ + virtual unsigned int + write ( const void * buf, + unsigned int len ) throw ( Exception ); + + /** + * Flush all data that was written to the encoder to the underlying + * connection. + * + * @exception Exception + */ + virtual void + flush ( void ) throw ( Exception ); + + /** + * Close the encoding session. + * + * @exception Exception + */ + virtual void + close ( void ) throw ( Exception ); +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + +#endif /* LAME_LIB_ENCODER_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.9 2001/10/19 12:39:42 darkeye + created configure options to compile with or without lame / Ogg Vorbis + + Revision 1.8 2001/10/19 09:03:39 darkeye + added support for resampling mp3 streams + + Revision 1.7 2001/09/15 11:35:08 darkeye + minor fixes + + Revision 1.6 2001/09/14 19:31:06 darkeye + added IceCast2 / vorbis support + + Revision 1.5 2001/09/02 09:54:12 darkeye + fixed typos in CVS substition keywords + + Revision 1.4 2001/08/31 20:09:05 darkeye + added funcitons conv8() and conv16() + + Revision 1.3 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.2 2001/08/29 21:06:16 darkeye + added real support for 8 / 16 bit mono / stereo input + (8 bit input still has to be spread on 16 bit words) + + Revision 1.1 2001/08/26 20:44:30 darkeye + removed external command-line encoder support + replaced it with a shared-object support for lame with the possibility + of static linkage + + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Makefile.am b/darkice/tags/darkice-0_7/src/Makefile.am new file mode 100644 index 0000000..16818ad --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Makefile.am @@ -0,0 +1,47 @@ +bin_PROGRAMS = darkice +CXXFLAGS = -O2 -Wall +INCLUDES = @LAME_INCFLAGS@ @VORBIS_INCFLAGS@ +LDADD = @LAME_LDFLAGS@ @VORBIS_LDFLAGS@ + +darkice_SOURCES = AudioEncoder.h\ + AudioSource.h\ + BufferedSink.cpp\ + BufferedSink.h\ + CastSink.cpp\ + CastSink.h\ + Connector.cpp\ + Connector.h\ + DarkIce.cpp\ + DarkIce.h\ + Exception.cpp\ + Exception.h\ + IceCast.cpp\ + IceCast.h\ + IceCast2.cpp\ + IceCast2.h\ + ShoutCast.cpp\ + ShoutCast.h\ + LameLibEncoder.cpp\ + LameLibEncoder.h\ + VorbisLibEncoder.cpp\ + VorbisLibEncoder.h\ + OssDspSource.cpp\ + OssDspSource.h\ + SolarisDspSource.cpp\ + SolarisDspSource.h\ + Ref.h\ + Referable.h\ + Sink.h\ + Source.h\ + TcpSocket.cpp\ + TcpSocket.h\ + Util.cpp\ + Util.h\ + ConfigSection.h\ + ConfigSection.cpp\ + Config.h\ + Config.cpp\ + Reporter.h\ + Reporter.cpp\ + main.cpp + diff --git a/darkice/tags/darkice-0_7/src/OssDspSource.cpp b/darkice/tags/darkice-0_7/src/OssDspSource.cpp new file mode 100644 index 0000000..96a7b69 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/OssDspSource.cpp @@ -0,0 +1,321 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : OssDspSource.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#include "OssDspSource.h" + +#ifdef SUPPORT_OSS_DSP +// only compile this code if there is support for it + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_UNISTD_H +#include +#else +#error need unistd.h +#endif + +#ifdef HAVE_STRING_H +#include +#else +#error need string.h +#endif + +#ifdef HAVE_SYS_TYPES_H +#include +#else +#error need sys/types.h +#endif + +#ifdef HAVE_SYS_STAT_H +#include +#else +#error need sys/stat.h +#endif + +#ifdef HAVE_FCNTL_H +#include +#else +#error need fcntl.h +#endif + +#ifdef HAVE_SYS_TIME_H +#include +#else +#error need sys/time.h +#endif + +#ifdef HAVE_SYS_IOCTL_H +#include +#else +#error need sys/ioctl.h +#endif + +#ifdef HAVE_SYS_SOUNDCARD_H +#include +#else +#error need sys/soundcard.h +#endif + + +#include "Util.h" +#include "Exception.h" +#include "OssDspSource.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Initialize the object + *----------------------------------------------------------------------------*/ +void +OssDspSource :: init ( const char * name ) throw ( Exception ) +{ + fileName = Util::strDup( name); + fileDescriptor = 0; + running = false; +} + + +/*------------------------------------------------------------------------------ + * De-initialize the object + *----------------------------------------------------------------------------*/ +void +OssDspSource :: strip ( void ) throw ( Exception ) +{ + if ( isOpen() ) { + close(); + } + + delete[] fileName; +} + + +/*------------------------------------------------------------------------------ + * Open the audio source + *----------------------------------------------------------------------------*/ +bool +OssDspSource :: open ( void ) throw ( Exception ) +{ + int format; + int i; + unsigned int u; + + if ( isOpen() ) { + return false; + } + + switch ( getBitsPerSample() ) { + case 8: + format = AFMT_U8; + break; + + case 16: + format = AFMT_S16_LE; + break; + + default: + return false; + } + + if ( (fileDescriptor = ::open( fileName, O_RDONLY)) == -1 ) { + fileDescriptor = 0; + return false; + } + + i = format; + if ( ioctl( fileDescriptor, SNDCTL_DSP_SETFMT, &i) == -1 || + i != format ) { + + close(); + throw Exception( __FILE__, __LINE__, "can't set format", i); + } + + u = getChannel(); + if ( ioctl( fileDescriptor, SNDCTL_DSP_CHANNELS, &u) == -1 || + u != getChannel() ) { + + close(); + throw Exception( __FILE__, __LINE__, "can't set channels", u); + } + + u = getSampleRate(); + if ( ioctl( fileDescriptor, SNDCTL_DSP_SPEED, &u) == -1 ) { + + close(); + throw Exception( __FILE__, __LINE__, + "can't set soundcard recording sample rate", u); + } + if ( u != getSampleRate() ) { + reportEvent( 2, "sound card recording sample rate set to ", u, + " while trying to set it to ", getSampleRate()); + reportEvent( 2, "this is probably not a problem, but a slight " + "drift in the sound card driver"); + } + + return true; +} + + +/*------------------------------------------------------------------------------ + * Check wether read() would return anything + *----------------------------------------------------------------------------*/ +bool +OssDspSource :: canRead ( unsigned int sec, + unsigned int usec ) throw ( Exception ) +{ + fd_set fdset; + struct timeval tv; + int ret; + + if ( !isOpen() ) { + return false; + } + + if ( !running ) { + /* ugly workaround to get the dsp into recording state */ + unsigned char b[getChannel()*getBitsPerSample()/8]; + + read( b, getChannel()*getBitsPerSample()/8); + } + + FD_ZERO( &fdset); + FD_SET( fileDescriptor, &fdset); + tv.tv_sec = sec; + tv.tv_usec = usec; + + ret = select( fileDescriptor + 1, &fdset, NULL, NULL, &tv); + + if ( ret == -1 ) { + throw Exception( __FILE__, __LINE__, "select error"); + } + + return ret > 0; +} + + +/*------------------------------------------------------------------------------ + * Read from the audio source + *----------------------------------------------------------------------------*/ +unsigned int +OssDspSource :: read ( void * buf, + unsigned int len ) throw ( Exception ) +{ + ssize_t ret; + + if ( !isOpen() ) { + return 0; + } + + ret = ::read( fileDescriptor, buf, len); + + if ( ret == -1 ) { + throw Exception( __FILE__, __LINE__, "read error"); + } + + running = true; + return ret; +} + + +/*------------------------------------------------------------------------------ + * Close the audio source + *----------------------------------------------------------------------------*/ +void +OssDspSource :: close ( void ) throw ( Exception ) +{ + if ( !isOpen() ) { + return; + } + + ::close( fileDescriptor); + fileDescriptor = 0; + running = false; +} + +#endif // SUPPORT_OSS_DSP + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.10 2001/09/26 16:55:30 darkeye + BSD port + + Revision 1.9 2001/09/11 15:05:21 darkeye + added Solaris support + + Revision 1.8 2001/09/02 14:08:40 darkeye + setting the sound card recording sample rate is now more relaxed + there is no error reported if the sample rate is not exactly the same + + Revision 1.7 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.6 2000/12/01 15:03:28 darkeye + bug fix in error reporting + + Revision 1.5 2000/11/17 15:50:48 darkeye + added -Wall flag to compiler and eleminated new warnings + + Revision 1.4 2000/11/13 20:05:07 darkeye + changed to workaround to start recording so that it reads one sample + per channel, as opposed to only one sample (which misalignes the channels) + + Revision 1.3 2000/11/12 13:31:40 darkeye + added kdoc-style documentation comments + + Revision 1.2 2000/11/05 14:08:28 darkeye + changed builting to an automake / autoconf environment + + Revision 1.1.1.1 2000/11/05 10:05:53 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/OssDspSource.h b/darkice/tags/darkice-0_7/src/OssDspSource.h new file mode 100644 index 0000000..281ce56 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/OssDspSource.h @@ -0,0 +1,283 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : OssDspSource.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef OSS_DSP_SOURCE_H +#define OSS_DSP_SOURCE_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Reporter.h" +#include "AudioSource.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * An audio input based on /dev/dsp-like raw devices + * + * @author $Author$ + * @version $Revision$ + */ +class OssDspSource : public AudioSource, public virtual Reporter +{ + private: + + /** + * The file name of the OSS DSP device (e.g. /dev/dsp or /dev/dsp0). + */ + char * fileName; + + /** + * The low-level file descriptor of the OSS DSP device. + */ + int fileDescriptor; + + /** + * Indicates wether the low-level OSS DSP device is in a recording + * state. + */ + bool running; + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + OssDspSource ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + /** + * Initialize the object + * + * @param name the file name of the OSS DSP device. + * @exception Exception + */ + void + init ( const char * name ) throw ( Exception ); + + /** + * De-iitialize the object + * + * @exception Exception + */ + void + strip ( void ) throw ( Exception ); + + + public: + + /** + * Constructor. + * + * @param name the file name of the OSS DSP device + * (e.g. /dev/dsp or /dev/dsp0). + * @param sampleRate samples per second (e.g. 44100 for 44.1kHz). + * @param bitsPerSample bits per sample (e.g. 16 bits). + * @param channel number of channels of the audio source + * (e.g. 1 for mono, 2 for stereo, etc.). + * @exception Exception + */ + inline + OssDspSource ( const char * name, + int sampleRate = 44100, + int bitsPerSample = 16, + int channel = 2 ) + throw ( Exception ) + + : AudioSource( sampleRate, bitsPerSample, channel) + { + init( name); + } + + /** + * Copy Constructor. + * + * @param source the object to copy. + * @exception Exception + */ + inline + OssDspSource ( const OssDspSource & ds ) throw ( Exception ) + : AudioSource( ds ) + { + init( ds.fileName); + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~OssDspSource ( void ) throw ( Exception ) + { + strip(); + } + + /** + * Assignment operator. + * + * @param ds the object to assign to this one. + * @return a reference to this object. + * @exception Exception + */ + inline virtual OssDspSource & + operator= ( const OssDspSource & ds ) throw ( Exception ) + { + if ( this != &ds ) { + strip(); + AudioSource::operator=( ds); + init( ds.fileName); + } + return *this; + } + + /** + * Tell if the data from this source comes in big or little endian. + * + * @return false + */ + virtual inline bool + isBigEndian ( void ) const throw () + { + return false; + } + + /** + * Open the OssDspSource. + * This does not put the OSS DSP device into recording mode. + * To start getting samples, call either canRead() or read(). + * + * @return true if opening was successful, false otherwise + * @exception Exception + * + * @see #canRead + * @see #read + */ + virtual bool + open ( void ) throw ( Exception ); + + /** + * Check if the OssDspSource is open. + * + * @return true if the OssDspSource is open, false otherwise. + */ + inline virtual bool + isOpen ( void ) const throw () + { + return fileDescriptor != 0; + } + + /** + * Check if the OssDspSource can be read from. + * Blocks until the specified time for data to be available. + * Puts the OSS DSP device into recording mode. + * + * @param sec the maximum seconds to block. + * @param usec micro seconds to block after the full seconds. + * @return true if the OssDspSource is ready to be read from, + * false otherwise. + * @exception Exception + */ + virtual bool + canRead ( unsigned int sec, + unsigned int usec ) throw ( Exception ); + + /** + * Read from the OssDspSource. + * Puts the OSS DSP device into recording mode. + * + * @param buf the buffer to read into. + * @param len the number of bytes to read into buf + * @return the number of bytes read (may be less than len). + * @exception Exception + */ + virtual unsigned int + read ( void * buf, + unsigned int len ) throw ( Exception ); + + /** + * Close the OssDspSource. + * + * @exception Exception + */ + virtual void + close ( void ) throw ( Exception ); +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* OSS_DSP_SOURCE_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.5 2001/09/18 14:57:19 darkeye + finalized Solaris port + + Revision 1.4 2001/09/02 14:08:40 darkeye + setting the sound card recording sample rate is now more relaxed + there is no error reported if the sample rate is not exactly the same + + Revision 1.3 2000/11/12 13:31:40 darkeye + added kdoc-style documentation comments + + Revision 1.2 2000/11/05 17:37:24 darkeye + removed clone() functions + + Revision 1.1.1.1 2000/11/05 10:05:53 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Ref.h b/darkice/tags/darkice-0_7/src/Ref.h new file mode 100644 index 0000000..e32b723 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Ref.h @@ -0,0 +1,288 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : Ref.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef REF_H +#define REF_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Exception.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * Java-like object reference class. + * Objects used with this reference class have to be descandents + * of class Referable. + * + * sample usage: + * + *
+ *  #include "Ref.h"
+ *  #include "Referable.h"
+ *
+ *  class  A : public virtual Referable;
+ *
+ *  ...
+ *   
+ *  A        * a = new A();
+ *  Ref     ref1 = a;       // 1 reference to a
+ *  Ref     ref2 = ref1;    // 2 references to a
+ *
+ *  ref1 = 0;      // 1 reference to a
+ *  ref2 = 0;      // at this point object a is destroyed
+ *  
+ * + * Based on Tima Saarinen's work, + * http://gamma.nic.fi/~timosa/comp/refcount.html + * + * @ref Referable + * + * @author $Author$ + * @version $Revision$ + */ +template +class Ref +{ + private: + + /** + * The object referenced by this Ref. + * Must be a descandant of Referable. + */ + T* object; + + + protected: + + + public: + + /** + * Default constructor. + */ + inline + Ref ( void ) throw () + { + object = NULL; + } + + /** + * Copy constructor. + * + * @param other the Ref to copy. + * @exception Exception + */ + inline + Ref ( const Ref & other ) throw ( Exception ) + { + object = NULL; + set( other.object); + } + + /** + * Constructor based on an object to reference. + * + * @param obj the object to reference. + * @exception Exception + */ + inline + Ref ( T * obj ) throw ( Exception ) + { + object = obj; + obj->increaseReferenceCount(); + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~Ref ( void ) throw ( Exception ) + { + set( 0 ); + } + + /** + * Operator overload to make the reference seem like a pointer. + * + * @return the pointer to the object referenced. + */ + inline T* + operator->() const throw () + { + if ( !object ) { + throw Exception( __FILE__, __LINE__, + "reference to NULL object"); + } + return object; + } + + /** + * Assignment operator. + * + * @param other the Ref to assign to this one. + * @return a reference to this Ref. + * @exception Exception + */ + inline Ref & + operator= ( Ref other ) throw ( Exception ) + { + set( other.object); + return *this; + } + + /** + * Assignment operator. + * + * @param obj pointer to the object to assign to this Ref. + * @return a reference to this Ref. + * @exception Exception + */ + inline Ref & + operator= ( T* obj ) throw ( Exception ) + { + set( obj); + return *this; + } + + /** + * Set the object referenced. + * Deletes the old referenced object is this was it's last reference. + * + * @param newobj pointer to the object to reference by this Ref. + * @exception Exception + */ + inline void + set ( T* newobj ) throw ( Exception ) + { + // If equal do nothing + if ( newobj == object ) { + return; + } + + // Increase reference count + if ( newobj ) { + newobj->increaseReferenceCount(); + } + + // Decrease the reference count of the old referable + if ( object ) { + if ( object->decreaseReferenceCount() == 0 ) { + delete object; + } + } + + // Assign + object = newobj; + } + + /** + * Return object pointer. This method should be used with + * care because it breaks the encapsulation. + * Typically this method is needed for the method calls + * which require literal object pointer. + * + * It may not be bad idea to pass the Ref + * objects as method arguments. + * + * @return Object pointer or NULL. + */ + inline T* + get ( void ) const throw () + { + return object; + } + + /** + * Equality operator. + * + * @param other the Ref to compare this with. + * @return true is the two Refs refer to the same object, + * false otherwise. + */ + inline bool + operator== ( const Ref & other ) const throw () + { + return object == other.object; + } + + /** + * Unequality operator. + * + * @param other the Ref to compare this with. + * @return false is the two Refs refer to the same object, + * true otherwise. + */ + inline bool + operator!= ( const Ref & other ) const throw () + { + return object != other.object; + } +}; + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* REF_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.3 2000/11/11 14:55:31 darkeye + minor bugfix + + Revision 1.2 2000/11/11 12:33:13 darkeye + added kdoc-style documentation + + Revision 1.1.1.1 2000/11/05 10:05:54 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Referable.h b/darkice/tags/darkice-0_7/src/Referable.h new file mode 100644 index 0000000..87ef065 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Referable.h @@ -0,0 +1,185 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : Referable.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef REFERABLE_H +#define REFERABLE_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Exception.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * Base class for an object for which references can be made + * with the reference class Ref. + * + * usage: + * + *
+ *  class A : public virtual Referable
+ *  {
+ *     ...
+ *  };
+ *  
+ * + * @ref Ref + * + * @author $Author$ + * @version $Revision$ + */ +class Referable +{ + private: + + /** + * Number of references to the object. + */ + unsigned int referenceCount; + + /** + * Maximum number of references before an overflow occurs. + */ + static const + unsigned int maxCount = ~((unsigned int)0); + + + protected: + + /** + * Default constructor. + */ + inline + Referable ( void ) throw () + { + referenceCount = 0; + } + + + /** + * Desctructor. + * + * @exception Exception + */ + inline virtual + ~Referable ( void ) throw ( Exception ) + { + if ( referenceCount > 0 ) { + throw Exception( __FILE__, __LINE__, + "reference count positive in destructor", + referenceCount); + } + } + + + public: + + /** + * Increase reference count. + * + * @return the new reference count. + * @exception Exception + */ + inline unsigned int + increaseReferenceCount ( void ) throw ( Exception ) + { + if ( referenceCount >= maxCount ) { + throw Exception( __FILE__, + __LINE__, + "reference count overflow", + referenceCount ); + } + return ++referenceCount; + } + + /** + * Decrease reference count. + * + * @return the new reference count. + * @exception Exception + */ + inline unsigned int + decreaseReferenceCount ( void ) throw ( Exception ) + { + if ( referenceCount == 0 ) { + throw Exception( __FILE__, __LINE__, + "reference count underflow", + referenceCount ); + } + return --referenceCount; + } + + /** + * Get the reference count. + * + * @return the reference count. + */ + inline unsigned int + getReferenceCount ( void ) const throw () + { + return referenceCount; + } +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* REFERABLE_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.2 2000/11/11 12:33:13 darkeye + added kdoc-style documentation + + Revision 1.1.1.1 2000/11/05 10:05:54 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Reporter.cpp b/darkice/tags/darkice-0_7/src/Reporter.cpp new file mode 100644 index 0000000..beb670d --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Reporter.cpp @@ -0,0 +1,74 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell Reporter + + File : Reporter.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#include + +#include "Reporter.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/*------------------------------------------------------------------------------ + * Initial values for static members of the class + *----------------------------------------------------------------------------*/ +unsigned int Reporter::verbosity = 1; +ostream * Reporter::os = &cout; + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.1 2000/11/16 08:48:43 darkeye + added multiple verbosity-level event reporting and verbosity command + line option + + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Reporter.h b/darkice/tags/darkice-0_7/src/Reporter.h new file mode 100644 index 0000000..a03d288 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Reporter.h @@ -0,0 +1,337 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell Reporter + + File : Reporter.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef REPORTER_H +#define REPORTER_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_UNISTD_H +#include +#else +#error need unistdt.h +#endif + +#ifdef HAVE_TIME_H +#include +#else +#error need time.h +#endif + + +#include + + +#include "Exception.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * Class for reporting events. All objects of this class share + * the same verbosity level. Typical usage is to inherit this class + * and use the report() function to report events. Only reports + * which are of suffucient importance are really reported. + * + * The default verbosity is 1, and the default ostream is cout. + * + * Known problems: this class is not thread-safe. + * + * @author $Author$ + * @version $Revision$ + */ +class Reporter +{ + + private: + + /** + * Verbosity level shared among all Reporter objects + */ + static unsigned int verbosity; + + /** + * The output stream to report to. + */ + static ostream * os; + + /** + * Print timestamp for every report only if verbosity level + * is above this value. + */ + static const unsigned int prefixVerbosity = 3; + + /** + * Print a prefix to each report. + */ + void + printPrefix( void ) throw () + { + if ( verbosity > prefixVerbosity ) { + char str[32]; + time_t now; + + now = time(NULL); + strftime( str, 32, "%H:%M:%S: ", localtime(&now) ); + (*(Reporter::os)) << str; + } + } + + + protected: + + + public: + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~Reporter ( void ) throw ( Exception ) + { + (Reporter::os)->flush(); + } + + /** + * Set the verbosity level. This sets the verbosity for all + * Reporter objects. + * + * @param verbosity the new verbosity level. + */ + inline void + setReportVerbosity ( unsigned int verbosity ) throw () + { + Reporter::verbosity = verbosity; + } + + /** + * Get the verbosity level. + * + * @return the current verbosity level. + */ + inline unsigned int + getReportVerbosity ( void ) throw () + { + return Reporter::verbosity; + } + + /** + * Set the output stream to report to. This setting effects all + * Reporter objects. + * + * @param os the output stream + */ + inline void + setReportOutputStream ( ostream & os ) throw () + { + Reporter::os = &os; + } + + /** + * Get the output stream to report to. + * + * @return the output stream + */ + inline ostream & + getReportOutputStream ( void ) throw () + { + return *(Reporter::os); + } + + /** + * Report an event with a given verbosity. + * + * @param verbosity the importance of the event, with 0 being + * the most important. + * @param t the object to report. Must have an + * ostream & operator<<( ostream&, const T) + * operator overload. + */ + template + inline void + reportEvent ( unsigned int verbosity, + const T t ) throw () + { + if ( Reporter::verbosity >= verbosity ) { + printPrefix(); + (*(Reporter::os)) << t << endl; + } + } + + /** + * Report an event with a given verbosity. + * + * @param verbosity the importance of the event, with 0 being + * the most important. + * @param t the object 1 to report. Must have an + * ostream & operator<<( ostream&, const T) + * operator overload. + * @param u the object 2 to report. Must have an + * ostream & operator<<( ostream&, const U) + * operator overload. + */ + template + inline void + reportEvent ( unsigned int verbosity, + const T t, + const U u ) throw () + { + if ( Reporter::verbosity >= verbosity ) { + printPrefix(); + (*(Reporter::os)) << t << " " + << u << endl; + } + } + + /** + * Report an event with a given verbosity. + * + * @param verbosity the importance of the event, with 0 being + * the most important. + * @param t the object 1 to report. Must have an + * ostream & operator<<( ostream&, const T) + * operator overload. + * @param u the object 2 to report. Must have an + * ostream & operator<<( ostream&, const U) + * operator overload. + * @param v the object 3 to report. Must have an + * ostream & operator<<( ostream&, const V) + * operator overload. + */ + template + inline void + reportEvent ( unsigned int verbosity, + const T t, + const U u, + const V v ) throw () + { + if ( Reporter::verbosity >= verbosity ) { + printPrefix(); + (*(Reporter::os)) << t << " " + << u << " " + << v << endl; + } + } + + /** + * Report an event with a given verbosity. + * + * @param verbosity the importance of the event, with 0 being + * the most important. + * @param t the object 1 to report. Must have an + * ostream & operator<<( ostream&, const T) + * operator overload. + * @param u the object 2 to report. Must have an + * ostream & operator<<( ostream&, const U) + * operator overload. + * @param v the object 3 to report. Must have an + * ostream & operator<<( ostream&, const V) + * operator overload. + * @param w the object 4 to report. Must have an + * ostream & operator<<( ostream&, const W) + * operator overload. + */ + template + inline void + reportEvent ( unsigned int verbosity, + const T t, + const U u, + const V v, + const W w ) throw () + { + if ( Reporter::verbosity >= verbosity ) { + printPrefix(); + (*(Reporter::os)) << t << " " + << u << " " + << v << " " + << w << endl; + } + } +}; + + + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* REPORTER_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.5 2001/09/05 20:11:15 darkeye + removed dependency on locally stored SGI STL header files + now compiler-supplied C++ library STL header files are used + compiles under GNU C++ 3 + hash_map (an SGI extension to STL) replaced with map + std:: namespace prefix added to all STL class references + + Revision 1.4 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.3 2000/12/20 12:47:40 darkeye + added prefixVerbosity value. in a low verbosity setting no time-stamp + prefix is displayed + + Revision 1.2 2000/11/18 11:12:01 darkeye + added timestamp display, removed process id display in reports + changed reportEvent functions to template functions + + Revision 1.1 2000/11/16 08:48:43 darkeye + added multiple verbosity-level event reporting and verbosity command + line option + + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/ShoutCast.cpp b/darkice/tags/darkice-0_7/src/ShoutCast.cpp new file mode 100644 index 0000000..8ee6b2f --- /dev/null +++ b/darkice/tags/darkice-0_7/src/ShoutCast.cpp @@ -0,0 +1,224 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : ShoutCast.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_STDIO_H +#include +#else +#error need stdio.h +#endif + +#ifdef HAVE_STRING_H +#include +#else +#error need string.h +#endif + + +#include "Exception.h" +#include "Source.h" +#include "Sink.h" +#include "Util.h" +#include "ShoutCast.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/*------------------------------------------------------------------------------ + * Size of string conversion buffer + *----------------------------------------------------------------------------*/ +#define STRBUF_SIZE 32 + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Initialize the object + *----------------------------------------------------------------------------*/ +void +ShoutCast :: init ( const char * irc, + const char * aim, + const char * icq ) + throw ( Exception ) +{ + this->irc = irc ? Util::strDup( irc) : 0; + this->aim = aim ? Util::strDup( aim) : 0; + this->icq = icq ? Util::strDup( icq) : 0; +} + + +/*------------------------------------------------------------------------------ + * De-initialize the object + *----------------------------------------------------------------------------*/ +void +ShoutCast :: strip ( void ) throw ( Exception ) +{ + if ( irc ) { + delete[] irc; + } + if ( aim ) { + delete[] aim; + } + if ( icq ) { + delete[] icq; + } +} + + +/*------------------------------------------------------------------------------ + * Log in to the ShoutCast server using the icy login scheme + *----------------------------------------------------------------------------*/ +bool +ShoutCast :: sendLogin ( void ) throw ( Exception ) +{ + Sink * sink = getSink(); + Source * source = getSocket(); + const char * str; + char resp[STRBUF_SIZE]; + unsigned int len; + + if ( !source->isOpen() ) { + return false; + } + if ( !sink->isOpen() ) { + return false; + } + + /* first line is the password in itself */ + str = getPassword(); + sink->write( str, strlen( str)); + str = "\n"; + sink->write( str, strlen( str)); + sink->flush(); + + /* send the icy headers */ + if ( getName() ) { + str = "icy-name:"; + sink->write( str, strlen( str)); + str = getName(); + sink->write( str, strlen( str)); + } + + if ( getUrl() ) { + str = "\nicy-url:"; + sink->write( str, strlen( str)); + str = getUrl(); + sink->write( str, strlen( str)); + } + + if ( getGenre() ) { + str = "\nicy-genre:"; + sink->write( str, strlen( str)); + str = getGenre(); + sink->write( str, strlen( str)); + } + + if ( getIrc() ) { + str = "\nicy-irc:"; + sink->write( str, strlen( str)); + str = getIrc(); + sink->write( str, strlen( str)); + } + + if ( getAim() ) { + str = "\nicy-aim:"; + sink->write( str, strlen( str)); + str = getAim(); + sink->write( str, strlen( str)); + } + + if ( getIcq() ) { + str = "\nicy-icq:"; + sink->write( str, strlen( str)); + str = getIcq(); + sink->write( str, strlen( str)); + } + + str = "\nicy-br:"; + sink->write( str, strlen( str)); + if ( snprintf( resp, STRBUF_SIZE, "%d", getBitRate()) == -1 ) { + throw Exception( __FILE__, __LINE__, "snprintf overflow"); + } + sink->write( resp, strlen( resp)); + + str = "\nicy-pub:"; + sink->write( str, strlen( str)); + str = getIsPublic() ? "yes" : "no"; + sink->write( str, strlen( str)); + + str = "\n\n"; + sink->write( str, strlen( str)); + sink->flush(); + + /* read the anticipated response: "OK" */ + len = source->read( resp, STRBUF_SIZE); + if ( len < 2 || resp[0] != 'O' || resp[1] != 'K' ) { + return false; + } + + /* suck anything that the other side has to say */ + while ( source->canRead( 0, 0) && + (len = source->read( resp, STRBUF_SIZE)) ) { + ; + } + + return true; +} + + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.1 2001/09/09 11:27:31 darkeye + added support for ShoutCast servers + + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/ShoutCast.h b/darkice/tags/darkice-0_7/src/ShoutCast.h new file mode 100644 index 0000000..ec5dd91 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/ShoutCast.h @@ -0,0 +1,266 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : ShoutCast.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef SHOUT_CAST_H +#define SHOUT_CAST_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Sink.h" +#include "TcpSocket.h" +#include "CastSink.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * Class representing output to a ShoutCast server with + * icy login + * + * @author $Author$ + * @version $Revision$ + */ +class ShoutCast : public CastSink +{ + private: + + /** + * IRC info string for the stream + */ + char * irc; + + /** + * AIM info string for the stream + */ + char * aim; + + /** + * ICQ info string for the stream + */ + char * icq; + + /** + * Initalize the object. + * + * @param irc IRC info string for the stream. + * @param aim AIM info string for the stream. + * @param icq ICQ info string for the stream. + * @exception Exception + */ + void + init ( const char * irc, + const char * aim, + const char * icq ) + throw ( Exception ); + + /** + * De-initalize the object. + * + * @exception Exception + */ + void + strip ( void ) throw ( Exception ); + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + ShoutCast ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + /** + * Log in to the server using the socket avialable. + * + * @return true if login was successful, false otherwise. + * @exception Exception + */ + virtual bool + sendLogin ( void ) throw ( Exception ); + + + public: + + /** + * Constructor. + * + * @param socket socket connection to the server. + * @param password password to the server. + * @param name name of the stream. + * @param url URL associated with the stream. + * @param genre genre of the stream. + * @param bitRate bitrate of the stream (e.g. mp3 bitrate). + * @param isPublic is the stream public? + * @param irc IRC info string for the stream. + * @param aim AIM info string for the stream. + * @param icq ICQ info string for the stream. + * @param bufferDuration duration of the BufferedSink buffer + * in seconds. + * @exception Exception + */ + inline + ShoutCast ( TcpSocket * socket, + const char * password, + unsigned int bitRate, + const char * name = 0, + const char * url = 0, + const char * genre = 0, + bool isPublic = false, + const char * irc = 0, + const char * aim = 0, + const char * icq = 0, + unsigned int bufferDuration = 10 ) + throw ( Exception ) + : CastSink( socket, + password, + bitRate, + name, + url, + genre, + isPublic, + bufferDuration ) + { + init( irc, aim, icq); + } + + /** + * Copy constructor. + * + * @param cs the ShoutCast to copy. + */ + inline + ShoutCast( const ShoutCast & cs ) throw ( Exception ) + : CastSink( cs ) + { + init( cs.getIrc(), cs.getAim(), cs.getIcq()); + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~ShoutCast( void ) throw ( Exception ) + { + strip(); + } + + /** + * Assignment operator. + * + * @param cs the ShoutCast to assign this to. + * @return a reference to this ShoutCast. + * @exception Exception + */ + inline virtual ShoutCast & + operator= ( const ShoutCast & cs ) throw ( Exception ) + { + if ( this != &cs ) { + strip(); + CastSink::operator=( cs ); + init( cs.getIrc(), cs.getAim(), cs.getIcq()); + } + return *this; + } + + /** + * Get the IRC info string for the stream. + * + * @return the IRC info string for the stream. + */ + inline const char * + getIrc ( void ) const throw () + { + return irc; + } + + /** + * Get the AIM info string for the stream. + * + * @return the AIM info string for the stream. + */ + inline const char * + getAim ( void ) const throw () + { + return aim; + } + + /** + * Get the ICQ info string for the stream. + * + * @return the ICQ info string for the stream. + */ + inline const char * + getIcq ( void ) const throw () + { + return icq; + } + +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* SHOUT_CAST_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.1 2001/09/09 11:27:31 darkeye + added support for ShoutCast servers + + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Sink.h b/darkice/tags/darkice-0_7/src/Sink.h new file mode 100644 index 0000000..fac29e6 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Sink.h @@ -0,0 +1,198 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : Sink.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef SINK_H +#define SINK_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Referable.h" +#include "Exception.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * A general data sink + * + * @author $Author$ + * @version $Revision$ + */ +class Sink : public virtual Referable +{ + private: + + + protected: + + /** + * Default constructor. + */ + inline + Sink ( void ) throw () + { + } + + /** + * Copy constructor. + * + * @param sink the Sink to copy. + */ + inline + Sink ( const Sink & sink ) throw () + { + } + + /** + * Assignment operator. + * + * @param sink the Sink to assign this to. + * @return a reference to this Sink. + * @exception Exception + */ + inline virtual Sink & + operator= ( const Sink & sink ) throw ( Exception ) + { + return *this; + } + + + public: + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~Sink ( void ) throw ( Exception ) + { + } + + /** + * Open the sink. + * + * @return true if opening was successfull, false otherwise. + * @exception Exception + */ + virtual bool + open ( void ) throw ( Exception ) = 0; + + /** + * Check if the Sink is open. + * + * @return true if the Sink is open, false otherwise. + */ + virtual bool + isOpen ( void ) const throw () = 0; + + /** + * Check if the Sink is ready to accept data. + * Blocks until the specified time for data to be available. + * + * @param sec the maximum seconds to block. + * @param usec micro seconds to block after the full seconds. + * @return true if the Sink is ready to accept data, false otherwise. + * @exception Exception + */ + virtual bool + canWrite ( unsigned int sec, + unsigned int usec ) throw ( Exception ) = 0; + + /** + * Write data to the Sink. + * + * @param buf the data to write. + * @param len number of bytes to write from buf. + * @return the number of bytes written (may be less than len). + * @exception Exception + */ + virtual unsigned int + write ( const void * buf, + unsigned int len ) throw ( Exception ) = 0; + + /** + * Flush all data that was written to the Sink to the underlying + * construct. + * + * @exception Exception + */ + virtual void + flush ( void ) throw ( Exception ) = 0; + + /** + * Close the Sink. + * + * @exception Exception + */ + virtual void + close ( void ) throw ( Exception ) = 0; +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* SINK_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.4 2000/11/12 14:54:25 darkeye + added Exception to throws clause for the destructor and assignment operator + + Revision 1.3 2000/11/12 13:31:16 darkeye + minor change in documentation + + Revision 1.2 2000/11/11 12:33:13 darkeye + added kdoc-style documentation + + Revision 1.1.1.1 2000/11/05 10:05:54 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/SolarisDspSource.cpp b/darkice/tags/darkice-0_7/src/SolarisDspSource.cpp new file mode 100644 index 0000000..3aa12d5 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/SolarisDspSource.cpp @@ -0,0 +1,282 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : SolarisDspSource.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#include "SolarisDspSource.h" + +#ifdef SUPPORT_SOLARIS_DSP +// only compile this code if there is support for it + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_UNISTD_H +#include +#else +#error need unistd.h +#endif + +#ifdef HAVE_STRING_H +#include +#else +#error need string.h +#endif + +#ifdef HAVE_SYS_TYPES_H +#include +#else +#error need sys/types.h +#endif + +#ifdef HAVE_SYS_STAT_H +#include +#else +#error need sys/stat.h +#endif + +#ifdef HAVE_FCNTL_H +#include +#else +#error need fcntl.h +#endif + +#ifdef HAVE_SYS_TIME_H +#include +#else +#error need sys/time.h +#endif + +#ifdef HAVE_SYS_IOCTL_H +#include +#else +#error need sys/ioctl.h +#endif + +#ifdef HAVE_SYS_AUDIO_H +#include +#else +#error need sys/audio.h +#endif + + +#include "Util.h" +#include "Exception.h" +#include "SolarisDspSource.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Initialize the object + *----------------------------------------------------------------------------*/ +void +SolarisDspSource :: init ( const char * name ) throw ( Exception ) +{ + fileName = Util::strDup( name); + fileDescriptor = 0; + running = false; +} + + +/*------------------------------------------------------------------------------ + * De-initialize the object + *----------------------------------------------------------------------------*/ +void +SolarisDspSource :: strip ( void ) throw ( Exception ) +{ + if ( isOpen() ) { + close(); + } + + delete[] fileName; +} + +#include + +/*------------------------------------------------------------------------------ + * Open the audio source + *----------------------------------------------------------------------------*/ +bool +SolarisDspSource :: open ( void ) throw ( Exception ) +{ + audio_info_t audioInfo; + + if ( isOpen() ) { + return false; + } + + if ( (fileDescriptor = ::open( fileName, O_RDONLY)) == -1 ) { + fileDescriptor = 0; + return false; + } + + AUDIO_INITINFO( &audioInfo); + audioInfo.record.sample_rate = getSampleRate(); + audioInfo.record.channels = getChannel(); + audioInfo.record.precision = getBitsPerSample(); + audioInfo.record.encoding = AUDIO_ENCODING_LINEAR; + + if ( ioctl( fileDescriptor, AUDIO_SETINFO, &audioInfo) == -1 ) { + + close(); + throw Exception( __FILE__, __LINE__, "ioctl error"); + } + + if ( audioInfo.record.channels != getChannel() ) { + close(); + throw Exception( __FILE__, __LINE__, + "can't set channels", audioInfo.record.channels); + } + + if ( audioInfo.record.precision != getBitsPerSample() ) { + close(); + throw Exception( __FILE__, __LINE__, + "can't set bits per sample", + audioInfo.record.precision); + } + + if ( audioInfo.record.sample_rate != getSampleRate() ) { + reportEvent( 2, "sound card recording sample rate set to ", + audioInfo.record.sample_rate, + " while trying to set it to ", getSampleRate()); + reportEvent( 2, "this is probably not a problem, but a slight " + "drift in the sound card driver"); + } + + return true; +} + + +/*------------------------------------------------------------------------------ + * Check wether read() would return anything + *----------------------------------------------------------------------------*/ +bool +SolarisDspSource :: canRead ( unsigned int sec, + unsigned int usec ) throw ( Exception ) +{ + fd_set fdset; + struct timeval tv; + int ret; + + if ( !isOpen() ) { + return false; + } + + if ( !running ) { + /* ugly workaround to get the dsp into recording state */ + unsigned char b[getChannel()*getBitsPerSample()/8]; + + read( b, getChannel()*getBitsPerSample()/8); + } + + FD_ZERO( &fdset); + FD_SET( fileDescriptor, &fdset); + tv.tv_sec = sec; + tv.tv_usec = usec; + + ret = select( fileDescriptor + 1, &fdset, NULL, NULL, &tv); + + if ( ret == -1 ) { + throw Exception( __FILE__, __LINE__, "select error"); + } + + return ret > 0; +} + + +/*------------------------------------------------------------------------------ + * Read from the audio source + *----------------------------------------------------------------------------*/ +unsigned int +SolarisDspSource :: read ( void * buf, + unsigned int len ) throw ( Exception ) +{ + ssize_t ret; + + if ( !isOpen() ) { + return 0; + } + + ret = ::read( fileDescriptor, buf, len); + + if ( ret == -1 ) { + throw Exception( __FILE__, __LINE__, "read error"); + } + + running = true; + return ret; +} + + +/*------------------------------------------------------------------------------ + * Close the audio source + *----------------------------------------------------------------------------*/ +void +SolarisDspSource :: close ( void ) throw ( Exception ) +{ + if ( !isOpen() ) { + return; + } + + ::close( fileDescriptor); + fileDescriptor = 0; + running = false; +} + +#endif // SUPPORT_SOLARIS_DSP + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.1 2001/09/11 15:05:21 darkeye + added Solaris support + + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/SolarisDspSource.h b/darkice/tags/darkice-0_7/src/SolarisDspSource.h new file mode 100644 index 0000000..5c8ce4b --- /dev/null +++ b/darkice/tags/darkice-0_7/src/SolarisDspSource.h @@ -0,0 +1,274 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : SolarisDspSource.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef SOLARIS_DSP_SOURCE_H +#define SOLARIS_DSP_SOURCE_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Reporter.h" +#include "AudioSource.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * An audio input based on Solaris /dev/audio devices + * + * @author $Author$ + * @version $Revision$ + */ +class SolarisDspSource : public AudioSource, public virtual Reporter +{ + private: + + /** + * The file name of the OSS DSP device (e.g. /dev/audio) + */ + char * fileName; + + /** + * The low-level file descriptor of the Solaris DSP device. + */ + int fileDescriptor; + + /** + * Indicates wether the low-level Solaris DSP device is in a recording + * state. + */ + bool running; + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + SolarisDspSource ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + /** + * Initialize the object + * + * @param name the file name of the Solaris DSP device. + * @exception Exception + */ + void + init ( const char * name ) throw ( Exception ); + + /** + * De-iitialize the object + * + * @exception Exception + */ + void + strip ( void ) throw ( Exception ); + + + public: + + /** + * Constructor. + * + * @param name the file name of the Solaris DSP device + * (e.g. /dev/audio or /dev/sound/0) + * @param sampleRate samples per second (e.g. 44100 for 44.1kHz). + * @param bitsPerSample bits per sample (e.g. 16 bits). + * @param channel number of channels of the audio source + * (e.g. 1 for mono, 2 for stereo, etc.). + * @exception Exception + */ + inline + SolarisDspSource ( const char * name, + int sampleRate = 44100, + int bitsPerSample = 16, + int channel = 2 ) + throw ( Exception ) + + : AudioSource( sampleRate, bitsPerSample, channel) + { + init( name); + } + + /** + * Copy Constructor. + * + * @param source the object to copy. + * @exception Exception + */ + inline + SolarisDspSource ( const SolarisDspSource & ds ) + throw ( Exception ) + : AudioSource( ds ) + { + init( ds.fileName); + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~SolarisDspSource ( void ) throw ( Exception ) + { + strip(); + } + + /** + * Assignment operator. + * + * @param ds the object to assign to this one. + * @return a reference to this object. + * @exception Exception + */ + inline virtual SolarisDspSource & + operator= ( const SolarisDspSource & ds ) throw ( Exception ) + { + if ( this != &ds ) { + strip(); + AudioSource::operator=( ds); + init( ds.fileName); + } + return *this; + } + + /** + * Tell if the data from this source comes in big or little endian. + * + * @return true + */ + virtual inline bool + isBigEndian ( void ) const throw () + { + return true; + } + + /** + * Open the SolarisDspSource. + * This does not put the Solaris DSP device into recording mode. + * To start getting samples, call either canRead() or read(). + * + * @return true if opening was successful, false otherwise + * @exception Exception + * + * @see #canRead + * @see #read + */ + virtual bool + open ( void ) throw ( Exception ); + + /** + * Check if the SolarisDspSource is open. + * + * @return true if the SolarisDspSource is open, false otherwise. + */ + inline virtual bool + isOpen ( void ) const throw () + { + return fileDescriptor != 0; + } + + /** + * Check if the SolarisDspSource can be read from. + * Blocks until the specified time for data to be available. + * Puts the Solaris DSP device into recording mode. + * + * @param sec the maximum seconds to block. + * @param usec micro seconds to block after the full seconds. + * @return true if the SolarisDspSource is ready to be read from, + * false otherwise. + * @exception Exception + */ + virtual bool + canRead ( unsigned int sec, + unsigned int usec ) throw ( Exception ); + + /** + * Read from the SolarisDspSource. + * Puts the Solaris DSP device into recording mode. + * + * @param buf the buffer to read into. + * @param len the number of bytes to read into buf + * @return the number of bytes read (may be less than len). + * @exception Exception + */ + virtual unsigned int + read ( void * buf, + unsigned int len ) throw ( Exception ); + + /** + * Close the SolarisDspSource. + * + * @exception Exception + */ + virtual void + close ( void ) throw ( Exception ); +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* SOLARIS_DSP_SOURCE_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.2 2001/09/18 14:57:19 darkeye + finalized Solaris port + + Revision 1.1 2001/09/11 15:05:21 darkeye + added Solaris support + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Source.h b/darkice/tags/darkice-0_7/src/Source.h new file mode 100644 index 0000000..a8cac63 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Source.h @@ -0,0 +1,186 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : Source.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef SOURCE_H +#define SOURCE_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Referable.h" +#include "Exception.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * A general data source + * + * @author $Author$ + * @version $Revision$ + */ +class Source : public virtual Referable +{ + private: + + protected: + + /** + * Default Constructor. + * + * @exception Exception + */ + inline + Source ( void ) throw ( Exception ) + { + } + + /** + * Copy Constructor. + * + * @param source the object to copy. + * @exception Exception + */ + inline + Source ( const Source & source ) throw ( Exception ) + { + } + + /** + * Assignment operator. + * + * @param source the object to assign to this one. + * @return a reference to this object. + * @exception Exception + */ + inline virtual Source & + operator= ( const Source & source ) throw ( Exception ) + { + return *this; + } + + + public: + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~Source ( void ) throw ( Exception ) + { + } + + /** + * Open the Source. + * + * @return true if opening was successful, false otherwise + * @exception Exception + */ + virtual bool + open ( void ) throw ( Exception ) = 0; + + /** + * Check if the Source is open. + * + * @return true if the Source is open, false otherwise. + */ + virtual bool + isOpen ( void ) const throw () = 0; + + /** + * Check if the Source can be read from. + * Blocks until the specified time for data to be available. + * + * @param sec the maximum seconds to block. + * @param usec micro seconds to block after the full seconds. + * @return true if the Source is ready to be read from, + * false otherwise. + * @exception Exception + */ + virtual bool + canRead ( unsigned int sec, + unsigned int usec ) throw ( Exception ) = 0; + + /** + * Read from the Source. + * + * @param buf the buffer to read into. + * @param len the number of bytes to read into buf + * @return the number of bytes read (may be less than len). + * @exception Exception + */ + virtual unsigned int + read ( void * buf, + unsigned int len ) throw ( Exception ) = 0; + + /** + * Close the Source. + * + * @exception Exception + */ + virtual void + close ( void ) throw ( Exception ) = 0; +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* SOURCE_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.2 2000/11/12 13:31:40 darkeye + added kdoc-style documentation comments + + Revision 1.1.1.1 2000/11/05 10:05:54 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/TcpSocket.cpp b/darkice/tags/darkice-0_7/src/TcpSocket.cpp new file mode 100644 index 0000000..dcd4039 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/TcpSocket.cpp @@ -0,0 +1,372 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : TcpSocket.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_STRING_H +#include +#else +#error need string.h +#endif + +#ifdef HAVE_SYS_TYPES_H +#include +#else +#error need sys/types.h +#endif + +#ifdef HAVE_ERRNO_H +#include +#else +#error need errno.h +#endif + +#ifdef HAVE_SYS_SOCKET_H +#include +#else +#error need sys/socket.h +#endif + +#ifdef HAVE_NETINET_IN_H +#include +#else +#error need netinet/in.h +#endif + +#ifdef HAVE_NETDB_H +#include +#else +#error need netdb.h +#endif + +#ifdef HAVE_UNISTD_H +#include +#else +#error need unistd.h +#endif + +#ifdef HAVE_SYS_TIME_H +#include +#else +#error need sys/time.h +#endif + + +#include "Util.h" +#include "Exception.h" +#include "TcpSocket.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Initialize the object + *----------------------------------------------------------------------------*/ +void +TcpSocket :: init ( const char * host, + unsigned short port ) throw ( Exception ) +{ + this->host = Util::strDup( host); + this->port = port; + this->sockfd = 0; +} + + +/*------------------------------------------------------------------------------ + * De-initialize the object + *----------------------------------------------------------------------------*/ +void +TcpSocket :: strip ( void) throw ( Exception ) +{ + if ( isOpen() ) { + close(); + } + + delete[] host; +} + + +/*------------------------------------------------------------------------------ + * Copy Constructor + *----------------------------------------------------------------------------*/ +TcpSocket :: TcpSocket ( const TcpSocket & ss ) throw ( Exception ) + : Source( ss), Sink( ss ) +{ + int fd; + + init( ss.host, ss.port); + + if ( (fd = ss.sockfd ? dup( ss.sockfd) : 0) == -1 ) { + strip(); + throw Exception( __FILE__, __LINE__, "dup failure"); + } + + sockfd = fd; +} + + +/*------------------------------------------------------------------------------ + * Assignment operator + *----------------------------------------------------------------------------*/ +TcpSocket & +TcpSocket :: operator= ( const TcpSocket & ss ) throw ( Exception ) +{ + if ( this != &ss ) { + int fd; + + /* first strip */ + strip(); + + + /* then build up */ + Sink::operator=( ss ); + Source::operator=( ss ); + + init( ss.host, ss.port); + + if ( (fd = ss.sockfd ? dup( ss.sockfd) : 0) == -1 ) { + strip(); + throw Exception( __FILE__, __LINE__, "dup failure"); + } + + sockfd = fd; + } + + return *this; +} + + +/*------------------------------------------------------------------------------ + * Open the file + *----------------------------------------------------------------------------*/ +bool +TcpSocket :: open ( void ) throw ( Exception ) +{ + struct sockaddr_in addr; + struct hostent * pHostEntry; + + if ( isOpen() ) { + return false; + } + + if ( !(pHostEntry = gethostbyname( host)) ) { + throw Exception( __FILE__, __LINE__, "gethostbyname error", errno); + } + + if ( (sockfd = socket( AF_INET, SOCK_STREAM, IPPROTO_TCP)) == -1 ) { + throw Exception( __FILE__, __LINE__, "socket error", errno); + } + + memset( &addr, 0, sizeof(addr)); + addr.sin_family = AF_INET; + addr.sin_port = htons(port); + addr.sin_addr.s_addr = *((long*) pHostEntry->h_addr_list[0]); + + if ( connect( sockfd, (struct sockaddr*)&addr, sizeof(addr)) == -1 ) { + ::close( sockfd); + sockfd = 0; + throw Exception( __FILE__, __LINE__, "connect error", errno); + } + + return true; +} + + +/*------------------------------------------------------------------------------ + * Check wether read() would return anything + *----------------------------------------------------------------------------*/ +bool +TcpSocket :: canRead ( unsigned int sec, + unsigned int usec ) throw ( Exception ) +{ + fd_set fdset; + struct timeval tv; + int ret; + + if ( !isOpen() ) { + return false; + } + + FD_ZERO( &fdset); + FD_SET( sockfd, &fdset); + tv.tv_sec = sec; + tv.tv_usec = usec; + + ret = select( sockfd + 1, &fdset, NULL, NULL, &tv); + + if ( ret == -1 ) { + throw Exception( __FILE__, __LINE__, "select error"); + } + + return ret > 0; +} + + +/*------------------------------------------------------------------------------ + * Read from the socket + *----------------------------------------------------------------------------*/ +unsigned int +TcpSocket :: read ( void * buf, + unsigned int len ) throw ( Exception ) +{ + int ret; + + if ( !isOpen() ) { + return 0; + } + + ret = recv( sockfd, buf, len, 0); + + if ( ret == -1 ) { + throw Exception( __FILE__, __LINE__, "recv error", errno); + } + + return ret; +} + + +/*------------------------------------------------------------------------------ + * Check wether read() would return anything + *----------------------------------------------------------------------------*/ +bool +TcpSocket :: canWrite ( unsigned int sec, + unsigned int usec ) throw ( Exception ) +{ + fd_set fdset; + struct timeval tv; + int ret; + + if ( !isOpen() ) { + return false; + } + + FD_ZERO( &fdset); + FD_SET( sockfd, &fdset); + tv.tv_sec = sec; + tv.tv_usec = usec; + + ret = select( sockfd + 1, NULL, &fdset, NULL, &tv); + + if ( ret == -1 ) { + throw Exception( __FILE__, __LINE__, "select error"); + } + + return ret > 0; +} + + +/*------------------------------------------------------------------------------ + * Write to the socket + *----------------------------------------------------------------------------*/ +unsigned int +TcpSocket :: write ( const void * buf, + unsigned int len ) throw ( Exception ) +{ + int ret; + + if ( !isOpen() ) { + return 0; + } + +// ret = send( sockfd, buf, len, MSG_DONTWAIT); + ret = send( sockfd, buf, len, 0); + + if ( ret == -1 ) { + if ( errno == EAGAIN ) { + ret = 0; + } else { + throw Exception( __FILE__, __LINE__, "send error", errno); + } + } + + return ret; +} + + +/*------------------------------------------------------------------------------ + * Close the socket + *----------------------------------------------------------------------------*/ +void +TcpSocket :: close ( void ) throw ( Exception ) +{ + if ( !isOpen() ) { + return; + } + + flush(); + ::close( sockfd); + sockfd = 0; +} + + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.6 2001/09/18 16:44:10 darkeye + TcpSocket did not report closed state when could not connect() + + Revision 1.5 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.4 2000/11/17 15:50:48 darkeye + added -Wall flag to compiler and eleminated new warnings + + Revision 1.3 2000/11/12 14:54:50 darkeye + added kdoc-style documentation comments + + Revision 1.2 2000/11/05 14:08:28 darkeye + changed builting to an automake / autoconf environment + + Revision 1.1.1.1 2000/11/05 10:05:55 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/TcpSocket.h b/darkice/tags/darkice-0_7/src/TcpSocket.h new file mode 100644 index 0000000..df8d4cb --- /dev/null +++ b/darkice/tags/darkice-0_7/src/TcpSocket.h @@ -0,0 +1,297 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : TcpSocket.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef TCP_SOCKET_H +#define TCP_SOCKET_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Source.h" +#include "Sink.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * A TCP network socket + * + * @author $Author$ + * @version $Revision$ + */ +class TcpSocket : public Source, public Sink +{ + private: + + /** + * Name of the host this socket connects to. + */ + char * host; + + /** + * Port to connect to. + */ + unsigned short port; + + /** + * Low-level socket descriptor. + */ + int sockfd; + + /** + * Initialize the object. + * + * @param host name of the host this socket connects to. + * @param port port to connect to. + * @exception Exception + */ + void + init ( const char * host, + unsigned short port ) throw ( Exception ); + + /** + * De-initialize the object. + * + * @exception Exception + */ + void + strip ( void ) throw ( Exception ); + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + TcpSocket ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + + public: + + /** + * Constructor. + * + * @param host name of the host this socket connects to. + * @param port port to connect to. + * @exception Exception + */ + inline + TcpSocket( const char * host, + unsigned short port ) throw ( Exception ) + { + init( host, port); + } + + /** + * Copy constructor. + * + * @param ss the TcpSocket to copy. + * @exception Exception + */ + TcpSocket( const TcpSocket & ss ) throw ( Exception ); + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~TcpSocket( void ) throw ( Exception ) + { + strip(); + } + + /** + * Assignment operator. + * + * @param ss the TcpSocket to assign this to. + * @return a reference to this TcpSocket. + * @exception Exception + */ + inline virtual TcpSocket & + operator= ( const TcpSocket & ss ) throw ( Exception ); + + /** + * Get the host this socket connects to. + * + * @return the host this socket connects to. + */ + inline const char * + getHost ( void ) const throw () + { + return host; + } + + /** + * Get the port this socket connects to. + * + * @return the port this socket connects to. + */ + inline unsigned int + getPort ( void ) const throw () + { + return port; + } + + /** + * Open the TcpSocket. + * + * @return true if opening was successfull, false otherwise. + * @exception Exception + */ + virtual bool + open ( void ) throw ( Exception ); + + /** + * Check if the TcpSocket is open. + * + * @return true if the TcpSocket is open, false otherwise. + */ + inline virtual bool + isOpen ( void ) const throw () + { + return sockfd != 0; + } + + /** + * Check if the TcpScoket can be read from. + * Blocks until the specified time for data to be available. + * + * @param sec the maximum seconds to block. + * @param usec micro seconds to block after the full seconds. + * @return true if the TcpSocket is ready to be read from, + * false otherwise. + * @exception Exception + */ + virtual bool + canRead ( unsigned int sec, + unsigned int usec ) throw ( Exception ); + + /** + * Read from the TcpSocket. + * + * @param buf the buffer to read into. + * @param len the number of bytes to read into buf + * @return the number of bytes read (may be less than len). + * @exception Exception + */ + virtual unsigned int + read ( void * buf, + unsigned int len ) throw ( Exception ); + + + /** + * Check if the TcpSocket is ready to accept data. + * Blocks until the specified time for data to be available. + * + * @param sec the maximum seconds to block. + * @param usec micro seconds to block after the full seconds. + * @return true if the TcpSocket is ready to accept data, + * false otherwise. + * @exception Exception + */ + virtual bool + canWrite ( unsigned int sec, + unsigned int usec ) throw ( Exception ); + + /** + * Write data to the TcpSocket. + * + * @param buf the data to write. + * @param len number of bytes to write from buf. + * @return the number of bytes written (may be less than len). + * @exception Exception + */ + virtual unsigned int + write ( const void * buf, + unsigned int len ) throw ( Exception ); + + /** + * Flush all data that was written to the TcpSocket to the underlying + * connection. + * + * @exception Exception + */ + inline virtual void + flush ( void ) throw ( Exception ) + { + } + + /** + * Close the TcpSocket. + * + * @exception Exception + */ + virtual void + close ( void ) throw ( Exception ); +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* TCP_SOCKET_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.3 2000/11/12 14:54:50 darkeye + added kdoc-style documentation comments + + Revision 1.2 2000/11/05 17:37:24 darkeye + removed clone() functions + + Revision 1.1.1.1 2000/11/05 10:05:55 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Util.cpp b/darkice/tags/darkice-0_7/src/Util.cpp new file mode 100644 index 0000000..c3ad0e6 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Util.cpp @@ -0,0 +1,209 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : Util.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_STRING_H +#include +#else +#error need string.h +#endif + +#ifdef HAVE_STDLIB_H +#include +#else +#error need stdlib.h +#endif + +#ifdef HAVE_LIMITS_H +#include +#else +#error need limits.h +#endif + + +#include "Util.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Calculate the length of a zero-terminated C string, + * w/o the zero-termination + *----------------------------------------------------------------------------*/ +unsigned int +Util :: strLen( const char * str ) throw ( Exception ) +{ + size_t len; + + if ( !str ) { + throw Exception( __FILE__, __LINE__, "no str"); + } + + len = strlen( str); + + return len; +} + + +/*------------------------------------------------------------------------------ + * Copy the contents of a string into another + *----------------------------------------------------------------------------*/ +void +Util :: strCpy ( char * dest, + const char * src ) throw ( Exception ) +{ + if ( !dest || !src ) { + throw Exception( __FILE__, __LINE__, "no src or dest"); + } + + strcpy( dest, src); +} + + +/*------------------------------------------------------------------------------ + * Concatenate the contents of a string onto another + *----------------------------------------------------------------------------*/ +void +Util :: strCat ( char * dest, + const char * src ) throw ( Exception ) +{ + if ( !dest || !src ) { + throw Exception( __FILE__, __LINE__, "no src or dest"); + } + + strcat( dest, src); +} + + +/*------------------------------------------------------------------------------ + * Duplicate a string by allocating space with new[] + * The returned string must be freed with delete[] + *----------------------------------------------------------------------------*/ +char * +Util :: strDup( const char * str ) throw ( Exception ) +{ + size_t len; + char * s; + + if ( !str ) { + throw Exception( __FILE__, __LINE__, "no str"); + } + + len = strlen( str) + 1; + s = new char[len]; + memcpy( s, str, len); + + return s; +} + + +/*------------------------------------------------------------------------------ + * Check wether two strings are equal + *----------------------------------------------------------------------------*/ +bool +Util :: strEq( const char * str1, + const char * str2 ) throw ( Exception ) +{ + if ( !str1 || !str2 ) { + throw Exception( __FILE__, __LINE__, "no str1 or no str2"); + } + + return !strcmp( str1, str2); +} + + +/*------------------------------------------------------------------------------ + * Convert a string to a long integer + *----------------------------------------------------------------------------*/ +long int +Util :: strToL( const char * str, + int base ) throw ( Exception ) +{ + long int val; + char * s; + + if ( !str ) { + throw Exception( __FILE__, __LINE__, "no str"); + } + + val = strtol( str, &s, base); + if ( s == str || val == LONG_MIN || val == LONG_MAX ) { + throw Exception( __FILE__, __LINE__, "number conversion error"); + } + + return val; +} + + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.6 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.5 2000/11/12 13:31:40 darkeye + added kdoc-style documentation comments + + Revision 1.4 2000/11/09 22:04:33 darkeye + added functions strLen strCpy and strCat + + Revision 1.3 2000/11/09 06:44:21 darkeye + added strEq and strToL functions + + Revision 1.2 2000/11/05 14:08:28 darkeye + changed builting to an automake / autoconf environment + + Revision 1.1.1.1 2000/11/05 10:05:55 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/Util.h b/darkice/tags/darkice-0_7/src/Util.h new file mode 100644 index 0000000..0dbf7a9 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/Util.h @@ -0,0 +1,222 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : Util.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef UTIL_H +#define UTIL_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#include "Exception.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * Widely used utilities. + * This class can not be instantiated, but contains useful (?) static + * functions. + * + * Typical usage: + * + *
+ *  #include "Util.h"
+ *  
+ *  char  * str = Util::strDup( otherStr);
+ *  
+ * + * @author $Author$ + * @version $Revision$ + */ +class Util +{ + private: + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + Util ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + /** + * Copy constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + Util ( const Util & e ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + /** + * Destructor. Always throws an Exception. + * + * @exception Exception + */ + inline + ~Util ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + /** + * Assignment operator. Always throws an Exception. + * + * @param u the object to assign to this one. + * @exception Exception + */ + inline Util & + operator= ( const Util & u ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + + + public: + + /** + * Determine a C string's length. + * + * @param str a zero-terminated C string. + * @return length of str + * @exception Exception + */ + static unsigned int + strLen ( const char * str ) throw ( Exception ); + + /** + * Copy a C string into another. + * + * @param dest place for the copy. Storage size must be at least + * Util::strLen(src) + 1 long. + * @param str the string to copy. + * @exception Exception + */ + static void + strCpy ( char * dest, + const char * src ) throw ( Exception ); + + /** + * Concatenate a string to another's end. + * + * @param dest the string to concatenate to. + * Storage size of dest must be at least + * Util::strLen(dest) + Util::strLen(src) + 1 long. + * @param str the string to concatenate. + * @exception Exception + */ + static void + strCat ( char * dest, + const char * src ) throw ( Exception ); + + /** + * Duplicate a string by allocating space with new[]. + * The returned string must be freed with delete[]. + * + * @param str the string to duplicate. + * @exception Exception + */ + static char * + strDup ( const char * str ) throw ( Exception ); + + /** + * Determine wether two string are equal. + * + * @param str1 one of the strings. + * @param str2 the other string. + * @return true if the two strings are equal, false othersize. + * @exception Exception + */ + static bool + strEq ( const char * str1, + const char * str2 ) throw ( Exception ); + + /** + * Convert a string to long. + * + * @param str the string to convert. + * @param base numeric base of number in str. + * @return the value of str as a long int + * @exception Exception + */ + static long int + strToL ( const char * str, + int base = 10 ) throw ( Exception ); +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* UTIL_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.4 2000/11/12 13:31:40 darkeye + added kdoc-style documentation comments + + Revision 1.3 2000/11/09 22:04:33 darkeye + added functions strLen strCpy and strCat + + Revision 1.2 2000/11/09 06:44:21 darkeye + added strEq and strToL functions + + Revision 1.1.1.1 2000/11/05 10:05:55 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/VorbisLibEncoder.cpp b/darkice/tags/darkice-0_7/src/VorbisLibEncoder.cpp new file mode 100644 index 0000000..66ec4c6 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/VorbisLibEncoder.cpp @@ -0,0 +1,377 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : VorbisLibEncoder.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +// compile only if configured for Ogg Vorbis +#ifdef HAVE_VORBIS_LIB + + +#include "Exception.h" +#include "Util.h" +#include "VorbisLibEncoder.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/* =============================================== local function prototypes */ + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Open an encoding session + *----------------------------------------------------------------------------*/ +bool +VorbisLibEncoder :: open ( void ) + throw ( Exception ) +{ + int ret; + + if ( isOpen() ) { + close(); + } + + vorbis_info_init( &vorbisInfo); + if ( (ret = vorbis_encode_init( &vorbisInfo, + getInChannel(), + getInSampleRate(), + getOutBitrate(), + getOutBitrate(), + getOutBitrate() )) ) { + throw Exception( __FILE__, __LINE__, "vorbis encode init error", ret); + } + + if ( (ret = vorbis_analysis_init( &vorbisDspState, &vorbisInfo)) ) { + throw Exception( __FILE__, __LINE__, "vorbis analysis init error", ret); + } + + if ( (ret = vorbis_block_init( &vorbisDspState, &vorbisBlock)) ) { + throw Exception( __FILE__, __LINE__, "vorbis block init error", ret); + } + + if ( (ret = ogg_stream_init( &oggStreamState, 0)) ) { + throw Exception( __FILE__, __LINE__, "ogg stream init error", ret); + } + + // open the underlying sink + if ( !sink->open() ) { + throw Exception( __FILE__, __LINE__, + "vorbis lib opening underlying sink error"); + } + + // create an empty vorbis_comment structure + vorbis_comment vorbisComment; + + vorbis_comment_init( &vorbisComment); + + // create the vorbis stream headers and send them to the underlying sink + ogg_packet header; + ogg_packet commentHeader; + ogg_packet codeHeader; + + if ( (ret = vorbis_analysis_headerout( &vorbisDspState, + &vorbisComment, + &header, + &commentHeader, + &codeHeader )) ) { + throw Exception( __FILE__, __LINE__, "vorbis header init error", ret); + } + + vorbis_comment_clear( &vorbisComment ); + + ogg_stream_packetin( &oggStreamState, &header); + ogg_stream_packetin( &oggStreamState, &commentHeader); + ogg_stream_packetin( &oggStreamState, &codeHeader); + + ogg_page oggPage; + while ( ogg_stream_flush( &oggStreamState, &oggPage) ) { + sink->write( oggPage.header, oggPage.header_len); + sink->write( oggPage.body, oggPage.body_len); + } + + encoderOpen = true; + + return true; +} + +/*------------------------------------------------------------------------------ + * Convert an unsigned char buffer holding 8 bit PCM values with channels + * interleaved to two float buffers (one for each channel) + *----------------------------------------------------------------------------*/ +void +VorbisLibEncoder :: conv8 ( unsigned char * pcmBuffer, + unsigned int lenPcmBuffer, + float * leftBuffer, + float * rightBuffer, + unsigned int channels ) +{ + if ( channels == 1 ) { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + short int value; + + value = pcmBuffer[i++]; + leftBuffer[j] = ((float) value) / 128.f; + ++j; + } + } else { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + short int value; + + value = pcmBuffer[i++]; + leftBuffer[j] = ((float) value) / 128.f; + value = pcmBuffer[i++]; + rightBuffer[j] = ((float) value) / 128.f; + ++j; + } + } +} + + +/*------------------------------------------------------------------------------ + * Convert an unsigned char buffer holding 16 bit PCM values with channels + * interleaved to two float buffers (one for each channel) + *----------------------------------------------------------------------------*/ +void +VorbisLibEncoder :: conv16 ( unsigned char * pcmBuffer, + unsigned int lenPcmBuffer, + float * leftBuffer, + float * rightBuffer, + unsigned int channels ) +{ + if ( isInBigEndian() ) { + if ( channels == 1 ) { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + short int value; + + value = pcmBuffer[i++] << 8; + value |= pcmBuffer[i++]; + leftBuffer[j] = ((float) value) / 32768.f; + ++j; + } + } else { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + short int value; + + value = pcmBuffer[i++] << 8; + value |= pcmBuffer[i++]; + leftBuffer[j] = ((float) value) / 32768.f; + value = pcmBuffer[i++] << 8; + value |= pcmBuffer[i++]; + rightBuffer[j] = ((float) value) / 32768.f; + ++j; + } + } + } else { + if ( channels == 1 ) { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + short int value; + + value = pcmBuffer[i++]; + value |= pcmBuffer[i++] << 8; + leftBuffer[j] = ((float) value) / 32768.f; + ++j; + } + } else { + unsigned int i, j; + + for ( i = 0, j = 0; i < lenPcmBuffer; ) { + short int value; + + value = pcmBuffer[i++]; + value |= pcmBuffer[i++] << 8; + leftBuffer[j] = ((float) value) / 32768.f; + value = pcmBuffer[i++]; + value |= pcmBuffer[i++] << 8; + rightBuffer[j] = ((float) value) / 32768.f; + ++j; + } + } + } +} + + +/*------------------------------------------------------------------------------ + * Write data to the encoder + *----------------------------------------------------------------------------*/ +unsigned int +VorbisLibEncoder :: write ( const void * buf, + unsigned int len ) throw ( Exception ) +{ + if ( !isOpen() ) { + return 0; + } + + unsigned int bitsPerSample = getInBitsPerSample(); + unsigned int channels = getInChannel(); + + if ( channels != 1 && channels != 2 ) { + throw Exception( __FILE__, __LINE__, + "unsupported number of channels for the encoder", + channels ); + } + + unsigned int sampleSize = (bitsPerSample / 8) * channels; + unsigned char * b = (unsigned char*) buf; + unsigned int processed = len - (len % sampleSize); + unsigned int nSamples = processed / sampleSize; + float ** vorbisBuffer; + + vorbisBuffer = vorbis_analysis_buffer( &vorbisDspState, nSamples); + + if ( bitsPerSample == 8 ) { + conv8( b, processed, vorbisBuffer[0], vorbisBuffer[1], channels); + } else if ( bitsPerSample == 16 ) { + conv16( b, processed, vorbisBuffer[0], vorbisBuffer[1], channels); + } else { + throw Exception( __FILE__, __LINE__, + "unsupported number of bits per sample for the encoder", + bitsPerSample ); + } + + vorbis_analysis_wrote( &vorbisDspState, nSamples); + vorbisBlocksOut(); + + return processed; +} + + +/*------------------------------------------------------------------------------ + * Flush the data from the encoder + *----------------------------------------------------------------------------*/ +void +VorbisLibEncoder :: flush ( void ) + throw ( Exception ) +{ + if ( !isOpen() ) { + return; + } + + vorbis_analysis_wrote( &vorbisDspState, 0); + vorbisBlocksOut(); + sink->flush(); +} + + +/*------------------------------------------------------------------------------ + * Send pending Vorbis blocks to the underlying stream + *----------------------------------------------------------------------------*/ +void +VorbisLibEncoder :: vorbisBlocksOut ( void ) throw () +{ + while ( 1 == vorbis_analysis_blockout( &vorbisDspState, &vorbisBlock) ) { + ogg_packet oggPacket; + ogg_page oggPage; + + vorbis_analysis( &vorbisBlock, &oggPacket); + ogg_stream_packetin( &oggStreamState, &oggPacket); + + while ( ogg_stream_pageout( &oggStreamState, &oggPage) ) { + int written; + + written = sink->write( oggPage.header, oggPage.header_len); + written += sink->write( oggPage.body, oggPage.body_len); + + if ( written < oggPage.header_len + oggPage.body_len ) { + // just let go data that could not be written + reportEvent( 2, + "couldn't write full vorbis data to underlying sink", + oggPage.header_len + oggPage.body_len - written); + } + } + } +} + + +/*------------------------------------------------------------------------------ + * Close the encoding session + *----------------------------------------------------------------------------*/ +void +VorbisLibEncoder :: close ( void ) throw ( Exception ) +{ + if ( isOpen() ) { + flush(); + + ogg_stream_clear( &oggStreamState); + vorbis_block_clear( &vorbisBlock); + vorbis_dsp_clear( &vorbisDspState); + vorbis_info_clear( &vorbisInfo); + + encoderOpen = false; + } +} + + +#endif // HAVE_VORBIS_LIB + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.4 2001/10/19 12:39:42 darkeye + created configure options to compile with or without lame / Ogg Vorbis + + Revision 1.3 2001/09/18 14:57:19 darkeye + finalized Solaris port + + Revision 1.2 2001/09/15 11:36:22 darkeye + added function vorbisBlocksOut(), finalized vorbis support + + Revision 1.1 2001/09/14 19:31:06 darkeye + added IceCast2 / vorbis support + + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/VorbisLibEncoder.h b/darkice/tags/darkice-0_7/src/VorbisLibEncoder.h new file mode 100644 index 0000000..5308f30 --- /dev/null +++ b/darkice/tags/darkice-0_7/src/VorbisLibEncoder.h @@ -0,0 +1,457 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : VorbisLibEncoder.h + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Copyright notice: + + 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. + +------------------------------------------------------------------------------*/ +#ifndef VORBIS_LIB_ENCODER_H +#define VORBIS_LIB_ENCODER_H + +#ifndef __cplusplus +#error This is a C++ include file +#endif + + +/* ============================================================ include files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_VORBIS_LIB +#include +#else +#error configure for Ogg Vorbis +#endif + + +#include "Ref.h" +#include "Exception.h" +#include "Reporter.h" +#include "AudioEncoder.h" +#include "Sink.h" + + +/* ================================================================ constants */ + + +/* =================================================================== macros */ + + +/* =============================================================== data types */ + +/** + * A class representing the ogg vorbis encoder linked as a shared object or + * as a static library. + * + * @author $Author$ + * @version $Revision$ + */ +class VorbisLibEncoder : public AudioEncoder, public virtual Reporter +{ + private: + + /** + * Value indicating if the encoding process is going on + */ + bool encoderOpen; + + /** + * Ogg Vorbis library global info + */ + vorbis_info vorbisInfo; + + /** + * Ogg Vorbis library global DSP state + */ + vorbis_dsp_state vorbisDspState; + + /** + * Ogg Vorbis library global block + */ + vorbis_block vorbisBlock; + + /** + * Ogg library global stream state + */ + ogg_stream_state oggStreamState; + + /** + * The Sink to dump mp3 data to + */ + Ref sink; + + /** + * Initialize the object. + * + * @param sink the sink to send mp3 output to + * @exception Exception + */ + inline void + init ( Sink * sink ) throw ( Exception ) + { + this->sink = sink; + + if ( getInBitsPerSample() != 16 && getInBitsPerSample() != 8 ) { + throw Exception( __FILE__, __LINE__, + "specified bits per sample not supported", + getInBitsPerSample() ); + } + + if ( getOutSampleRate() != getInSampleRate() ) { + throw Exception( __FILE__, __LINE__, + "different in and out sample rate not supported"); + } + + if ( getInChannel() != getOutChannel() ) { + throw Exception( __FILE__, __LINE__, + "different in and out channels not supported"); + } + + encoderOpen = false; + } + + /** + * De-initialize the object. + * + * @exception Exception + */ + inline void + strip ( void ) throw ( Exception ) + { + } + + /** + * Convert a char buffer holding 8 bit PCM values to a short buffer + * + * @param pcmBuffer buffer holding 8 bit PCM audio values, + * channels are interleaved + * @param lenPcmBuffer length of pcmBuffer + * @param leftBuffer put the left channel here (must be big enough) + * @param rightBuffer put the right channel here (if mono, not + * touched, must be big enough) + * @param channels number of channels (1 = mono, 2 = stereo) + */ + void + conv8 ( unsigned char * pcmBuffer, + unsigned int lenPcmBuffer, + float * leftBuffer, + float * rightBuffer, + unsigned int channels ); + + /** + * Convert a char buffer holding 16 bit PCM values to a short buffer + * + * @param pcmBuffer buffer holding 16 bit PCM audio values, + * channels are interleaved + * @param lenPcmBuffer length of pcmBuffer + * @param leftBuffer put the left channel here (must be big enough) + * @param rightBuffer put the right channel here (if mono, not + * touched, must be big enough) + * @param channels number of channels (1 = mono, 2 = stereo) + */ + void + conv16 ( unsigned char * pcmBuffer, + unsigned int lenPcmBuffer, + float * leftBuffer, + float * rightBuffer, + unsigned int channels ); + + /** + * Send pending Vorbis blocks to the underlying stream + */ + void + vorbisBlocksOut( void ) throw (); + + + protected: + + /** + * Default constructor. Always throws an Exception. + * + * @exception Exception + */ + inline + VorbisLibEncoder ( void ) throw ( Exception ) + { + throw Exception( __FILE__, __LINE__); + } + + + public: + + /** + * Constructor. + * + * @param sink the sink to send mp3 output to + * @param inSampleRate sample rate of the input. + * @param inBitsPerSample number of bits per sample of the input. + * @param inChannel number of channels of the input. + * @param outBitrate bit rate of the output (bits/sec). + * @param outSampleRate sample rate of the output. + * If 0, inSampleRate is used. + * @param outChannel number of channels of the output. + * If 0, inChannel is used. + * @exception Exception + */ + inline + VorbisLibEncoder ( Sink * sink, + unsigned int inSampleRate, + unsigned int inBitsPerSample, + unsigned int inChannel, + unsigned int outBitrate, + unsigned int outSampleRate = 0, + unsigned int outChannel = 0 ) + throw ( Exception ) + + : AudioEncoder ( inSampleRate, + inBitsPerSample, + inChannel, + outBitrate, + outSampleRate, + outChannel ) + { + init( sink); + } + + /** + * Constructor. + * + * @param sink the sink to send mp3 output to + * @param as get input sample rate, bits per sample and channels + * from this AudioSource. + * @param outBitrate bit rate of the output (bits/sec). + * @param outSampleRate sample rate of the output. + * If 0, input sample rate is used. + * @param outChannel number of channels of the output. + * If 0, input channel is used. + * @exception Exception + */ + inline + VorbisLibEncoder ( Sink * sink, + const AudioSource * as, + unsigned int outBitrate, + unsigned int outSampleRate = 0, + unsigned int outChannel = 0 ) + throw ( Exception ) + + : AudioEncoder ( as, + outBitrate, + outSampleRate, + outChannel ) + { + init( sink); + } + + /** + * Copy constructor. + * + * @param encoder the VorbisLibEncoder to copy. + */ + inline + VorbisLibEncoder ( const VorbisLibEncoder & encoder ) + throw ( Exception ) + : AudioEncoder( encoder ) + { + if( encoder.isOpen() ) { + throw Exception(__FILE__, __LINE__, "don't copy open encoders"); + } + init( encoder.sink.get()); + } + + /** + * Destructor. + * + * @exception Exception + */ + inline virtual + ~VorbisLibEncoder ( void ) throw ( Exception ) + { + if ( isOpen() ) { + close(); + } + strip(); + } + + /** + * Assignment operator. + * + * @param encoder the VorbisLibEncoder to assign this to. + * @return a reference to this VorbisLibEncoder. + * @exception Exception + */ + inline virtual VorbisLibEncoder & + operator= ( const VorbisLibEncoder & encoder ) throw ( Exception ) + { + if( encoder.isOpen() ) { + throw Exception(__FILE__, __LINE__, "don't copy open encoders"); + } + + if ( this != &encoder ) { + strip(); + AudioEncoder::operator=( encoder); + init( encoder.sink.get()); + } + + return *this; + } + + /** + * Check wether encoding is in progress. + * + * @return true if encoding is in progress, false otherwise. + */ + inline virtual bool + isRunning ( void ) const throw () + { + return isOpen(); + } + + /** + * Start encoding. This function returns as soon as possible, + * with encoding started in the background. + * + * @return true if encoding has started, false otherwise. + * @exception Exception + */ + inline virtual bool + start ( void ) throw ( Exception ) + { + return open(); + } + + /** + * Stop encoding. Stops the encoding running in the background. + * + * @exception Exception + */ + inline virtual void + stop ( void ) throw ( Exception ) + { + return close(); + } + + /** + * Open an encoding session. + * + * @return true if opening was successfull, false otherwise. + * @exception Exception + */ + virtual bool + open ( void ) throw ( Exception ); + + /** + * Check if the encoding session is open. + * + * @return true if the encoding session is open, false otherwise. + */ + inline virtual bool + isOpen ( void ) const throw () + { + return encoderOpen; + } + + /** + * Check if the encoder is ready to accept data. + * + * @param sec the maximum seconds to block. + * @param usec micro seconds to block after the full seconds. + * @return true if the encoder is ready to accept data, + * false otherwise. + * @exception Exception + */ + inline virtual bool + canWrite ( unsigned int sec, + unsigned int usec ) throw ( Exception ) + { + if ( !isOpen() ) { + return false; + } + + return true; + } + + /** + * Write data to the encoder. + * Buf is expected to be a sequence of big-endian 16 bit values, + * with left and right channels interleaved. Len is the number of + * bytes, must be a multiple of 4. + * + * @param buf the data to write. + * @param len number of bytes to write from buf. + * @return the number of bytes written (may be less than len). + * @exception Exception + */ + virtual unsigned int + write ( const void * buf, + unsigned int len ) throw ( Exception ); + + /** + * Flush all data that was written to the encoder to the underlying + * connection. + * + * @exception Exception + */ + virtual void + flush ( void ) throw ( Exception ); + + /** + * Close the encoding session. + * + * @exception Exception + */ + virtual void + close ( void ) throw ( Exception ); +}; + + +/* ================================================= external data structures */ + + +/* ====================================================== function prototypes */ + + + +#endif /* VORBIS_LIB_ENCODER_H */ + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.3 2001/10/19 12:39:42 darkeye + created configure options to compile with or without lame / Ogg Vorbis + + Revision 1.2 2001/09/15 11:36:22 darkeye + added function vorbisBlocksOut(), finalized vorbis support + + Revision 1.1 2001/09/14 19:31:06 darkeye + added IceCast2 / vorbis support + + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/src/main.cpp b/darkice/tags/darkice-0_7/src/main.cpp new file mode 100644 index 0000000..f3f05bf --- /dev/null +++ b/darkice/tags/darkice-0_7/src/main.cpp @@ -0,0 +1,198 @@ +/*------------------------------------------------------------------------------ + + Copyright (c) 2000 Tyrell Corporation. All rights reserved. + + Tyrell DarkIce + + File : main.cpp + Version : $Revision$ + Author : $Author$ + Location : $Source$ + + Abstract : + + Program entry point + + Copyright notice: + + 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 files */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef HAVE_STDLIB_H +#include +#else +#error needs stdlib.h +#endif + +#include +#include + +#include "Ref.h" +#include "Exception.h" +#include "Util.h" +#include "DarkIce.h" + + +/* =================================================== local data structures */ + + +/* ================================================ local constants & macros */ + +/*------------------------------------------------------------------------------ + * File identity + *----------------------------------------------------------------------------*/ +static const char fileid[] = "$Id$"; + + +/* =============================================== local function prototypes */ + +/*------------------------------------------------------------------------------ + * Show program usage + *----------------------------------------------------------------------------*/ +static void +showUsage ( ostream & os ); + + +/* ============================================================= module code */ + +/*------------------------------------------------------------------------------ + * Program entry point + *----------------------------------------------------------------------------*/ +int +main ( + int argc, + char * argv[] ) +{ + int res = -1; + + cout << "DarkIce " << VERSION + << " live audio streamer, http://darkice.sourceforge.net" << endl; + cout << "Copyright (c) 2000-2001, Tyrell Hungary, http://tyrell.hu" << endl; + cout << endl; + + try { + const char * configFileName = 0; + unsigned int verbosity = 1; + int i; + const char opts[] = "hc:v:"; + + while ( (i = getopt( argc, argv, opts)) != -1 ) { + switch ( i ) { + case 'c': + configFileName = optarg; + break; + + case 'v': + verbosity = Util::strToL( optarg); + break; + + default: + case ':': + case '?': + case 'h': + showUsage( cout); + return 1; + } + } + + if ( !configFileName ) { + showUsage( cout); + throw Exception( __FILE__, __LINE__, + "no configuration file specified"); + } + + cout << "Using config file: " << configFileName << endl; + + ifstream configFile( configFileName); + Config config( configFile); + Ref di = new DarkIce( config); + di->setReportVerbosity( verbosity ); + di->setReportOutputStream( cout ); + + res = di->run(); + + } catch ( Exception & e ) { + cout << "DarkIce: " << e << endl << flush; + } + + return res; +} + + +/*------------------------------------------------------------------------------ + * Show program usage + *----------------------------------------------------------------------------*/ +static void +showUsage ( ostream & os ) +{ + os + << "usage: darkice -c config.file" + << endl + << endl + << "options:" + << endl + << " -c config.file use configuration file config.file" + << endl + << " -v n verbosity level (0 = silent, 10 = loud)" + << endl + << " -h print this message and exit" + << endl + << endl; +} + + +/*------------------------------------------------------------------------------ + + $Source$ + + $Log$ + Revision 1.9 2001/09/11 15:05:21 darkeye + added Solaris support + + Revision 1.8 2001/09/02 12:24:29 darkeye + now displays usage info when no command line parameters given + + Revision 1.7 2001/08/30 17:25:56 darkeye + renamed configure.h to config.h + + Revision 1.6 2001/08/26 08:43:13 darkeye + added support for unlimited time encoding + + Revision 1.5 2000/11/15 18:08:43 darkeye + added multiple verbosity-level event reporting and verbosity command + line option + + Revision 1.4 2000/11/13 20:21:29 darkeye + added program version display on startup + + Revision 1.3 2000/11/13 19:38:55 darkeye + moved command line parameter parsing from DarkIce.cpp to main.cpp + + Revision 1.2 2000/11/08 17:29:50 darkeye + added configuration file reader + + Revision 1.1.1.1 2000/11/05 10:05:52 darkeye + initial version + + +------------------------------------------------------------------------------*/ + diff --git a/darkice/tags/darkice-0_7/stamp-h.in b/darkice/tags/darkice-0_7/stamp-h.in new file mode 100644 index 0000000..9788f70 --- /dev/null +++ b/darkice/tags/darkice-0_7/stamp-h.in @@ -0,0 +1 @@ +timestamp diff --git a/darkice/tags/darkice-0_7/update-conf b/darkice/tags/darkice-0_7/update-conf new file mode 100755 index 0000000..3b0242b --- /dev/null +++ b/darkice/tags/darkice-0_7/update-conf @@ -0,0 +1,10 @@ +#!/bin/sh +# +# Update the automake / autoconf configuration +# + +rm -f config.cache config.log config.status +rm -f configure config.h config.h.in aclocal.m4 +rm -f Makefile Makefile.in */Makefile */Makefile.in +autoheader && automake && aclocal && autoheader && autoconf && ./configure +