Compare commits

..

13 Commits

Author SHA1 Message Date
Max Kellermann
1b5f33a435 release v0.18.20 2014-12-08 14:57:17 +01:00
Max Kellermann
41b4a63f2b decoder/ffmpeg: support FFmpeg 2.5
Version 2.5 fixed an API oddity, however it broke API compatibility,
at least with C++.  Disable the workaround when a libavformat version
is detected that is recent enough.
2014-12-08 14:25:34 +01:00
Max Kellermann
d8fc2db910 thread/Id: drop "::" prefix before pthread function names
The "::" to explicitly refer to the global namespace appeared like a
good idea in C++, but it breaks with C libraries that implement
standard functions using macros (e.g. musl).
2014-12-08 14:17:17 +01:00
Max Kellermann
dc11dea7cc configure.ac: prepare for 0.18.20 2014-12-08 14:13:20 +01:00
Max Kellermann
04f627c2af release v0.18.19 2014-11-26 19:58:48 +01:00
Max Kellermann
a254f5a3a8 archive/zzip: fix inverted error handler
Set the Error when zzip_seek()==-1 and not on success.  Fixes a crash
after seeking.
2014-11-24 22:08:50 +01:00
Max Kellermann
143c735f96 configure.ac: prepare for 0.18.19 2014-11-24 22:08:50 +01:00
Max Kellermann
7aa2104596 release v0.18.18 2014-11-18 21:34:03 +01:00
Max Kellermann
c8b93d6573 Client: assume uid==0 is local socket
A negative uid value means it's not a "local socket" (PF_LOCAL).
uid==0 means user "root" connected.
2014-11-18 20:56:27 +01:00
Max Kellermann
3f5f96ac91 event/ServerSocket: fix get_remote_uid() error value
Must return -1 on error, not 0.  0 is root.
2014-11-18 20:53:59 +01:00
Florent Le Coz
7e7b403043 Construct a Null AllocatedPath if the filename conversion into UTF8 failed 2014-11-11 17:15:19 +01:00
Max Kellermann
c64ad78c7b decoder/ffmpeg: support opus 2014-11-10 18:00:30 +01:00
Max Kellermann
4a043a915f configure.ac: prepare for 0.18.1 2014-11-10 17:59:06 +01:00
1102 changed files with 24009 additions and 51696 deletions

133
.gitignore vendored
View File

@@ -6,76 +6,75 @@
*.lo *.lo
*.o *.o
*.exe *.exe
*~
.#*
.stgit*
.deps .deps
.dirstamp .dirstamp
Makefile
Makefile.in
aclocal.m4
autom4te.cache
compile
config.guess
config.h
config.h.in
config.log
config.mk
config.status
config.sub
config_detected.h
config_detected.mk
configure
configure.lineno
depcomp
depmode
install-sh
libtool
ltmain.sh
missing
mkinstalldirs
/test-driver
mpd
mpd.service
stamp-h1
tags tags
*~
/Makefile .#*
/Makefile.in .stgit*
/aclocal.m4 src/dsd2pcm/dsd2pcm
/autom4te.cache src/win32/mpd_win32_rc.rc
/config.h doc/doxygen.conf
/config.h.in doc/protocol.html
/config.log doc/protocol
/config.mk doc/user
/config.status doc/developer
/config_detected.h doc/sticker
/config_detected.mk doc/api
/configure test/software_volume
/configure.lineno test/run_convert
/depmode test/run_decoder
/libtool test/read_tags
/ltmain.sh test/run_filter
/mkinstalldirs test/run_encoder
/build test/run_output
/src/mpd test/read_conf
/systemd/mpd.service test/run_input
/stamp-h1 test/read_mixer
test/dump_playlist
/src/dsd2pcm/dsd2pcm test/run_normalize
/src/win32/mpd_win32_rc.rc test/tmp
test/run_inotify
/doc/doxygen.conf test/test_queue_priority
/doc/protocol.html test/test_protocol
/doc/protocol test/run_ntp_server
/doc/user test/run_resolver
/doc/developer test/run_tcp_connect
/doc/sticker test/test_pcm
/doc/api test/dump_rva2
test/dump_text_file
/test/software_volume test/test_util
/test/run_convert test/test_byte_reverse
/test/run_decoder test/test_mixramp
/test/read_tags test/test_vorbis_encoder
/test/run_filter test/DumpDatabase
/test/run_encoder
/test/run_output
/test/read_conf
/test/run_input
/test/read_mixer
/test/dump_playlist
/test/run_normalize
/test/tmp
/test/run_inotify
/test/test_queue_priority
/test/test_protocol
/test/run_ntp_server
/test/run_resolver
/test/run_tcp_connect
/test/test_pcm
/test/dump_rva2
/test/dump_text_file
/test/test_util
/test/test_byte_reverse
/test/test_mixramp
/test/test_vorbis_encoder
/test/DumpDatabase
/*.tar.gz /*.tar.gz
/*.tar.bz2 /*.tar.bz2

View File

@@ -1,5 +1,5 @@
Music Player Daemon - http://www.musicpd.org Music Player Daemon - http://www.musicpd.org
Copyright (C) 2003-2014 The Music Player Daemon Project Copyright (C) 2003-2013 The Music Player Daemon Project
The following people have contributed code to MPD: The following people have contributed code to MPD:

View File

@@ -16,8 +16,6 @@ gcc 4.6 or later - http://gcc.gnu.org/
clang 3.2 or later - http://clang.llvm.org/ clang 3.2 or later - http://clang.llvm.org/
Any other C++11 compliant compiler should also work. Any other C++11 compliant compiler should also work.
Boost 1.46 - http://www.boost.org/
GLib 2.28 - http://www.gtk.org/ GLib 2.28 - http://www.gtk.org/
General-purpose utility library. General-purpose utility library.
@@ -119,9 +117,6 @@ For AdLib playback.
despotify - https://github.com/SimonKagstrom/despotify despotify - https://github.com/SimonKagstrom/despotify
For Spotify playback. For Spotify playback.
MP4v2 - https://code.google.com/p/mp4v2/
For MP4 playback. You will need FAAD2.
Optional Miscellaneous Dependencies Optional Miscellaneous Dependencies
----------------------------------- -----------------------------------

File diff suppressed because it is too large Load Diff

113
NEWS
View File

@@ -1,107 +1,17 @@
ver 0.19.2 (2014/11/02) ver 0.18.20 (2014/12/08)
* input
- curl: fix redirected streams
* playlist
- don't allow empty playlist name
- m3u: don't ignore unterminated last line
- m3u: recognize the file suffix ".m3u8"
* decoder * decoder
- ignore URI query string for plugin detection - ffmpeg: support FFmpeg 2.5
- faad: remove workaround for ancient libfaad2 ABI bug * fix build failure with musl
- ffmpeg: recognize MIME type audio/aacp
- mad: fix negative replay gain values
* output
- fix memory leak after filter initialization error
- fall back to PCM if given DSD sample rate is not supported
* fix assertion failure on unsupported PCM conversion
* auto-disable plugins that require GLib when --disable-glib is used
ver 0.19.1 (2014/10/19) ver 0.18.19 (2014/11/26)
* input
- mms: fix deadlock bug
* playlist
- extm3u: fix Extended M3U detection
- m3u, extm3u, cue: fix truncated lines
* fix build failure on Mac OS X
* add missing file systemd/mpd.socket to tarball
ver 0.19 (2014/10/10)
* protocol
- new commands "addtagid", "cleartagid", "listfiles", "listmounts",
"listneighbors", "mount", "rangeid", "unmount"
- "lsinfo" and "readcomments" allowed for remote files
- "listneighbors" lists file servers on the local network
- "playlistadd" supports file:///
- "idle" with unrecognized event name fails
- "list" on album artist falls back to the artist tag
- "list" and "count" allow grouping
- new "search"/"find" filter "modified-since"
- "seek*" allows fractional position
- close connection after syntax error
* database
- proxy: forward "idle" events
- proxy: forward the "update" command
- proxy: copy "Last-Modified" from remote directories
- simple: compress the database file using gzip
- upnp: new plugin
- cancel the update on shutdown
* storage
- music_directory can point to a remote file server
- nfs: new plugin
- smbclient: new plugin
* playlist
- cue: fix bogus duration of the last track
- cue: restore CUE tracks from state file
- soundcloud: use https instead of http
- soundcloud: add default API key
* archive * archive
- read tags from songs in an archive - zzip: fix crash after seeking
* input
- alsa: new input plugin ver 0.18.18 (2014/11/18)
- curl: options "verify_peer" and "verify_host" * decoder
- ffmpeg: update offset after seeking - ffmpeg: support opus
- ffmpeg: improved error messages * fix crash on failed filename charset conversion
- mms: non-blocking I/O * fix local socket detection from uid=0 (root)
- nfs: new input plugin
- smbclient: new input plugin
* filter
- volume: improved software volume dithering
* decoder:
- vorbis, flac, opus: honor DESCRIPTION= tag in Xiph-based files as a comment to the song
- audiofile: support scanning remote files
- audiofile: log libaudiofile errors
- dsdiff, dsf: report bit rate
- dsdiff, dsf: implement seeking
- dsf: support DSD512
- dsf: support multi-channel files
- dsf: fix big-endian bugs
- dsf: fix noise at end of malformed file
- mpg123: support ID3v2, ReplayGain and MixRamp
- sndfile: support scanning remote files
- sndfile: support tags "comment", "album", "track", "genre"
- sndfile: native floating point playback
- sndfile: optimized 16 bit playback
- mp4v2: support playback of MP4 files.
* encoder:
- shine: new encoder plugin
* output
- alsa: support native DSD playback
- alsa: rename "DSD over USB" to "DoP"
- osx: fix hang after (un)plugging headphones
* threads:
- the update thread runs at "idle" priority
- the output thread runs at "real-time" priority
- increase kernel timer slack on Linux
- name each thread (for debugging)
* configuration
- allow playlist directory without music directory
- use XDG to auto-detect "music_directory" and "db_file"
* add tags "AlbumSort", "MUSICBRAINZ_RELEASETRACKID"
* disable global Latin-1 fallback for tag values
* new resampler option using libsoxr
* ARM NEON optimizations
* install systemd unit for socket activation
* Android port
ver 0.18.17 (2014/11/02) ver 0.18.17 (2014/11/02)
* playlist * playlist
@@ -132,7 +42,6 @@ ver 0.18.14 (2014/09/11)
ver 0.18.13 (2014/08/31) ver 0.18.13 (2014/08/31)
* protocol * protocol
- don't change song on "seekcur" in random mode - don't change song on "seekcur" in random mode
* decoder * decoder
- dsdiff, dsf: fix endless loop on malformed file - dsdiff, dsf: fix endless loop on malformed file
- ffmpeg: support ffmpeg/libav version 11 - ffmpeg: support ffmpeg/libav version 11

92
UPGRADING Normal file
View File

@@ -0,0 +1,92 @@
Music Player Daemon (MPD) - UPGRADING
Upgrading to 0.14
-----------------
The filesystem character set is determined by GLib, if it is not
configured. GLib has an affinity towards UTF-8, while older MPD
versions used to choose ISO-Latin-1.
Upgrading to 0.13.0
-------------------
JACK, Avahi, and libsamplerate have been added as optional dependencies.
FLAC/OggFLAC now supports the 1.1.3 API, and libmikmod 3.2.0 betas are
supported as well.
New mpd.conf parameters include zeroconf_name, samplerate_converter, and
gapless_mp3_playback. See the mpd.conf man page or updated mpconf.example for
more information on these parameters.
Support for the ID3v2 "Original Artist/Performer" tag has been added. Your
MP3s will need to be rescanned for these tags to be included in the database.
This can be done by running mpd --create-db.
Upgrading to 0.12.0
-------------------
The ao_driver and ao_driver_options config parameters have been removed and
replaced with the audio_output config section. You will have to update your
config file to use this instead. See the mpd.conf man page or the new
mpdconf.example for details on specifying audio_output sections.
The db_file parameter is no longer optional. If you did not specify it in your
old config file then you will have to add it in order to run 0.12.0.
Support for OggFLAC and Musepack audio files has been added. Additionally,
scanning of MP3 files has been improved. To make use of these updates it is
highly recommended that you run mpd --create-db to recreate your entire
database.
Upgrading to 0.11.0
-------------------
The database format has changed a little bit, but in a backward compatible way.
This means that if you upgrade to 0.11.0 from 0.10.x, you do not need to make
any changes. However, if you downgrade back to 0.10.x, then you will need
to recreate your db.
The default port for MPD is now 6600, so update your mpd and client
configurations appropriately.
Upgrading to 0.10.0
-------------------
All information is now stored in the db in UTF-8 format, and the character
set used for the filesystem is stored in the db. Thus, it is highly
recommended that you recreate the db. To do so, run mpd with the
"--create-db" command line option. Also, note that the filesystem
character set will be determined from your current locale settings.
If your locale settings are not the same as those used for the filesystem,
then use the config file parameter "filesystem_charset" to specify the
correct character set (this maybe necessary if you create the db with root).
Upgrading to 0.9.3
------------------
Wave support was added, so to have your wave files added, update the db (mpc
update).
Also, song lengths are now stored in the db. To get this stuff
added to the db, you will need to recreate the db from scratch. To do this,
run mpd with the "--create-db" commandline option.
Upgrading to 0.9.0
------------------
The "stop_on_error" config parameter was removed, so be sure to remove this
parameter from your config file.
Upgrading to 0.8.x
------------------
If you have FLACs, then to have them added to your list of available music,
just use "update".
Upgrading from 0.5.x to 0.6.x
-----------------------------
If you have not compiled MPD with "make ogg", then nothing is needed.
If you compiled with "make ogg", just use "update" (available via the phpMp
interface) to add your OGGs to MPD's list of available music.

1
android/.gitignore vendored
View File

@@ -1 +0,0 @@
/build

View File

@@ -1,24 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="org.musicpd"
android:installLocation="auto"
android:versionCode="7"
android:versionName="0.19.1">
<uses-sdk android:minSdkVersion="9" android:targetSdkVersion="17"/>
<application android:icon="@drawable/icon" android:label="@string/app_name">
<activity android:name=".Main"
android:label="@string/app_name"
android:launchMode="singleInstance">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.WAKE_LOCK"/>
<uses-permission android:name="android.permission.INTERNET"/>
</manifest>

View File

@@ -1,433 +0,0 @@
#!/usr/bin/env python3
import os, os.path
import sys, shutil, subprocess
import urllib.request
import hashlib
import re
if len(sys.argv) < 3:
print("Usage: build.py SDK_PATH NDK_PATH [configure_args...]", file=sys.stderr)
sys.exit(1)
sdk_path = sys.argv[1]
ndk_path = sys.argv[2]
configure_args = sys.argv[3:]
if not os.path.isfile(os.path.join(sdk_path, 'tools', 'android')):
print("SDK not found in", ndk_path, file=sys.stderr)
sys.exit(1)
if not os.path.isdir(ndk_path):
print("NDK not found in", ndk_path, file=sys.stderr)
sys.exit(1)
# the path to the MPD sources
mpd_path = os.path.dirname(os.path.dirname(sys.argv[0]))
# output directories
lib_path = os.path.abspath('lib')
tarball_path = lib_path
src_path = os.path.join(lib_path, 'src')
build_path = os.path.join(lib_path, 'build')
root_path = os.path.join(lib_path, 'root')
# build host configuration
build_arch = 'linux-x86_64'
# redirect pkg-config to use our root directory instead of the default
# one on the build host
os.environ['PKG_CONFIG_LIBDIR'] = os.path.join(root_path, 'lib/pkgconfig')
# select the NDK compiler
gcc_version = '4.8'
llvm_version = '3.3'
# select the NDK target
ndk_arch = 'arm'
host_arch = 'arm-linux-androideabi'
android_abi = 'armeabi-v7a'
ndk_platform = 'android-14'
# set up the NDK toolchain
gcc_toolchain = os.path.join(ndk_path, 'toolchains', host_arch + '-' + gcc_version, 'prebuilt', build_arch)
llvm_toolchain = os.path.join(ndk_path, 'toolchains', 'llvm-' + llvm_version, 'prebuilt', build_arch)
ndk_platform_path = os.path.join(ndk_path, 'platforms', ndk_platform)
target_root = os.path.join(ndk_platform_path, 'arch-' + ndk_arch)
llvm_triple = 'armv7-none-linux-androideabi'
def select_toolchain(use_cxx, use_clang):
global cc, cxx, ar, strip, cflags, cxxflags, cppflags, ldflags, libs
target_arch = '-march=armv7-a -mfloat-abi=softfp'
if use_clang:
cc = os.path.join(llvm_toolchain, 'bin/clang')
cxx = os.path.join(llvm_toolchain, 'bin/clang++')
target_arch += ' -target ' + llvm_triple + ' -integrated-as -gcc-toolchain ' + gcc_toolchain
else:
cc = os.path.join(gcc_toolchain, 'bin', host_arch + '-gcc')
cxx = os.path.join(gcc_toolchain, 'bin', host_arch + '-g++')
ar = os.path.join(gcc_toolchain, 'bin', host_arch + '-ar')
strip = os.path.join(gcc_toolchain, 'bin', host_arch + '-strip')
libstdcxx_path = os.path.join(ndk_path, 'sources/cxx-stl/gnu-libstdc++', gcc_version)
libstdcxx_cppflags = '-isystem ' + os.path.join(libstdcxx_path, 'include') + ' -isystem ' + os.path.join(libstdcxx_path, 'libs', android_abi, 'include')
if use_clang:
libstdcxx_cppflags += ' -D__STRICT_ANSI__'
libstdcxx_ldadd = os.path.join(libstdcxx_path, 'libs', android_abi, 'libgnustl_static.a')
cflags = '-Os -g ' + target_arch
cxxflags = '-Os -g ' + target_arch
cppflags = '--sysroot=' + target_root + ' -I' + root_path + '/include'
ldflags = '--sysroot=' + target_root + ' -L' + root_path + '/lib'
libs = ''
if use_cxx:
libs += ' ' + libstdcxx_ldadd
cppflags += ' ' + libstdcxx_cppflags
def file_md5(path):
"""Calculate the MD5 checksum of a file and return it in hexadecimal notation."""
with open(path, 'rb') as f:
m = hashlib.md5()
while True:
data = f.read(65536)
if len(data) == 0:
# end of file
return m.hexdigest()
m.update(data)
def download_tarball(url, md5):
"""Download a tarball, verify its MD5 checksum and return the local path."""
global tarball_path
os.makedirs(tarball_path, exist_ok=True)
path = os.path.join(tarball_path, os.path.basename(url))
try:
calculated_md5 = file_md5(path)
if md5 == calculated_md5: return path
os.unlink(path)
except FileNotFoundError:
pass
tmp_path = path + '.tmp'
print("download", url)
urllib.request.urlretrieve(url, tmp_path)
calculated_md5 = file_md5(tmp_path)
if calculated_md5 != md5:
os.unlink(tmp_path)
raise "MD5 mismatch"
os.rename(tmp_path, path)
return path
class Project:
def __init__(self, url, md5, installed, name=None, version=None,
base=None,
use_cxx=False, use_clang=False):
if base is None:
basename = os.path.basename(url)
m = re.match(r'^(.+)\.(tar(\.(gz|bz2|xz|lzma))?|zip)$', basename)
if not m: raise
self.base = m.group(1)
else:
self.base = base
if name is None or version is None:
m = re.match(r'^([-\w]+)-(\d[\d.]*[a-z]?)$', self.base)
if name is None: name = m.group(1)
if version is None: version = m.group(2)
self.name = name
self.version = version
self.url = url
self.md5 = md5
self.installed = installed
self.use_cxx = use_cxx
self.use_clang = use_clang
def download(self):
return download_tarball(self.url, self.md5)
def is_installed(self):
global root_path
tarball = self.download()
installed = os.path.join(root_path, self.installed)
tarball_mtime = os.path.getmtime(tarball)
try:
return os.path.getmtime(installed) >= tarball_mtime
except FileNotFoundError:
return False
def unpack(self):
global src_path
tarball = self.download()
path = os.path.join(src_path, self.base)
try:
shutil.rmtree(path)
except FileNotFoundError:
pass
os.makedirs(src_path, exist_ok=True)
subprocess.check_call(['/bin/tar', 'xfC', tarball, src_path])
return path
def make_build_path(self):
path = os.path.join(build_path, self.base)
try:
shutil.rmtree(path)
except FileNotFoundError:
pass
os.makedirs(path, exist_ok=True)
return path
class AutotoolsProject(Project):
def __init__(self, url, md5, installed, configure_args=[],
autogen=False,
cppflags='',
**kwargs):
Project.__init__(self, url, md5, installed, **kwargs)
self.configure_args = configure_args
self.autogen = autogen
self.cppflags = cppflags
def build(self):
src = self.unpack()
if self.autogen:
subprocess.check_call(['/usr/bin/aclocal'], cwd=src)
subprocess.check_call(['/usr/bin/automake', '--add-missing', '--force-missing', '--foreign'], cwd=src)
subprocess.check_call(['/usr/bin/autoconf'], cwd=src)
subprocess.check_call(['/usr/bin/libtoolize', '--force'], cwd=src)
build = self.make_build_path()
select_toolchain(use_cxx=self.use_cxx, use_clang=self.use_clang)
configure = [
os.path.join(src, 'configure'),
'CC=' + cc,
'CXX=' + cxx,
'CFLAGS=' + cflags,
'CXXFLAGS=' + cxxflags,
'CPPFLAGS=' + cppflags + ' ' + self.cppflags,
'LDFLAGS=' + ldflags,
'LIBS=' + libs,
'AR=' + ar,
'STRIP=' + strip,
'--host=' + host_arch,
'--prefix=' + root_path,
'--with-sysroot=' + target_root,
'--enable-silent-rules',
] + self.configure_args
subprocess.check_call(configure, cwd=build)
subprocess.check_call(['/usr/bin/make', '--quiet', '-j12'], cwd=build)
subprocess.check_call(['/usr/bin/make', '--quiet', 'install'], cwd=build)
class FfmpegProject(Project):
def __init__(self, url, md5, installed, configure_args=[],
cppflags='',
**kwargs):
Project.__init__(self, url, md5, installed, **kwargs)
self.configure_args = configure_args
self.cppflags = cppflags
def build(self):
src = self.unpack()
build = self.make_build_path()
select_toolchain(use_cxx=self.use_cxx, use_clang=self.use_clang)
configure = [
os.path.join(src, 'configure'),
'--cc=' + cc,
'--cxx=' + cxx,
'--extra-cflags=' + cflags + ' ' + cppflags + ' ' + self.cppflags,
'--extra-cxxflags=' + cxxflags + ' ' + cppflags + ' ' + self.cppflags,
'--extra-ldflags=' + ldflags,
'--extra-libs=' + libs,
'--ar=' + ar,
'--enable-cross-compile',
'--target-os=linux',
'--arch=' + ndk_arch,
'--cpu=cortex-a8',
'--prefix=' + root_path,
] + self.configure_args
subprocess.check_call(configure, cwd=build)
subprocess.check_call(['/usr/bin/make', '--quiet', '-j12'], cwd=build)
subprocess.check_call(['/usr/bin/make', '--quiet', 'install'], cwd=build)
class BoostProject(Project):
def __init__(self, url, md5, installed,
**kwargs):
m = re.match(r'.*/boost_(\d+)_(\d+)_(\d+)\.tar\.bz2$', url)
version = "%s.%s.%s" % (m.group(1), m.group(2), m.group(3))
Project.__init__(self, url, md5, installed,
name='boost', version=version,
**kwargs)
def build(self):
src = self.unpack()
# install the headers manually; don't build any library
# (because right now, we only use header-only libraries)
includedir = os.path.join(root_path, 'include')
for dirpath, dirnames, filenames in os.walk(os.path.join(src, 'boost')):
relpath = dirpath[len(src)+1:]
destdir = os.path.join(includedir, relpath)
try:
os.mkdir(destdir)
except:
pass
for name in filenames:
if name[-4:] == '.hpp':
shutil.copyfile(os.path.join(dirpath, name),
os.path.join(destdir, name))
# a list of third-party libraries to be used by MPD on Android
thirdparty_libs = [
AutotoolsProject(
'http://downloads.xiph.org/releases/ogg/libogg-1.3.2.tar.xz',
'5c3a34309d8b98640827e5d0991a4015',
'lib/libogg.a',
['--disable-shared', '--enable-static'],
),
AutotoolsProject(
'http://downloads.xiph.org/releases/vorbis/libvorbis-1.3.4.tar.xz',
'55f2288055e44754275a17c9a2497391',
'lib/libvorbis.a',
['--disable-shared', '--enable-static'],
),
AutotoolsProject(
'http://downloads.xiph.org/releases/opus/opus-1.1.tar.gz',
'c5a8cf7c0b066759542bc4ca46817ac6',
'lib/libopus.a',
['--disable-shared', '--enable-static'],
use_clang=True,
),
AutotoolsProject(
'https://svn.xiph.org/releases/flac/flac-1.3.0.tar.xz',
'13b5c214cee8373464d3d65dee362cdd',
'lib/libFLAC.a',
[
'--disable-shared', '--enable-static',
'--disable-xmms-plugin', '--disable-cpplibs',
],
use_clang=True,
),
AutotoolsProject(
'ftp://ftp.mars.org/pub/mpeg/libid3tag-0.15.1b.tar.gz',
'e5808ad997ba32c498803822078748c3',
'lib/libid3tag.a',
['--disable-shared', '--enable-static'],
autogen=True,
),
AutotoolsProject(
'ftp://ftp.mars.org/pub/mpeg/libmad-0.15.1b.tar.gz',
'1be543bc30c56fb6bea1d7bf6a64e66c',
'lib/libmad.a',
['--disable-shared', '--enable-static'],
autogen=True,
),
FfmpegProject(
'http://www.ffmpeg.org/releases/ffmpeg-2.2.3.tar.bz2',
'dbb5b6b69bd010916f17df0ae596e0b1',
'lib/libavcodec.a',
[
'--disable-shared', '--enable-static',
'--enable-gpl',
'--enable-small',
'--disable-pthreads',
'--disable-runtime-cpudetect',
'--disable-programs',
'--disable-doc',
'--disable-avdevice',
'--disable-swresample',
'--disable-swscale',
'--disable-postproc',
'--disable-avfilter',
'--disable-network',
'--disable-encoders',
'--disable-protocols',
'--disable-outdevs',
'--disable-filters',
],
),
AutotoolsProject(
'http://curl.haxx.se/download/curl-7.37.0.tar.lzma',
'54bfd1eb5214f604186d6f5ac61c7781',
'lib/libcurl.a',
[
'--disable-shared', '--enable-static',
'--disable-debug',
'--enable-http',
'--enable-ipv6',
'--disable-ftp', '--disable-file',
'--disable-ldap', '--disable-ldaps',
'--disable-rtsp', '--disable-proxy', '--disable-dict', '--disable-telnet',
'--disable-tftp', '--disable-pop3', '--disable-imap', '--disable-smtp',
'--disable-gopher',
'--disable-manual',
'--disable-threaded-resolver', '--disable-verbose', '--disable-sspi',
'--disable-crypto-auth', '--disable-ntlm-wb', '--disable-tls-srp', '--disable-cookies',
'--without-ssl', '--without-gnutls', '--without-nss', '--without-libssh2',
],
use_clang=True,
),
BoostProject(
'http://netcologne.dl.sourceforge.net/project/boost/boost/1.55.0/boost_1_55_0.tar.bz2',
'd6eef4b4cacb2183f2bf265a5a03a354',
'include/boost/version.hpp',
),
]
# build the third-party libraries
for x in thirdparty_libs:
if not x.is_installed():
x.build()
# configure and build MPD
select_toolchain(use_cxx=True, use_clang=True)
configure = [
os.path.join(mpd_path, 'configure'),
'CC=' + cc,
'CXX=' + cxx,
'CFLAGS=' + cflags,
'CXXFLAGS=' + cxxflags,
'CPPFLAGS=' + cppflags,
'LDFLAGS=' + ldflags,
'LIBS=' + libs,
'AR=' + ar,
'STRIP=' + strip,
'--host=' + host_arch,
'--prefix=' + root_path,
'--with-sysroot=' + target_root,
'--with-android-sdk=' + sdk_path,
'--enable-silent-rules',
'--disable-glib',
'--disable-icu',
# disabled for now because these features require GLib:
'--disable-httpd-output',
'--disable-vorbis-encoder',
] + configure_args
subprocess.check_call(configure)
subprocess.check_call(['/usr/bin/make', '--quiet', '-j12'])

View File

@@ -1,11 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project name="mpd_rules">
<!-- setting these two properties works around a bug in Android
SDK's build.xml, which deletes all .class files every time -->
<property name="build.last.is.packaging.debug" value="true" />
<property name="build.is.packaging.debug" value="true" />
<target name="compile-jni-classes"
depends="-set-debug-mode,-compile"/>
</project>

View File

@@ -1,5 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="app_name">MPD</string>
</resources>

View File

@@ -1,30 +0,0 @@
/*
* Copyright (C) 2003-2014 The Music Player Daemon Project
* http://www.musicpd.org
*
* 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.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
package org.musicpd;
import android.content.Context;
/**
* Bridge to native code.
*/
public class Bridge {
public static native void run(Context context);
public static native void shutdown();
}

View File

@@ -1,39 +0,0 @@
/*
* Copyright (C) 2003-2014 The Music Player Daemon Project
* http://www.musicpd.org
*
* 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.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
package org.musicpd;
import android.util.Log;
public class Loader {
private static final String TAG = "MPD";
public static boolean loaded = false;
public static String error;
static {
try {
System.loadLibrary("mpd");
loaded = true;
} catch (UnsatisfiedLinkError e) {
Log.e(TAG, e.getMessage());
error = e.getMessage();
}
}
}

View File

@@ -1,75 +0,0 @@
/*
* Copyright (C) 2003-2014 The Music Player Daemon Project
* http://www.musicpd.org
*
* 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.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
package org.musicpd;
import android.app.Activity;
import android.os.Bundle;
import android.os.Build;
import android.os.Handler;
import android.os.Message;
import android.widget.TextView;
import android.util.Log;
public class Main extends Activity implements Runnable {
private static final String TAG = "MPD";
Thread thread;
TextView textView;
final Handler quitHandler = new Handler() {
public void handleMessage(Message msg) {
textView.setText("Music Player Daemon has quit");
// TODO: what now? restart?
}
};
@Override protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if (!Loader.loaded) {
TextView tv = new TextView(this);
tv.setText("Failed to load the native MPD libary.\n" +
"Report this problem to us, and include the following information:\n" +
"ABI=" + Build.CPU_ABI + "\n" +
"PRODUCT=" + Build.PRODUCT + "\n" +
"FINGERPRINT=" + Build.FINGERPRINT + "\n" +
"error=" + Loader.error);
setContentView(tv);
return;
}
if (thread == null || !thread.isAlive()) {
thread = new Thread(this, "NativeMain");
thread.start();
}
textView = new TextView(this);
textView.setText("Music Player Daemon is running"
+ "\nCAUTION: this version is EXPERIMENTAL!");
setContentView(textView);
}
@Override public void run() {
Bridge.run(this);
quitHandler.sendMessage(quitHandler.obtainMessage());
}
}

View File

@@ -1,11 +1,137 @@
#!/bin/sh #!/bin/sh
# Run this to set up the build system: configure, makefiles, etc.
# (at one point this was based on the version in enlightenment's cvs)
set -e package="mpd"
rm -rf config.cache build olddir="`pwd`"
mkdir build srcdir="`dirname $0`"
test -z "$srcdir" && srcdir=.
cd "$srcdir"
DIE=
AM_VERSIONGREP="sed -e s/.*[^0-9\.]\([0-9]\.[0-9][0-9]*\).*/\1/"
AC_VERSIONGREP="sed -e s/.*[^0-9\.]\([0-9]\.[0-9][0-9]\).*/\1/"
VERSIONMKINT="sed -e s/[^0-9]//"
if test -n "$AM_FORCE_VERSION"
then
AM_VERSIONS="$AM_FORCE_VERSION"
else
AM_VERSIONS='1.11'
fi
if test -n "$AC_FORCE_VERSION"
then
AC_VERSIONS="$AC_FORCE_VERSION"
else
AC_VERSIONS='2.60 2.61'
fi
aclocal -I m4 $ACLOCAL_FLAGS versioned_bins ()
autoheader {
automake --add-missing $AUTOMAKE_FLAGS bin="$1"
autoconf needed_int=`echo $VERNEEDED | $VERSIONMKINT`
for i in $VERSIONS
do
i_int=`echo $i | $VERSIONMKINT`
if test $i_int -ge $needed_int
then
echo $bin-$i $bin$i $bin-$i_int $bin$i_int
fi
done
echo $bin
}
for c in autoconf autoheader automake aclocal
do
uc=`echo $c | tr '[:lower:]' '[:upper:]'`
eval "val=`echo '$'$uc`"
if test -n "$val"
then
echo "$uc=$val in environment, will not attempt to auto-detect"
continue
fi
case "$c" in
autoconf|autoheader)
VERNEEDED=`fgrep AC_PREREQ configure.ac | $AC_VERSIONGREP`
VERSIONS="$AC_VERSIONS"
pkg=autoconf
;;
automake|aclocal)
VERNEEDED=`fgrep AUTOMAKE_OPTIONS Makefile.am | $AM_VERSIONGREP`
VERSIONS="$AM_VERSIONS"
pkg=automake
;;
esac
printf "checking for $c ... "
for x in `versioned_bins $c`; do
($x --version < /dev/null > /dev/null 2>&1) > /dev/null 2>&1
if test $? -eq 0
then
echo $x
eval $uc=$x
break
fi
done
eval "val=`echo '$'$uc`"
if test -z "$val"
then
if test $c = $pkg
then
DIE="$DIE $c=$VERNEEDED"
else
DIE="$DIE $c($pkg)=$VERNEEDED"
fi
fi
done
if test -n "$DIE"
then
echo "You must have the following installed to compile $package:"
for i in $DIE
do
printf ' '
echo $i | sed -e 's/(/ (from /' -e 's/=\(.*\)/ (>= \1)/'
done
echo "Download the appropriate package(s) for your system,"
echo "or get the source from one of the GNU ftp sites"
echo "listed in http://www.gnu.org/order/ftp.html"
exit 1
fi
echo "Generating configuration files for $package, please wait...."
ACLOCAL_FLAGS="$ACLOCAL_FLAGS -I m4"
# /usr/share/aclocal is most likely included by default, already...
ac_local_paths='
/usr/local/share/aclocal
/sw/share/aclocal
/usr/pkg/share/aclocal
/opt/share/aclocal
/usr/gnu/share/aclocal
'
for i in $ac_local_paths; do
if test -d "$i"; then
ACLOCAL_FLAGS="$ACLOCAL_FLAGS -I $i"
# we probably only want one of these...
break
fi
done
echo " $ACLOCAL $ACLOCAL_FLAGS"
$ACLOCAL $ACLOCAL_FLAGS || exit 1
echo " $AUTOHEADER"
$AUTOHEADER || exit 1
echo " $AUTOMAKE --add-missing $AUTOMAKE_FLAGS"
$AUTOMAKE --add-missing $AUTOMAKE_FLAGS || exit 1
echo " $AUTOCONF"
$AUTOCONF || exit 1
cd "$olddir"
if test x$NOCONFIGURE = x; then
"$srcdir"/configure "$@" || exit 1
fi

View File

@@ -1,25 +1,20 @@
AC_PREREQ(2.60) AC_PREREQ(2.60)
AC_INIT(mpd, 0.19.2, musicpd-dev-team@lists.sourceforge.net) AC_INIT(mpd, 0.18.20, mpd-devel@musicpd.org)
VERSION_MAJOR=0 VERSION_MAJOR=0
VERSION_MINOR=19 VERSION_MINOR=18
VERSION_REVISION=2 VERSION_REVISION=20
VERSION_EXTRA=0 VERSION_EXTRA=0
AC_CONFIG_SRCDIR([src/Main.cxx]) AC_CONFIG_SRCDIR([src/Main.cxx])
AC_CONFIG_AUX_DIR(build)
AM_INIT_AUTOMAKE([foreign 1.11 dist-xz subdir-objects]) AM_INIT_AUTOMAKE([foreign 1.11 dist-xz subdir-objects])
AM_SILENT_RULES AM_SILENT_RULES
AC_CONFIG_HEADERS(config.h) AC_CONFIG_HEADERS(config.h)
AC_CONFIG_MACRO_DIR([m4]) AC_CONFIG_MACRO_DIR([m4])
AC_DEFINE(PROTOCOL_VERSION, "0.19.0", [The MPD protocol version]) AC_DEFINE(PROTOCOL_VERSION, "0.18.0", [The MPD protocol version])
GIT_COMMIT=`GIT_DIR="$srcdir/.git" git describe --dirty --always 2>/dev/null`
if test x$GIT_COMMIT != x; then
AC_DEFINE_UNQUOTED(GIT_COMMIT, ["$GIT_COMMIT"], [The current git commit])
fi
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
dnl Programs dnl Programs
@@ -70,31 +65,9 @@ dnl OS Specific Defaults
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
AC_CANONICAL_HOST AC_CANONICAL_HOST
host_is_unix=yes
host_is_linux=no
host_is_android=no
host_is_darwin=no host_is_darwin=no
host_is_solaris=no
host_is_windows=no
linux_auto=no
case "$host_os" in case "$host_os" in
linux-android*)
host_is_android=yes
host_is_linux=yes
linux_auto=auto
AM_CPPFLAGS="$AM_CPPFLAGS -DANDROID"
;;
linux*)
host_is_linux=yes
linux_auto=auto
dnl allow using all glibc features
CPPFLAGS="$CPPFLAGS -D_GNU_SOURCE"
;;
mingw32* | windows*) mingw32* | windows*)
AC_CONFIG_FILES([ AC_CONFIG_FILES([
src/win32/mpd_win32_rc.rc src/win32/mpd_win32_rc.rc
@@ -103,21 +76,14 @@ mingw32* | windows*)
AM_CPPFLAGS="$AM_CPPFLAGS -DWIN32_LEAN_AND_MEAN" AM_CPPFLAGS="$AM_CPPFLAGS -DWIN32_LEAN_AND_MEAN"
AM_CPPFLAGS="$AM_CPPFLAGS -DWINVER=0x0600 -D_WIN32_WINNT=0x0600" AM_CPPFLAGS="$AM_CPPFLAGS -DWINVER=0x0600 -D_WIN32_WINNT=0x0600"
LIBS="$LIBS -lws2_32" LIBS="$LIBS -lws2_32"
host_is_windows=yes HAVE_WINDOWS=1
host_is_unix=no
;; ;;
darwin*) darwin*)
host_is_darwin=yes host_is_darwin=yes
;; ;;
solaris*)
host_is_solaris=yes
;;
esac esac
AM_CONDITIONAL([HAVE_WINDOWS], [test x$HAVE_WINDOWS = x1])
AM_CONDITIONAL([ANDROID], [test x$host_is_android = xyes])
AM_CONDITIONAL([HAVE_WINDOWS], [test x$host_is_windows = xyes])
if test -z "$prefix" || test "x$prefix" = xNONE; then if test -z "$prefix" || test "x$prefix" = xNONE; then
local_lib= local_lib=
@@ -155,27 +121,6 @@ if test -z "$prefix" || test "x$prefix" = xNONE; then
done done
fi fi
dnl ---------------------------------------------------------------------------
dnl Android
dnl ---------------------------------------------------------------------------
AC_ARG_WITH([android-sdk],
AS_HELP_STRING([--with-android-sdk=DIR],
[Directory for Android SDK]),
[], [with_android_sdk=no])
if test x$host_is_android = xyes; then
if test x$with_android_sdk = xno; then
AC_MSG_ERROR([Android build requires option --with-android-sdk=DIR])
fi
if ! test -x $with_android_sdk/tools/android; then
AC_MSG_ERROR([Android SDK not found in $with_android_sdk])
fi
fi
AC_SUBST(ANDROID_SDK, [$with_android_sdk])
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
dnl Language Checks dnl Language Checks
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
@@ -192,8 +137,7 @@ fi
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
dnl Header/Library Checks dnl Header/Library Checks
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
AC_CHECK_FUNCS(daemon fork)
AC_SEARCH_LIBS([clock_gettime], [rt])
AC_SEARCH_LIBS([syslog], [bsd socket inet], AC_SEARCH_LIBS([syslog], [bsd socket inet],
[AC_DEFINE(HAVE_SYSLOG, 1, [Define if syslog() is available])]) [AC_DEFINE(HAVE_SYSLOG, 1, [Define if syslog() is available])])
@@ -201,16 +145,10 @@ AC_SEARCH_LIBS([syslog], [bsd socket inet],
AC_SEARCH_LIBS([socket], [socket]) AC_SEARCH_LIBS([socket], [socket])
AC_SEARCH_LIBS([gethostbyname], [nsl]) AC_SEARCH_LIBS([gethostbyname], [nsl])
if test x$host_is_linux = xyes; then AC_CHECK_FUNCS(pipe2 accept4)
AC_CHECK_FUNCS(pipe2 accept4) MPD_OPTIONAL_FUNC(eventfd, eventfd, USE_EVENTFD)
fi MPD_OPTIONAL_FUNC(signalfd, signalfd, USE_SIGNALFD)
MPD_OPTIONAL_FUNC(epoll, epoll_create1, USE_EPOLL)
AC_CHECK_FUNCS(getpwnam_r getpwuid_r)
if test x$host_is_linux = xyes; then
MPD_OPTIONAL_FUNC(eventfd, eventfd, USE_EVENTFD)
MPD_OPTIONAL_FUNC(signalfd, signalfd, USE_SIGNALFD)
fi
AC_SEARCH_LIBS([exp], [m],, AC_SEARCH_LIBS([exp], [m],,
[AC_MSG_ERROR([exp() not found])]) [AC_MSG_ERROR([exp() not found])])
@@ -218,96 +156,14 @@ AC_SEARCH_LIBS([exp], [m],,
AC_CHECK_HEADERS(locale.h) AC_CHECK_HEADERS(locale.h)
AC_CHECK_HEADERS(valgrind/memcheck.h) AC_CHECK_HEADERS(valgrind/memcheck.h)
AC_CHECK_HEADERS([sys/prctl.h], AC_CHECK_FUNCS([prctl]))
AX_PTHREAD
LIBS="$PTHREAD_LIBS $LIBS"
AM_CFLAGS="$AM_CFLAGS $PTHREAD_CFLAGS"
AM_CXXFLAGS="$AM_CXXFLAGS $PTHREAD_CFLAGS"
AC_CHECK_LIB([pthread], [pthread_setname_np],
[have_pthread_setname_np=yes],
[have_pthread_setname_np=no])
if test x$have_pthread_setname_np = xyes; then
AC_DEFINE(HAVE_PTHREAD_SETNAME_NP, 1, [Is pthread_setname_np() available?])
fi
dnl ---------------------------------------------------------------------------
dnl Event loop selection
dnl ---------------------------------------------------------------------------
MPD_OPTIONAL_FUNC_NODEF(poll, poll)
if test x$host_is_linux = xyes; then
MPD_OPTIONAL_FUNC_NODEF(epoll, epoll_create1)
fi
AC_ARG_WITH(pollmethod,
AS_HELP_STRING(
[--with-pollmethod=@<:@epoll|poll|winselect|auto@:>@],
[specify poll method for internal event loop (default=auto)]),,
[with_pollmethod=auto])
if test "x$with_pollmethod" = xauto; then
if test "x$enable_epoll" = xyes; then
with_pollmethod=epoll
elif test "x$enable_poll" = xyes; then
with_pollmethod=poll
elif test "x$host_is_windows" = xyes; then
with_pollmethod=winselect
else
AC_MSG_ERROR([no poll method is available for your platform])
fi
fi
case "$with_pollmethod" in
epoll)
AC_DEFINE(USE_EPOLL, 1, [Define to poll sockets with epoll])
;;
poll)
AC_DEFINE(USE_POLL, 1, [Define to poll sockets with poll])
;;
winselect)
AC_DEFINE(USE_WINSELECT, 1,
[Define to poll sockets with Windows select])
;;
*)
AC_MSG_ERROR([unknown pollmethod option: $with_pollmethod])
esac
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
dnl Allow tools to be specifically built dnl Allow tools to be specifically built
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
AC_ARG_ENABLE(database,
AS_HELP_STRING([--enable-database],
[enable support for the music database]),,
enable_database=yes)
AM_CONDITIONAL(ENABLE_DATABASE, test x$enable_database = xyes)
if test x$enable_database = xyes; then
database_auto=auto
AC_DEFINE(ENABLE_DATABASE, 1, [Define to enable the music database])
else
database_auto=no
fi
AC_ARG_ENABLE(libmpdclient, AC_ARG_ENABLE(libmpdclient,
AS_HELP_STRING([--enable-libmpdclient], AS_HELP_STRING([--enable-libmpdclient],
[enable support for the MPD client]),, [enable support for the MPD client]),,
enable_libmpdclient=auto) enable_libmpdclient=auto)
MPD_DEPENDS([enable_libmpdclient], [enable_database],
[Cannot use --enable-libmpdclient with --disable-database])
AC_ARG_ENABLE(expat,
AS_HELP_STRING([--enable-expat],
[enable the expat XML parser]),,
enable_expat=auto)
AC_ARG_ENABLE(upnp,
AS_HELP_STRING([--enable-upnp],
[enable UPnP client support (default: auto)]),,
enable_upnp=auto)
MPD_DEPENDS([enable_upnp], [enable_database],
[Cannot use --enable-upnp with --disable-database])
AC_ARG_ENABLE(adplug, AC_ARG_ENABLE(adplug,
AS_HELP_STRING([--enable-adplug], AS_HELP_STRING([--enable-adplug],
@@ -316,7 +172,7 @@ AC_ARG_ENABLE(adplug,
AC_ARG_ENABLE(alsa, AC_ARG_ENABLE(alsa,
AS_HELP_STRING([--enable-alsa], [enable ALSA support]),, AS_HELP_STRING([--enable-alsa], [enable ALSA support]),,
[enable_alsa=$linux_auto]) [enable_alsa=auto])
AC_ARG_ENABLE(roar, AC_ARG_ENABLE(roar,
AS_HELP_STRING([--enable-roar], AS_HELP_STRING([--enable-roar],
@@ -327,19 +183,12 @@ AC_ARG_ENABLE(ao,
AS_HELP_STRING([--enable-ao], AS_HELP_STRING([--enable-ao],
[enable support for libao]),, [enable support for libao]),,
enable_ao=auto) enable_ao=auto)
MPD_DEPENDS([enable_ao], [enable_glib],
[Cannot use --enable-ao with --disable-glib])
AC_ARG_ENABLE(audiofile, AC_ARG_ENABLE(audiofile,
AS_HELP_STRING([--enable-audiofile], AS_HELP_STRING([--enable-audiofile],
[enable audiofile support (WAV and others)]),, [enable audiofile support (WAV and others)]),,
enable_audiofile=auto) enable_audiofile=auto)
AC_ARG_ENABLE(zlib,
AS_HELP_STRING([--enable-zlib],
[enable zlib support (default: auto)]),,
enable_zlib=auto)
AC_ARG_ENABLE(bzip2, AC_ARG_ENABLE(bzip2,
AS_HELP_STRING([--enable-bzip2], AS_HELP_STRING([--enable-bzip2],
[enable bzip2 archive support (default: auto)]),, [enable bzip2 archive support (default: auto)]),,
@@ -349,24 +198,12 @@ AC_ARG_ENABLE(cdio-paranoia,
AS_HELP_STRING([--enable-cdio-paranoia], AS_HELP_STRING([--enable-cdio-paranoia],
[enable support for audio CD support]),, [enable support for audio CD support]),,
enable_cdio_paranoia=auto) enable_cdio_paranoia=auto)
MPD_DEPENDS([enable_cdio_paranoia], [enable_glib],
[Cannot use --enable-cdio-paranoia with --disable-glib])
AC_ARG_ENABLE(curl, AC_ARG_ENABLE(curl,
AS_HELP_STRING([--enable-curl], AS_HELP_STRING([--enable-curl],
[enable support for libcurl HTTP streaming (default: auto)]),, [enable support for libcurl HTTP streaming (default: auto)]),,
[enable_curl=auto]) [enable_curl=auto])
AC_ARG_ENABLE(smbclient,
AS_HELP_STRING([--enable-smbclient],
[enable support for libsmbclient (default: auto)]),,
[enable_smbclient=auto])
AC_ARG_ENABLE(nfs,
AS_HELP_STRING([--enable-nfs],
[enable support for libnfs (default: auto)]),,
[enable_nfs=auto])
AC_ARG_ENABLE(debug, AC_ARG_ENABLE(debug,
AS_HELP_STRING([--enable-debug], AS_HELP_STRING([--enable-debug],
[enable debugging (default: disabled)]),, [enable debugging (default: disabled)]),,
@@ -406,15 +243,11 @@ AC_ARG_ENABLE(gme,
AS_HELP_STRING([--enable-gme], AS_HELP_STRING([--enable-gme],
[enable Blargg's game music emulator plugin]),, [enable Blargg's game music emulator plugin]),,
enable_gme=auto) enable_gme=auto)
MPD_DEPENDS([enable_gme], [enable_glib],
[Cannot use --enable-gme with --disable-glib])
AC_ARG_ENABLE(httpd-output, AC_ARG_ENABLE(httpd-output,
AS_HELP_STRING([--enable-httpd-output], AS_HELP_STRING([--enable-httpd-output],
[enables the HTTP server output]),, [enables the HTTP server output]),,
[enable_httpd_output=auto]) [enable_httpd_output=auto])
MPD_DEPENDS([enable_httpd_output], [enable_glib],
[Cannot use --enable-httpd-output with --disable-glib])
AC_ARG_ENABLE(id3, AC_ARG_ENABLE(id3,
AS_HELP_STRING([--enable-id3], AS_HELP_STRING([--enable-id3],
@@ -440,8 +273,6 @@ AC_ARG_ENABLE(jack,
AS_HELP_STRING([--enable-jack], AS_HELP_STRING([--enable-jack],
[enable jack support]),, [enable jack support]),,
enable_jack=auto) enable_jack=auto)
MPD_DEPENDS([enable_jack], [enable_glib],
[Cannot use --enable-jack with --disable-glib])
AC_SYS_LARGEFILE AC_SYS_LARGEFILE
@@ -454,8 +285,6 @@ AC_ARG_ENABLE(soundcloud,
AS_HELP_STRING([--enable-soundcloud], AS_HELP_STRING([--enable-soundcloud],
[enable support for soundcloud.com]),, [enable support for soundcloud.com]),,
[enable_soundcloud=auto]) [enable_soundcloud=auto])
MPD_DEPENDS([enable_soundcloud], [enable_glib],
[Cannot use --enable-soundcloud with --disable-glib])
AC_ARG_ENABLE(lame-encoder, AC_ARG_ENABLE(lame-encoder,
AS_HELP_STRING([--enable-lame-encoder], AS_HELP_STRING([--enable-lame-encoder],
@@ -471,11 +300,6 @@ AC_ARG_ENABLE(lsr,
[enable libsamplerate support]),, [enable libsamplerate support]),,
enable_lsr=auto) enable_lsr=auto)
AC_ARG_ENABLE(soxr,
AS_HELP_STRING([--enable-soxr],
[enable the libsoxr resampler]),,
enable_soxr=auto)
AC_ARG_ENABLE(mad, AC_ARG_ENABLE(mad,
AS_HELP_STRING([--enable-mad], AS_HELP_STRING([--enable-mad],
[enable libmad mp3 decoder plugin]),, [enable libmad mp3 decoder plugin]),,
@@ -496,11 +320,6 @@ AC_ARG_ENABLE(modplug,
[enable modplug decoder plugin]),, [enable modplug decoder plugin]),,
enable_modplug=auto) enable_modplug=auto)
AC_ARG_ENABLE(mp4v2,
AS_HELP_STRING([--enable-mp4v2],
[enable libmp4v2 decoder plugin]),,
enable_mp4v2=auto)
AC_ARG_ENABLE(mpc, AC_ARG_ENABLE(mpc,
AS_HELP_STRING([--enable-mpc], AS_HELP_STRING([--enable-mpc],
[disable musepack (MPC) support (default: auto)]),, [disable musepack (MPC) support (default: auto)]),,
@@ -550,13 +369,7 @@ AC_ARG_ENABLE(sidplay,
AS_HELP_STRING([--enable-sidplay], AS_HELP_STRING([--enable-sidplay],
[enable C64 SID support via libsidplay2]),, [enable C64 SID support via libsidplay2]),,
enable_sidplay=auto) enable_sidplay=auto)
MPD_DEPENDS([enable_sidplay], [enable_glib],
[Cannot use --enable-sidplay with --disable-glib])
AC_ARG_ENABLE(shine-encoder,
AS_HELP_STRING([--enable-shine-encoder],
[enables shine encoder]),,
[enable_shine_encoder=auto])
AC_ARG_ENABLE(shout, AC_ARG_ENABLE(shout,
AS_HELP_STRING([--enable-shout], AS_HELP_STRING([--enable-shout],
@@ -571,19 +384,17 @@ AC_ARG_ENABLE(sndfile,
AC_ARG_ENABLE(solaris_output, AC_ARG_ENABLE(solaris_output,
AS_HELP_STRING([--enable-solaris-output], AS_HELP_STRING([--enable-solaris-output],
[enables the Solaris /dev/audio output]),, [enables the Solaris /dev/audio output]),,
[enable_solaris_output=$host_is_solaris]) [enable_solaris_output=auto])
AC_ARG_ENABLE(sqlite, AC_ARG_ENABLE(sqlite,
AS_HELP_STRING([--enable-sqlite], AS_HELP_STRING([--enable-sqlite],
[enable support for the SQLite database]),, [enable support for the SQLite database]),,
[enable_sqlite=$database_auto]) [enable_sqlite=auto])
MPD_DEPENDS([enable_sqlite], [enable_glib],
[Cannot use --enable-sqlite with --disable-glib])
AC_ARG_ENABLE(systemd-daemon, AC_ARG_ENABLE(systemd-daemon,
AS_HELP_STRING([--enable-systemd-daemon], AS_HELP_STRING([--enable-systemd-daemon],
[use the systemd daemon library (default=auto)]),, [use the systemd daemon library (default=auto)]),,
[enable_systemd_daemon=$linux_auto]) [enable_systemd_daemon=auto])
AC_ARG_ENABLE(tcp, AC_ARG_ENABLE(tcp,
AS_HELP_STRING([--disable-tcp], AS_HELP_STRING([--disable-tcp],
@@ -608,7 +419,7 @@ AC_ARG_ENABLE(twolame-encoder,
AC_ARG_ENABLE(un, AC_ARG_ENABLE(un,
AS_HELP_STRING([--disable-un], AS_HELP_STRING([--disable-un],
[disable support for clients connecting via unix domain sockets (default: enable)]),, [disable support for clients connecting via unix domain sockets (default: enable)]),,
[enable_un=$host_is_unix]) [enable_un=yes])
AC_ARG_ENABLE(vorbis, AC_ARG_ENABLE(vorbis,
AS_HELP_STRING([--enable-vorbis], AS_HELP_STRING([--enable-vorbis],
@@ -619,8 +430,6 @@ AC_ARG_ENABLE(vorbis-encoder,
AS_HELP_STRING([--enable-vorbis-encoder], AS_HELP_STRING([--enable-vorbis-encoder],
[enable the Ogg Vorbis encoder]),, [enable the Ogg Vorbis encoder]),,
[enable_vorbis_encoder=auto]) [enable_vorbis_encoder=auto])
MPD_DEPENDS([enable_vorbis_encoder], [enable_glib],
[Cannot use --enable-vorbis-encoder with --disable-glib])
AC_ARG_ENABLE(wave-encoder, AC_ARG_ENABLE(wave-encoder,
AS_HELP_STRING([--enable-wave-encoder], AS_HELP_STRING([--enable-wave-encoder],
@@ -631,8 +440,6 @@ AC_ARG_ENABLE(wavpack,
AS_HELP_STRING([--enable-wavpack], AS_HELP_STRING([--enable-wavpack],
[enable WavPack support]),, [enable WavPack support]),,
enable_wavpack=auto) enable_wavpack=auto)
MPD_DEPENDS([enable_wavpack], [enable_glib],
[Cannot use --enable-wavpack with --disable-glib])
AC_ARG_ENABLE(werror, AC_ARG_ENABLE(werror,
AS_HELP_STRING([--enable-werror], AS_HELP_STRING([--enable-werror],
@@ -668,58 +475,13 @@ AC_ARG_WITH(tremor-includes,
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
dnl Mandatory Libraries dnl Mandatory Libraries
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
PKG_CHECK_MODULES([GLIB], [glib-2.0 >= 2.28 gthread-2.0],,
no_exceptions=yes
AX_BOOST_BASE([1.46],, [AC_MSG_ERROR([Boost not found])])
dnl Don't disable exceptions on Boost older than 1.54, because
dnl Boost.Intrusive supports this compiler mode only since 1.54;
dnl see https://svn.boost.org/trac/boost/ticket/7849
CPPFLAGS_SAVED="$CPPFLAGS"
CPPFLAGS="$CPPFLAGS $BOOST_CPPFLAGS"
export CPPFLAGS
AC_LANG_PUSH(C++)
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[
@%:@include <boost/version.hpp>
]], [[
#if BOOST_VERSION < 105400
#error detected Boost older than 1.54
#endif
]])],, [no_exceptions=no])
AC_LANG_POP([C++])
CPPFLAGS="$CPPFLAGS_SAVED"
AC_ARG_ENABLE(icu,
AS_HELP_STRING([--enable-icu],
[enable libicu for Unicode (default: enabled)]),,
enable_icu=yes)
if test x$enable_icu = xyes; then
PKG_CHECK_MODULES([ICU], [icu-i18n],,
[AC_MSG_ERROR([libicu not found])])
AC_DEFINE(HAVE_ICU, 1, [Define if libicu is used])
fi
AM_CONDITIONAL(HAVE_ICU, test x$enable_icu = xyes)
AC_ARG_ENABLE(glib,
AS_HELP_STRING([--enable-glib],
[enable GLib usage (default: enabled)]),,
enable_glib=yes)
if test x$enable_glib = xyes; then
PKG_CHECK_MODULES([GLIB], [glib-2.0 >= 2.28 gthread-2.0],,
[AC_MSG_ERROR([GLib 2.28 is required])]) [AC_MSG_ERROR([GLib 2.28 is required])])
if test x$GCC = xyes; then if test x$GCC = xyes; then
# suppress warnings in the GLib headers # suppress warnings in the GLib headers
GLIB_CFLAGS=`echo $GLIB_CFLAGS |sed -e 's,-I/,-isystem /,g'` GLIB_CFLAGS=`echo $GLIB_CFLAGS |sed -e 's,-I/,-isystem /,g'`
fi
AC_DEFINE(HAVE_GLIB, 1, [Define if GLib is used])
fi fi
AM_CONDITIONAL(HAVE_GLIB, test x$enable_glib = xyes)
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
dnl Protocol Options dnl Protocol Options
@@ -757,6 +519,12 @@ if test x$enable_tcp = xyes; then
AC_DEFINE(HAVE_TCP, 1, [Define if TCP socket support is enabled]) AC_DEFINE(HAVE_TCP, 1, [Define if TCP socket support is enabled])
fi fi
case "$host_os" in
mingw* | windows* | cygwin*)
enable_un=no
;;
esac
if test x$enable_un = xyes; then if test x$enable_un = xyes; then
AC_DEFINE(HAVE_UN, 1, [Define if unix domain socket support is enabled]) AC_DEFINE(HAVE_UN, 1, [Define if unix domain socket support is enabled])
STRUCT_UCRED STRUCT_UCRED
@@ -797,15 +565,6 @@ fi
AM_CONDITIONAL(HAVE_LIBMPDCLIENT, test x$enable_libmpdclient = xyes) AM_CONDITIONAL(HAVE_LIBMPDCLIENT, test x$enable_libmpdclient = xyes)
dnl -------------------------------- expat --------------------------------
MPD_AUTO_PKG(expat, EXPAT, [expat],
[expat XML parser], [expat not found])
if test x$enable_expat = xyes; then
AC_DEFINE(HAVE_EXPAT, 1, [Define to use the expat XML parser])
fi
AM_CONDITIONAL(HAVE_EXPAT, test x$enable_expat = xyes)
dnl --------------------------------- inotify --------------------------------- dnl --------------------------------- inotify ---------------------------------
AC_CHECK_FUNCS(inotify_init inotify_init1) AC_CHECK_FUNCS(inotify_init inotify_init1)
@@ -885,7 +644,7 @@ avahi)
;; ;;
esac esac
MPD_AUTO_PKG(avahi, AVAHI, [avahi-client dbus-1], MPD_AUTO_PKG(avahi, AVAHI, [avahi-client],
[avahi client library], [avahi-client not found]) [avahi client library], [avahi-client not found])
if test x$enable_avahi = xyes; then if test x$enable_avahi = xyes; then
AC_DEFINE([HAVE_AVAHI], 1, [Define to enable Avahi Zeroconf support]) AC_DEFINE([HAVE_AVAHI], 1, [Define to enable Avahi Zeroconf support])
@@ -938,22 +697,21 @@ dnl Converter Plugins
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
dnl ------------------------------ libsamplerate ------------------------------ dnl ------------------------------ libsamplerate ------------------------------
MPD_AUTO_PKG(lsr, SAMPLERATE, [samplerate >= 0.1.3], MPD_AUTO_PKG(lsr, SAMPLERATE, [samplerate >= 0.0.15],
[libsamplerate resampling], [libsamplerate not found]) [libsamplerate resampling], [libsamplerate not found])
if test x$enable_lsr = xyes; then if test x$enable_lsr = xyes; then
AC_DEFINE([HAVE_LIBSAMPLERATE], 1, AC_DEFINE([HAVE_LIBSAMPLERATE], 1,
[Define to enable libsamplerate]) [Define to enable libsamplerate])
fi fi
AM_CONDITIONAL(HAVE_LIBSAMPLERATE, test x$enable_lsr = xyes)
dnl ------------------------------ libsoxr ------------------------------------ if test x$enable_lsr = xyes; then
MPD_AUTO_PKG(soxr, SOXR, [soxr], PKG_CHECK_MODULES([SAMPLERATE_013],
[libsoxr resampler], [libsoxr not found]) [samplerate >= 0.1.3],,
if test x$enable_soxr = xyes; then [AC_DEFINE([HAVE_LIBSAMPLERATE_NOINT], 1,
AC_DEFINE([HAVE_SOXR], 1, [Define to enable libsoxr]) [libsamplerate doesn't provide src_int_to_float_array() (<0.1.3)])])
fi fi
AM_CONDITIONAL(HAVE_SOXR, test x$enable_soxr = xyes) AM_CONDITIONAL(HAVE_LIBSAMPLERATE, test x$enable_lsr = xyes)
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
dnl Input Plugins dnl Input Plugins
@@ -967,23 +725,6 @@ if test x$enable_curl = xyes; then
fi fi
AM_CONDITIONAL(ENABLE_CURL, test x$enable_curl = xyes) AM_CONDITIONAL(ENABLE_CURL, test x$enable_curl = xyes)
dnl ----------------------------------- smbclient -----------------------------
MPD_AUTO_PKG_LIB(smbclient, SMBCLIENT, [smbclient >= 0.2],
[smbclient], [smbc_init], [-lsmbclient], [],
[smbclient input plugin], [libsmbclient not found])
if test x$enable_smbclient = xyes; then
AC_DEFINE(ENABLE_SMBCLIENT, 1, [Define when libsmbclient is used])
fi
AM_CONDITIONAL(ENABLE_SMBCLIENT, test x$enable_smbclient = xyes)
dnl ----------------------------------- NFS -----------------------------
MPD_AUTO_PKG(nfs, NFS, [libnfs],
[NFS input plugin], [libnfs not found])
if test x$enable_nfs = xyes; then
AC_DEFINE(ENABLE_NFS, 1, [Define when libnfs is used])
fi
AM_CONDITIONAL(ENABLE_NFS, test x$enable_nfs = xyes)
dnl --------------------------------- Despotify --------------------------------- dnl --------------------------------- Despotify ---------------------------------
MPD_AUTO_PKG(despotify, DESPOTIFY, [despotify], MPD_AUTO_PKG(despotify, DESPOTIFY, [despotify],
[Despotify support], [despotify not found]) [Despotify support], [despotify not found])
@@ -1027,30 +768,6 @@ if test x$enable_mms = xyes; then
fi fi
AM_CONDITIONAL(ENABLE_MMS, test x$enable_mms = xyes) AM_CONDITIONAL(ENABLE_MMS, test x$enable_mms = xyes)
dnl ---------------------------------------------------------------------------
dnl Neighbor Plugins
dnl ---------------------------------------------------------------------------
AC_ARG_ENABLE(neighbor-plugins,
AS_HELP_STRING([--enable-neighbor-plugins],
[enable support for neighbor discovery (default: auto)]),,
[enable_neighbor_plugins=auto])
if test x$enable_neighbor_plugins = xauto; then
if test x$enable_smbclient = xyes; then
enable_neighbor_plugins=yes
fi
if test x$enable_upnp = xyes; then
enable_neighbor_plugins=yes
fi
fi
if test x$enable_neighbor_plugins = xyes; then
AC_DEFINE(ENABLE_NEIGHBOR_PLUGINS, 1,
[Define to enable support for neighbor discovery])
fi
AM_CONDITIONAL(ENABLE_NEIGHBOR_PLUGINS, test x$enable_neighbor_plugins = xyes)
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
dnl Archive Plugins dnl Archive Plugins
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
@@ -1070,16 +787,6 @@ fi
AM_CONDITIONAL(ENABLE_ISO9660_TEST, test x$MKISOFS != xno) AM_CONDITIONAL(ENABLE_ISO9660_TEST, test x$MKISOFS != xno)
dnl ---------------------------------- zlib ---------------------------------
MPD_AUTO_PKG(zlib, ZLIB, [zlib],
[zlib support], [zlib not found])
AM_CONDITIONAL(HAVE_ZLIB, test x$enable_zlib = xyes)
if test x$enable_zlib = xyes; then
AC_DEFINE(HAVE_ZLIB, 1, [Define to enable zlib support])
fi
dnl ---------------------------------- libbz2 --------------------------------- dnl ---------------------------------- libbz2 ---------------------------------
MPD_AUTO_LIB(bzip2, BZ2, bz2, BZ2_bzDecompressInit, [-lbz2], [], MPD_AUTO_LIB(bzip2, BZ2, bz2, BZ2_bzDecompressInit, [-lbz2], [],
@@ -1096,24 +803,6 @@ fi
AM_CONDITIONAL(ENABLE_BZIP2_TEST, test x$BZIP2 != xno) AM_CONDITIONAL(ENABLE_BZIP2_TEST, test x$BZIP2 != xno)
dnl ---------------------------------- libupnp ---------------------------------
if test x$enable_expat = xno; then
if test x$enable_upnp = xauto; then
AC_MSG_WARN([expat disabled -- disabling UPnP])
enable_upnp=no
elif test x$enable_upnp = xyes; then
AC_MSG_ERROR([expat disabled -- required for UPnP])
fi
fi
MPD_AUTO_PKG(upnp, UPNP, [libupnp],
[UPnP client support], [libupnp not found])
if test x$enable_upnp = xyes; then
AC_DEFINE(HAVE_LIBUPNP, 1, [Define when libupnp is used])
fi
AM_CONDITIONAL(HAVE_LIBUPNP, test x$enable_upnp = xyes)
dnl --------------------------------- libzzip --------------------------------- dnl --------------------------------- libzzip ---------------------------------
MPD_AUTO_PKG(zzip, ZZIP, [zziplib >= 0.13], MPD_AUTO_PKG(zzip, ZZIP, [zziplib >= 0.13],
[libzzip archive library], [libzzip not found]) [libzzip archive library], [libzzip not found])
@@ -1264,24 +953,6 @@ if test x$enable_modplug = xyes; then
fi fi
AM_CONDITIONAL(HAVE_MODPLUG, test x$enable_modplug = xyes) AM_CONDITIONAL(HAVE_MODPLUG, test x$enable_modplug = xyes)
dnl -------------------------------- libmp4v2 ---------------------------------
if test x$enable_aac = xyes; then
MPD_AUTO_LIB(mp4v2, MP4V2, mp4v2, MP4Create, [-lmp4v2], [],
[mp4v2], [libmp4v2 not found])
if test x$enable_mp4v2 = xyes; then
AC_DEFINE(HAVE_MP4V2, 1, [Define to use libmp4v2 for MP4 decoding])
fi
else
if test x$enable_mp4v2 = xyes; then
AC_MSG_ERROR([MP4V2 requires AAC!])
fi
enable_mp4v2=no
fi
AM_CONDITIONAL(HAVE_MP4V2, test x$enable_mp4v2 = xyes)
dnl -------------------------------- libopus ---------------------------------- dnl -------------------------------- libopus ----------------------------------
MPD_AUTO_PKG(opus, OPUS, [opus ogg], MPD_AUTO_PKG(opus, OPUS, [opus ogg],
[opus decoder plugin], [libopus not found]) [opus decoder plugin], [libopus not found])
@@ -1448,7 +1119,6 @@ else
enable_vorbis_encoder=no enable_vorbis_encoder=no
enable_lame_encoder=no enable_lame_encoder=no
enable_twolame_encoder=no enable_twolame_encoder=no
enable_shine_encoder=no
enable_wave_encoder=no enable_wave_encoder=no
enable_flac_encoder=no enable_flac_encoder=no
fi fi
@@ -1460,17 +1130,6 @@ if test x$enable_flac_encoder = xyes; then
fi fi
AM_CONDITIONAL(ENABLE_FLAC_ENCODER, test x$enable_flac_encoder = xyes) AM_CONDITIONAL(ENABLE_FLAC_ENCODER, test x$enable_flac_encoder = xyes)
dnl ------------------------------- Shine Encoder ------------------------------
MPD_AUTO_PKG(shine_encoder, SHINE, [shine >= 3.1],
[shine encoder], [libshine not found])
if test x$enable_shine_encoder = xyes; then
AC_DEFINE(ENABLE_SHINE_ENCODER, 1,
[Define to enable the shine encoder plugin])
fi
AM_CONDITIONAL(ENABLE_SHINE_ENCODER, test x$enable_shine_encoder = xyes)
dnl ---------------------------- Ogg Vorbis Encoder --------------------------- dnl ---------------------------- Ogg Vorbis Encoder ---------------------------
MPD_AUTO_PKG(vorbis_encoder, VORBISENC, [vorbisenc vorbis ogg], MPD_AUTO_PKG(vorbis_encoder, VORBISENC, [vorbisenc vorbis ogg],
[Ogg Vorbis encoder], [libvorbisenc not found]) [Ogg Vorbis encoder], [libvorbisenc not found])
@@ -1514,7 +1173,6 @@ if test x$enable_vorbis_encoder != xno ||
test x$enable_lame_encoder != xno || test x$enable_lame_encoder != xno ||
test x$enable_twolame_encoder != xno || test x$enable_twolame_encoder != xno ||
test x$enable_flac_encoder != xno || test x$enable_flac_encoder != xno ||
test x$enable_shine_encoder != xno ||
test x$enable_wave_encoder != xno; then test x$enable_wave_encoder != xno; then
# at least one encoder plugin is enabled # at least one encoder plugin is enabled
enable_encoder=yes enable_encoder=yes
@@ -1710,6 +1368,18 @@ AM_CONDITIONAL(HAVE_SHOUT, test x$enable_shout = xyes)
dnl --------------------------------- Solaris --------------------------------- dnl --------------------------------- Solaris ---------------------------------
if test x$enable_solaris_output = xauto; then
case "$host_os" in
solaris*)
enable_solaris_output=yes
;;
*)
enable_solaris_output=no
;;
esac
fi
if test x$enable_solaris_output = xyes; then if test x$enable_solaris_output = xyes; then
AC_DEFINE(ENABLE_SOLARIS_OUTPUT, 1, [Define to enable Solaris /dev/audio support]) AC_DEFINE(ENABLE_SOLARIS_OUTPUT, 1, [Define to enable Solaris /dev/audio support])
fi fi
@@ -1718,13 +1388,17 @@ AM_CONDITIONAL(ENABLE_SOLARIS_OUTPUT, test x$enable_solaris_output = xyes)
dnl --------------------------------- WinMM --------------------------------- dnl --------------------------------- WinMM ---------------------------------
if test "x$host_is_windows" = xyes; then case "$host_os" in
AC_DEFINE(ENABLE_WINMM_OUTPUT, 1, [Define to enable WinMM support]) mingw32* | windows*)
enable_winmm_output=yes AC_DEFINE(ENABLE_WINMM_OUTPUT, 1, [Define to enable WinMM support])
LIBS="$LIBS -lwinmm" enable_winmm_output=yes
else LIBS="$LIBS -lwinmm"
enable_winmm_output=no ;;
fi
*)
enable_winmm_output=no
;;
esac
AM_CONDITIONAL(ENABLE_WINMM_OUTPUT, test x$enable_winmm_output = xyes) AM_CONDITIONAL(ENABLE_WINMM_OUTPUT, test x$enable_winmm_output = xyes)
@@ -1733,11 +1407,8 @@ dnl Documentation
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
if test x$enable_documentation = xyes; then if test x$enable_documentation = xyes; then
AC_PATH_PROG(XMLTO, xmlto) AC_PATH_PROG(XMLTO, xmlto)
if test x$XMLTO = x; then
AC_MSG_ERROR([xmlto not found])
fi
AC_SUBST(XMLTO) AC_SUBST(XMLTO)
AM_CONDITIONAL(HAVE_XMLTO, test x$XMLTO != x)
AC_PATH_PROG(DOXYGEN, doxygen) AC_PATH_PROG(DOXYGEN, doxygen)
if test x$DOXYGEN = x; then if test x$DOXYGEN = x; then
@@ -1745,6 +1416,8 @@ if test x$enable_documentation = xyes; then
fi fi
AC_SUBST(DOXYGEN) AC_SUBST(DOXYGEN)
else
AM_CONDITIONAL(HAVE_XMLTO, false)
fi fi
AM_CONDITIONAL(ENABLE_DOCUMENTATION, test x$enable_documentation = xyes) AM_CONDITIONAL(ENABLE_DOCUMENTATION, test x$enable_documentation = xyes)
@@ -1779,12 +1452,8 @@ AC_LANG_PUSH([C++])
AX_APPEND_COMPILE_FLAGS([-fvisibility=hidden]) AX_APPEND_COMPILE_FLAGS([-fvisibility=hidden])
AX_APPEND_COMPILE_FLAGS([-fno-threadsafe-statics]) AX_APPEND_COMPILE_FLAGS([-fno-threadsafe-statics])
AX_APPEND_COMPILE_FLAGS([-fmerge-all-constants]) AX_APPEND_COMPILE_FLAGS([-fmerge-all-constants])
AX_APPEND_COMPILE_FLAGS([-fno-exceptions])
if test x$no_exceptions = xyes; then AX_APPEND_COMPILE_FLAGS([-fno-rtti])
AX_APPEND_COMPILE_FLAGS([-fno-exceptions])
AX_APPEND_COMPILE_FLAGS([-fno-rtti])
fi
AX_APPEND_COMPILE_FLAGS([-ffast-math]) AX_APPEND_COMPILE_FLAGS([-ffast-math])
AX_APPEND_COMPILE_FLAGS([-ftree-vectorize]) AX_APPEND_COMPILE_FLAGS([-ftree-vectorize])
AC_LANG_POP AC_LANG_POP
@@ -1851,10 +1520,6 @@ results(ipv6, "IPv6")
results(tcp, "TCP") results(tcp, "TCP")
results(un,[UNIX Domain Sockets]) results(un,[UNIX Domain Sockets])
printf '\nStorage support:\n\t'
results(nfs, [NFS])
results(smbclient, [SMB])
printf '\nFile format support:\n\t' printf '\nFile format support:\n\t'
results(aac, [AAC]) results(aac, [AAC])
results(adplug, [AdPlug]) results(adplug, [AdPlug])
@@ -1868,7 +1533,6 @@ printf '\n\t'
results(sndfile, [libsndfile]) results(sndfile, [libsndfile])
results(mikmod, [MikMod]) results(mikmod, [MikMod])
results(modplug, [MODPLUG]) results(modplug, [MODPLUG])
results(mp4v2, [MP4V2])
results(mad, [MAD]) results(mad, [MAD])
results(mpg123, [MPG123]) results(mpg123, [MPG123])
results(mpc, [Musepack]) results(mpc, [Musepack])
@@ -1882,7 +1546,6 @@ results(wildmidi, [WildMidi])
printf '\nOther features:\n\t' printf '\nOther features:\n\t'
results(lsr, [libsamplerate]) results(lsr, [libsamplerate])
results(soxr, [libsoxr])
results(libmpdclient, [libmpdclient]) results(libmpdclient, [libmpdclient])
results(inotify, [inotify]) results(inotify, [inotify])
results(sqlite, [SQLite]) results(sqlite, [SQLite])
@@ -1916,7 +1579,6 @@ if
printf '\nStreaming encoder support:\n\t' printf '\nStreaming encoder support:\n\t'
results(flac_encoder, [FLAC]) results(flac_encoder, [FLAC])
results(lame_encoder, [LAME]) results(lame_encoder, [LAME])
results(shine_encoder, [Shine])
results(vorbis_encoder, [Ogg Vorbis]) results(vorbis_encoder, [Ogg Vorbis])
results(opus, [Opus]) results(opus, [Opus])
results(twolame_encoder, [TwoLAME]) results(twolame_encoder, [TwoLAME])
@@ -1926,15 +1588,11 @@ fi
printf '\nStreaming support:\n\t' printf '\nStreaming support:\n\t'
results(cdio_paranoia, [CDIO_PARANOIA]) results(cdio_paranoia, [CDIO_PARANOIA])
results(curl,[CURL]) results(curl,[CURL])
results(smbclient,[SMBCLIENT])
results(despotify,[Despotify]) results(despotify,[Despotify])
results(soundcloud,[Soundcloud]) results(soundcloud,[Soundcloud])
printf '\n\t' printf '\n\t'
results(mms,[MMS]) results(mms,[MMS])
printf '\nEvent loop:\n\t'
printf $with_pollmethod
printf '\n\n##########################################\n\n' printf '\n\n##########################################\n\n'
echo 'Generating files needed for compilation' echo 'Generating files needed for compilation'
@@ -1944,7 +1602,7 @@ dnl Generate files
dnl --------------------------------------------------------------------------- dnl ---------------------------------------------------------------------------
AC_CONFIG_FILES(Makefile) AC_CONFIG_FILES(Makefile)
AC_CONFIG_FILES(doc/doxygen.conf) AC_CONFIG_FILES(doc/doxygen.conf)
AC_CONFIG_FILES(systemd/mpd.service) AC_CONFIG_FILES(mpd.service)
AC_OUTPUT AC_OUTPUT
echo 'MPD is ready for compilation, type "make" to begin.' echo 'MPD is ready for compilation, type "make" to begin.'

View File

@@ -10,7 +10,7 @@
<para> <para>
This is a guide for those who wish to hack on the MPD source This is a guide for those who wish to hack on the MPD source
code. MPD is an open project, and we are always happy about code. MPD is an open project, and we are always happy about
contributions. So far, more than 150 people have contributed contributions. So far, more than 50 people have contributed
patches. patches.
</para> </para>
@@ -155,53 +155,7 @@ foo(const char *abc, int xyz)
<para> <para>
Send your patches to the mailing list: Send your patches to the mailing list:
<email>mpd-devel@musicpd.org</email> (<ulink mpd-devel@musicpd.org
url="http://mailman.blarg.de/listinfo/mpd-devel">subscribe
here</ulink>)
</para> </para>
<para>
<command>git pull</command> requests are preferred. Regular
contributors can get <ulink
url="http://git.musicpd.org/account-policy.html">an account on
git.musicpd.org</ulink>, but any public git repository will do.
</para>
</chapter>
<chapter>
<title>Development Tools</title>
<section>
<title>Clang Static Analyzer</title>
<para>
The <ulink url="http://clang-analyzer.llvm.org/">clang static
analyzer</ulink> is a tool that helps find bugs. To run it on
the MPD code base, install LLVM and clang. Configure MPD to
use clang:
</para>
<programlisting>./configure --enable-debug CXX=clang++ CC=clang ...</programlisting>
<para>
It is recommended to use <option>--enable-debug</option>,
because the analyzer takes advantage of
<function>assert()</function> calls, which are only enabled in
the debug build.
</para>
<para>
Now run the analyzer:
</para>
<programlisting>scan-build --use-c++=clang++ --use-cc=clang make</programlisting>
<para>
The options <option>--use-c++</option> and
<option>--use-cc</option> are necessary because it invokes
<command>cc</command> for actually compiling the sources by
default. That breaks, because MPD requires a C99 compiler.
</para>
</section>
</chapter> </chapter>
</book> </book>

View File

@@ -136,6 +136,53 @@ for the format of this parameter. Multiple audio_output sections may be
specified. If no audio_output section is specified, then MPD will scan for a specified. If no audio_output section is specified, then MPD will scan for a
usable audio output. usable audio output.
.TP .TP
.B audio_output_format <sample_rate:bits:channels>
This specifies the sample rate, bits per sample, and number of channels of
audio that is sent to each audio output. Note that audio outputs may specify
their own audio format which will be used for actual output to the audio
device. An example is "44100:16:2" for 44100Hz, 16 bits, and 2 channels. The
default is to use the audio format of the input file.
Any of the three attributes may be an asterisk to specify that this
attribute should not be enforced
.TP
.B samplerate_converter <integer or prefix>
This specifies the libsamplerate converter to use. The supplied value should
either be an integer or a prefix of the name of a converter. The default is
"Fastest Sinc Interpolator".
At the time of this writing, the following converters are available:
.RS
.TP
Best Sinc Interpolator (0)
Band limited sinc interpolation, best quality, 97dB SNR, 96% BW.
.TP
Medium Sinc Interpolator (1)
Band limited sinc interpolation, medium quality, 97dB SNR, 90% BW.
.TP
Fastest Sinc Interpolator (2)
Band limited sinc interpolation, fastest, 97dB SNR, 80% BW.
.TP
ZOH Interpolator (3)
Zero order hold interpolator, very fast, very poor quality with audible
distortions.
.TP
Linear Interpolator (4)
Linear interpolator, very fast, poor quality.
.TP
internal
Poor quality, no floating point operations. This is the default (and
only choice) if MPD was compiled without libsamplerate.
.RE
.IP
For an up-to-date list of available converters, please see the libsamplerate
documentation (available online at <\fBhttp://www.mega\-nerd.com/SRC/\fP>).
.TP
.B replaygain <off or album or track or auto> .B replaygain <off or album or track or auto>
If specified, mpd will adjust the volume of songs played using ReplayGain tags If specified, mpd will adjust the volume of songs played using ReplayGain tags
(see <\fBhttp://www.replaygain.org/\fP>). Setting this to "album" will adjust (see <\fBhttp://www.replaygain.org/\fP>). Setting this to "album" will adjust
@@ -151,6 +198,39 @@ This is the gain (in dB) applied to songs with ReplayGain tags.
.B volume_normalization <yes or no> .B volume_normalization <yes or no>
If yes, mpd will normalize the volume of songs as they play. The default is no. If yes, mpd will normalize the volume of songs as they play. The default is no.
.TP .TP
.B audio_buffer_size <size in KiB>
This specifies the size of the audio buffer in kibibytes. The default is 4096,
large enough for nearly 12 seconds of CD-quality audio.
.TP
.B buffer_before_play <0-100%>
This specifies how much of the audio buffer should be filled before playing a
song. Try increasing this if you hear skipping when manually changing songs.
The default is 10%, a little over 1 second of CD-quality audio with the default
buffer size.
.TP
.B http_proxy_host <hostname>
This setting is deprecated. Use the "proxy" setting in the "curl"
input block. See MPD user manual for details.
.TP
.B connection_timeout <seconds>
If a client does not send any new data in this time period, the connection is
closed. The default is 60.
.TP
.B max_connections <number>
This specifies the maximum number of clients that can be connected to mpd. The
default is 5.
.TP
.B max_playlist_length <number>
This specifies the maximum number of songs that can be in the playlist. The
default is 16384.
.TP
.B max_command_list_size <size in KiB>
This specifies the maximum size a command list can be. The default is 2048.
.TP
.B max_output_buffer_size <size in KiB>
This specifies the maximum size of the output buffer to a client. The default
is 8192.
.TP
.B filesystem_charset <charset> .B filesystem_charset <charset>
This specifies the character set used for the filesystem. A list of supported This specifies the character set used for the filesystem. A list of supported
character sets can be obtained by running "iconv \-l". The default is character sets can be obtained by running "iconv \-l". The default is
@@ -180,8 +260,7 @@ clients. Note that you must recreate (not update) your database for changes to
this parameter to take effect. Possible values are artist, album, title, this parameter to take effect. Possible values are artist, album, title,
track, name, genre, date, composer, performer, comment, disc, track, name, genre, date, composer, performer, comment, disc,
musicbrainz_artistid, musicbrainz_albumid, musicbrainz_albumartistid, musicbrainz_artistid, musicbrainz_albumid, musicbrainz_albumartistid,
musicbrainz_releasetrackid, musicbrainz_trackid. Multiple tags may be specified musicbrainz_trackid. Multiple tags may be specified as a comma separated list.
as a comma separated list.
An example value is "artist,album,title,track". The special value "none" may An example value is "artist,album,title,track". The special value "none" may
be used alone to disable all metadata. The default is to use all known tag be used alone to disable all metadata. The default is to use all known tag
types except for comments and those starting with "musicbrainz". types except for comments and those starting with "musicbrainz".

View File

@@ -373,6 +373,38 @@ input {
# #
############################################################################### ###############################################################################
# MPD Internal Buffering ######################################################
#
# This setting adjusts the size of internal decoded audio buffering. Changing
# this may have undesired effects. Don't change this if you don't know what you
# are doing.
#
#audio_buffer_size "4096"
#
# This setting controls the percentage of the buffer which is filled before
# beginning to play. Increasing this reduces the chance of audio file skipping,
# at the cost of increased time prior to audio playback.
#
#buffer_before_play "10%"
#
###############################################################################
# Resource Limitations ########################################################
#
# These settings are various limitations to prevent MPD from using too many
# resources. Generally, these settings should be minimized to prevent security
# risks, depending on the operating resources.
#
#connection_timeout "60"
#max_connections "10"
#max_playlist_length "16384"
#max_command_list_size "2048"
#max_output_buffer_size "8192"
#
###############################################################################
# Character Encoding ########################################################## # Character Encoding ##########################################################
# #
# If file or directory names do not display correctly for your locale then you # If file or directory names do not display correctly for your locale then you

View File

@@ -4,18 +4,18 @@
<book> <book>
<title>The Music Player Daemon protocol</title> <title>The Music Player Daemon protocol</title>
<chapter id="syntax"> <chapter>
<title>General protocol syntax</title> <title>General protocol syntax</title>
<section> <section>
<title>Protocol overview</title> <title>Protocol overview</title>
<para> <para>
The <application>MPD</application> command protocol exchanges The MPD command protocol exchanges line-based text records
line-based text records between client and server over TCP. between client and server over TCP. Once the client is
Once the client is connected to the server, they conduct a connected to the server, they conduct a conversation until the
conversation until the client closes the connection. The client closes the connection. The conversation flow is always
conversation flow is always initiated by the client. initiated by the client.
</para> </para>
<para> <para>
@@ -38,7 +38,7 @@
</para> </para>
</section> </section>
<section id="request_syntax"> <section>
<title>Requests</title> <title>Requests</title>
<cmdsynopsis> <cmdsynopsis>
@@ -70,7 +70,7 @@
</para> </para>
</section> </section>
<section id="response_syntax"> <section>
<title>Responses</title> <title>Responses</title>
<para> <para>
@@ -79,7 +79,7 @@
denote the end of command execution. denote the end of command execution.
</para> </para>
<section id="failure_response_syntax"> <section>
<title>Failure responses</title> <title>Failure responses</title>
<para> <para>
@@ -188,7 +188,7 @@
</para> </para>
</section> </section>
<section id="range_syntax"> <section>
<title>Ranges</title> <title>Ranges</title>
<para> <para>
@@ -203,21 +203,21 @@
</section> </section>
</chapter> </chapter>
<chapter id="recipes"> <chapter>
<title>Recipes</title> <title>Recipes</title>
<section id="queuing_recipe"> <section>
<title>Queuing</title> <title>Queuing</title>
<para> <para>
Often, users run <application>MPD</application> with "<link Often, users run MPD with "<link
linkend="command_random">random</link>" enabled, but want to linkend="command_random">random</link>" enabled, but want to
be able to insert songs "before" the rest of the playlist. be able to insert songs "before" the rest of the playlist.
That is commonly called "queuing". That is commonly called "queuing".
</para> </para>
<para> <para>
<application>MPD</application> implements this by allowing the client to specify a MPD implements this by allowing the client to specify a
"priority" for each song in the playlist (commands <link "priority" for each song in the playlist (commands <link
linkend="command_prio"><command>prio</command></link> and linkend="command_prio"><command>prio</command></link> and
<link <link
@@ -227,25 +227,24 @@
</para> </para>
<para> <para>
In "random" mode, <application>MPD</application> maintains an In "random" mode, MPD maintains an internal randomized
internal randomized sequence of songs. In this sequence, sequence of songs. In this sequence, songs with a higher
songs with a higher priority come first, and all songs with priority come first, and all songs with the same priority are
the same priority are shuffled (by default, all songs are shuffled (by default, all songs are shuffled, because all have
shuffled, because all have the same priority "0"). When you the same priority "0"). When you increase the priority of a
increase the priority of a song, it is moved to the front of song, it is moved to the front of the sequence according to
the sequence according to its new priority, but always after its new priority, but always after the current one. A song
the current one. A song that has been played already (it's that has been played already (it's "before" the current song
"before" the current song in that sequence) will only be in that sequence) will only be scheduled for repeated playback
scheduled for repeated playback if its priority has become if its priority has become bigger than the priority of the
bigger than the priority of the current song. Decreasing the current song. Decreasing the priority of a song will moved it
priority of a song will moved it farther to the end of the farther to the end of the sequence. Changing the priority of
sequence. Changing the priority of the current song has no the current song has no effect on the sequence.
effect on the sequence.
</para> </para>
</section> </section>
</chapter> </chapter>
<chapter id="command_reference"> <chapter>
<title>Command reference</title> <title>Command reference</title>
<note> <note>
@@ -256,12 +255,12 @@
commands using song ids should be used instead of the commands commands using song ids should be used instead of the commands
that manipulate and control playback based on playlist that manipulate and control playback based on playlist
position. Using song ids is a safer method when multiple position. Using song ids is a safer method when multiple
clients are interacting with <application>MPD</application>. clients are interacting with MPD.
</para> </para>
</note> </note>
<section id="status_commands"> <section>
<title>Querying <application>MPD</application>'s status</title> <title>Querying MPD's status</title>
<variablelist> <variablelist>
<varlistentry id="command_clearerror"> <varlistentry id="command_clearerror">
@@ -299,14 +298,12 @@
</term> </term>
<listitem> <listitem>
<para> <para>
<footnote id="since_0_14"><simpara>Introduced with <footnote id="since_0_14"><simpara>Introduced with MPD 0.14</simpara></footnote>
<application>MPD</application> 0.14</simpara></footnote>
Waits until there is a noteworthy change in one or more Waits until there is a noteworthy change in one or more
of <application>MPD</application>'s subsystems. As soon of MPD's subsystems. As soon as there is one, it lists
as there is one, it lists all changed systems in a line all changed systems in a line in the format
in the format <returnvalue>changed: <returnvalue>changed: SUBSYSTEM</returnvalue>, where
SUBSYSTEM</returnvalue>, where SUBSYSTEM is one of the SUBSYSTEM is one of the following:
following:
</para> </para>
<itemizedlist> <itemizedlist>
<listitem> <listitem>
@@ -388,15 +385,14 @@
to wait for events as long as mpd runs. The to wait for events as long as mpd runs. The
<command>idle</command> command can be canceled by <command>idle</command> command can be canceled by
sending the command <command>noidle</command> (no other sending the command <command>noidle</command> (no other
commands are allowed). <application>MPD</application> commands are allowed). MPD will then leave
will then leave <command>idle</command> mode and print <command>idle</command> mode and print results
results immediately; might be empty at this time. immediately; might be empty at this time.
</para> </para>
<para> <para>
If the optional <varname>SUBSYSTEMS</varname> argument If the optional <varname>SUBSYSTEMS</varname> argument is used,
is used, <application>MPD</application> will only send MPD will only send notifications when something changed in
notifications when something changed in one of the one of the specified subsytems.
specified subsytems.
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>
@@ -433,7 +429,7 @@
<listitem> <listitem>
<para> <para>
<varname>single</varname>: <varname>single</varname>:
<footnote id="since_0_15"><simpara>Introduced with <application>MPD</application> 0.15</simpara></footnote> <footnote id="since_0_15"><simpara>Introduced with MPD 0.15</simpara></footnote>
<returnvalue>0 or 1</returnvalue> <returnvalue>0 or 1</returnvalue>
</para> </para>
</listitem> </listitem>
@@ -508,7 +504,7 @@
<listitem> <listitem>
<para> <para>
<varname>elapsed</varname>: <varname>elapsed</varname>:
<footnote id="since_0_16"><simpara>Introduced with <application>MPD</application> 0.16</simpara></footnote> <footnote id="since_0_16"><simpara>Introduced with MPD 0.16</simpara></footnote>
<returnvalue> <returnvalue>
Total time elapsed within the current song, but Total time elapsed within the current song, but
with higher resolution. with higher resolution.
@@ -616,7 +612,7 @@
</variablelist> </variablelist>
</section> </section>
<section id="playback_option_commands"> <section>
<title>Playback options</title> <title>Playback options</title>
<variablelist> <variablelist>
@@ -749,7 +745,7 @@
<parameter>album</parameter>, <parameter>album</parameter>,
<parameter>auto</parameter><footnote <parameter>auto</parameter><footnote
id="replay_gain_auto_since_0_16"> id="replay_gain_auto_since_0_16">
<simpara>added in <application>MPD</application> 0.16</simpara> <simpara>added in MPD 0.16</simpara>
</footnote>. </footnote>.
</para> </para>
<para> <para>
@@ -799,7 +795,7 @@
</variablelist> </variablelist>
</section> </section>
<section id="playback_commands"> <section>
<title>Controlling playback</title> <title>Controlling playback</title>
<variablelist> <variablelist>
@@ -886,8 +882,8 @@
<listitem> <listitem>
<para> <para>
Seeks to the position <varname>TIME</varname> (in Seeks to the position <varname>TIME</varname> (in
seconds; fractions allowed) of entry seconds) of entry <varname>SONGPOS</varname> in the
<varname>SONGPOS</varname> in the playlist. playlist.
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>
@@ -902,8 +898,7 @@
<listitem> <listitem>
<para> <para>
Seeks to the position <varname>TIME</varname> (in Seeks to the position <varname>TIME</varname> (in
seconds; fractions allowed) of song seconds) of song <varname>SONGID</varname>.
<varname>SONGID</varname>.
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>
@@ -917,10 +912,9 @@
</term> </term>
<listitem> <listitem>
<para> <para>
Seeks to the position <varname>TIME</varname> (in Seeks to the position <varname>TIME</varname> within the
seconds; fractions allowed) within the current song. If current song. If prefixed by '+' or '-', then the time
prefixed by '+' or '-', then the time is relative to the is relative to the current playing position.
current playing position.
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>
@@ -940,7 +934,7 @@
</variablelist> </variablelist>
</section> </section>
<section id="queue"> <section>
<title>The current playlist</title> <title>The current playlist</title>
<variablelist> <variablelist>
@@ -1041,7 +1035,7 @@ OK
at <varname>START:END</varname> to <varname>TO</varname> at <varname>START:END</varname> to <varname>TO</varname>
in the playlist. in the playlist.
<footnote id="range_since_0_15"> <footnote id="range_since_0_15">
<simpara>Ranges are supported since <application>MPD</application> 0.15</simpara> <simpara>Ranges are supported since MPD 0.15</simpara>
</footnote> </footnote>
</para> </para>
</listitem> </listitem>
@@ -1224,28 +1218,6 @@ OK
</listitem> </listitem>
</varlistentry> </varlistentry>
<varlistentry id="command_rangeid">
<term>
<cmdsynopsis>
<command>rangeid</command>
<arg choice="req"><replaceable>ID</replaceable></arg>
<arg choice="req"><replaceable>START:END</replaceable></arg>
</cmdsynopsis>
</term>
<listitem>
<para>
<footnote id="since_0_19"><simpara>Since <application>MPD</application>
0.19</simpara></footnote> Specifies the portion of the
song that shall be played. <varname>START</varname> and
<varname>END</varname> are offsets in seconds
(fractional seconds allowed); both are optional.
Omitting both (i.e. sending just ":") means "remove the
range, play everything". A song that is currently
playing cannot be manipulated this way.
</para>
</listitem>
</varlistentry>
<varlistentry id="command_shuffle"> <varlistentry id="command_shuffle">
<term> <term>
<cmdsynopsis> <cmdsynopsis>
@@ -1291,48 +1263,10 @@ OK
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>
<varlistentry id="command_addtagid">
<term>
<cmdsynopsis>
<command>addtagid</command>
<arg choice="req"><replaceable>SONGID</replaceable></arg>
<arg choice="req"><replaceable>TAG</replaceable></arg>
<arg choice="req"><replaceable>VALUE</replaceable></arg>
</cmdsynopsis>
</term>
<listitem>
<para>
Adds a tag to the specified song. Editing song tags is
only possible for remote songs. This change is
volatile: it may be overwritten by tags received from
the server, and the data is gone when the song gets
removed from the queue.
</para>
</listitem>
</varlistentry>
<varlistentry id="command_cleartagid">
<term>
<cmdsynopsis>
<command>cleartagid</command>
<arg choice="req"><replaceable>SONGID</replaceable></arg>
<arg choice="opt"><replaceable>TAG</replaceable></arg>
</cmdsynopsis>
</term>
<listitem>
<para>
Removes tags from the specified song. If
<varname>TAG</varname> is not specified, then all tag
values will be removed. Editing song tags is only
possible for remote songs.
</para>
</listitem>
</varlistentry>
</variablelist> </variablelist>
</section> </section>
<section id="playlist_files"> <section>
<title>Stored playlists</title> <title>Stored playlists</title>
<para> <para>
@@ -1522,19 +1456,16 @@ OK
</variablelist> </variablelist>
</section> </section>
<section id="database"> <section>
<title>The music database</title> <title>The music database</title>
<variablelist> <variablelist>
<varlistentry id="command_count"> <varlistentry id="command_count">
<term> <term>
<cmdsynopsis> <cmdsynopsis>
<command>count</command> <command>count</command>
<arg choice="req"><replaceable>TAG</replaceable></arg> <arg choice="req"><replaceable>TAG</replaceable></arg>
<arg choice="req"><replaceable>NEEDLE</replaceable></arg> <arg choice="req"><replaceable>NEEDLE</replaceable></arg>
<arg choice="opt">group</arg>
<arg choice="opt"><replaceable>GROUPTYPE</replaceable></arg>
</cmdsynopsis> </cmdsynopsis>
</term> </term>
<listitem> <listitem>
@@ -1542,15 +1473,8 @@ OK
Counts the number of songs and their total playtime in Counts the number of songs and their total playtime in
the db matching <varname>TAG</varname> exactly. the db matching <varname>TAG</varname> exactly.
</para> </para>
<para>
The <parameter>group</parameter> keyword may be used to
group the results by a tag. The following prints
per-artist counts:
</para>
<programlisting>count group artist</programlisting>
</listitem> </listitem>
</varlistentry> </varlistentry>
<varlistentry id="command_find"> <varlistentry id="command_find">
<term> <term>
<cmdsynopsis> <cmdsynopsis>
@@ -1564,43 +1488,15 @@ OK
<para> <para>
Finds songs in the db that are exactly Finds songs in the db that are exactly
<varname>WHAT</varname>. <varname>TYPE</varname> can <varname>WHAT</varname>. <varname>TYPE</varname> can
be any tag supported by <application>MPD</application>, or one of the special be any tag supported by MPD, or one of the three special
parameters: parameters<parameter>file</parameter> to search by
</para>
<itemizedlist> full path (relative to the music directory),
<listitem> <parameter>in</parameter> to restrict the search to
<para> songs in the given directory (also relative to the music
<parameter>any</parameter> checks all tag values directory) and
</para> <parameter>any</parameter> to match against all
</listitem> available tags. <varname>WHAT</varname> is what to find.
<listitem>
<para>
<parameter>file</parameter> checks the full path
(relative to the music directory)
</para>
</listitem>
<listitem>
<para>
<parameter>base</parameter> restricts the search to
songs in the given directory (also relative to the
music directory)
</para>
</listitem>
<listitem>
<para>
<parameter>modified-since</parameter> compares the
file's time stamp with the given value (ISO 8601 or
UNIX time stamp)
</para>
</listitem>
</itemizedlist>
<para>
<varname>WHAT</varname> is what to find.
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>
@@ -1621,43 +1517,27 @@ OK
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>
<varlistentry id="command_list"> <varlistentry id="command_list">
<term> <term>
<cmdsynopsis> <cmdsynopsis>
<command>list</command> <command>list</command>
<arg choice="req"><replaceable>TYPE</replaceable></arg> <arg choice="req"><replaceable>TYPE</replaceable></arg>
<arg choice="opt"><replaceable>FILTERTYPE</replaceable></arg> <arg><replaceable>ARTIST</replaceable></arg>
<arg choice="opt"><replaceable>FILTERWHAT</replaceable></arg>
<arg choice="opt"><replaceable>...</replaceable></arg>
<arg choice="opt">group</arg>
<arg choice="opt"><replaceable>GROUPTYPE</replaceable></arg>
<arg choice="opt"><replaceable>...</replaceable></arg>
</cmdsynopsis> </cmdsynopsis>
</term> </term>
<listitem> <listitem>
<para> <para>
Lists unique tags values of the specified type. Lists all tags of the specified type.
<varname>TYPE</varname> can be any tag supported by <varname>TYPE</varname> can be any tag supported by MPD or
<application>MPD</application> or
<parameter>file</parameter>. <parameter>file</parameter>.
</para> </para>
<para> <para>
Additional arguments may specify a filter like the one <varname>ARTIST</varname> is an optional parameter when
in the <link type is album, this specifies to list albums by an
linkend="command_find"><command>find</command> artist.
command</link>.
</para> </para>
<para>
The <parameter>group</parameter> keyword may be used
(repeatedly) to group the results by one or more tags.
The following example lists all album names,
grouped by their respective (album) artist:
</para>
<programlisting>list album group albumartist</programlisting>
</listitem> </listitem>
</varlistentry> </varlistentry>
<varlistentry id="command_listall"> <varlistentry id="command_listall">
<term> <term>
<cmdsynopsis> <cmdsynopsis>
@@ -1670,14 +1550,6 @@ OK
Lists all songs and directories in Lists all songs and directories in
<varname>URI</varname>. <varname>URI</varname>.
</para> </para>
<para>
Do not use this command. Do not manage a client-side
copy of <application>MPD</application>'s database. That
is fragile and adds huge overhead. It will break with
large databases. Instead, query
<application>MPD</application> whenever you need
something.
</para>
</listitem> </listitem>
</varlistentry> </varlistentry>
<varlistentry id="command_listallinfo"> <varlistentry id="command_listallinfo">
@@ -1693,40 +1565,6 @@ OK
returns metadata info in the same format as returns metadata info in the same format as
<command>lsinfo</command>. <command>lsinfo</command>.
</para> </para>
<para>
Do not use this command. Do not manage a client-side
copy of <application>MPD</application>'s database. That
is fragile and adds huge overhead. It will break with
large databases. Instead, query
<application>MPD</application> whenever you need
something.
</para>
</listitem>
</varlistentry>
<varlistentry id="command_listfiles">
<term>
<cmdsynopsis>
<command>listfiles</command>
<arg><replaceable>URI</replaceable></arg>
</cmdsynopsis>
</term>
<listitem>
<para>
Lists the contents of the directory
<varname>URI</varname>, including files are not
recognized by <application>MPD</application>.
<varname>URI</varname> can be a path relative to the
music directory or an URI understood by one of the
storage plugins. The response contains at least one
line for each directory entry with the prefix "file: "
or "directory: ", and may be followed by file attributes
such as "Last-Modified" and "size".
</para>
<para>
For example, "smb://SERVER" returns a list of all shares
on the given SMB/CIFS server; "nfs://servername/path"
obtains a directory listing from the NFS server.
</para>
</listitem> </listitem>
</varlistentry> </varlistentry>
<varlistentry id="command_lsinfo"> <varlistentry id="command_lsinfo">
@@ -1746,10 +1584,6 @@ OK
the list of stored playlists. This behavior is the list of stored playlists. This behavior is
deprecated; use "listplaylists" instead. deprecated; use "listplaylists" instead.
</para> </para>
<para>
This command may be used to list metadata of remote
files (e.g. URI beginning with "http://" or "smb://").
</para>
<para> <para>
Clients that are connected via UNIX domain socket may Clients that are connected via UNIX domain socket may
use this command to read the tags of an arbitrary local use this command to read the tags of an arbitrary local
@@ -1771,10 +1605,6 @@ OK
to the music directory or a URL in the form to the music directory or a URL in the form
"file:///foo/bar.ogg". "file:///foo/bar.ogg".
</para> </para>
<para>
This command may be used to list metadata of remote
files (e.g. URI beginning with "http://" or "smb://").
</para>
<para> <para>
The response consists of lines in the form "KEY: VALUE". The response consists of lines in the form "KEY: VALUE".
Comments with suspicious characters (e.g. newlines) are Comments with suspicious characters (e.g. newlines) are
@@ -1892,131 +1722,22 @@ OK
</variablelist> </variablelist>
</section> </section>
<section id="mount"> <section>
<title>Mounts and neighbors</title>
<para>
A "storage" provides access to files in a directory tree. The
most basic storage plugin is the "local" storage plugin which
accesses the local file system, and there are plugins to
access NFS and SMB servers.
</para>
<para>
Multiple storages can be "mounted" together, similar to the
<application>mount</application> command on many operating
systems, but without cooperation from the kernel. No
superuser privileges are necessary, beause this mapping exists
only inside the <application>MPD</application> process
</para>
<variablelist>
<varlistentry id="command_mount">
<term>
<cmdsynopsis>
<command>mount</command>
<arg choice="req"><replaceable>PATH</replaceable></arg>
<arg choice="req"><replaceable>URI</replaceable></arg>
</cmdsynopsis>
</term>
<listitem>
<para>
Mount the specified remote storage URI at the given
path. Example:
</para>
<programlisting>mount foo nfs://192.168.1.4/export/mp3</programlisting>
</listitem>
</varlistentry>
<varlistentry id="command_umount">
<term>
<cmdsynopsis>
<command>unmount</command>
<arg choice="req"><replaceable>PATH</replaceable></arg>
</cmdsynopsis>
</term>
<listitem>
<para>
Unmounts the specified path. Example:
</para>
<programlisting>unmount foo</programlisting>
</listitem>
</varlistentry>
<varlistentry id="command_listmounts">
<term>
<cmdsynopsis>
<command>listmounts</command>
</cmdsynopsis>
</term>
<listitem>
<para>
Queries a list of all mounts. By default, this contains
just the configured <varname>music_directory</varname>.
Example:
</para>
<programlisting>listmounts
mount:
storage: /home/foo/music
mount: foo
storage: nfs://192.168.1.4/export/mp3
OK
</programlisting>
</listitem>
</varlistentry>
<varlistentry id="command_listneighbors">
<term>
<cmdsynopsis>
<command>listneighbors</command>
</cmdsynopsis>
</term>
<listitem>
<para>
Queries a list of "neighbors" (e.g. accessible file
servers on the local net). Items on that list may be
used with the <link
linkend="command_mount"><command>mount</command></link>
command. Example:
</para>
<programlisting>listneighbors
neighbor: smb://FOO
name: FOO (Samba 4.1.11-Debian)
OK
</programlisting>
</listitem>
</varlistentry>
</variablelist>
</section>
<section id="stickers">
<title>Stickers</title> <title>Stickers</title>
<para> <para>
"Stickers"<footnoteref linkend="since_0_15"/> are pieces of "Stickers"<footnoteref linkend="since_0_15"/> are pieces of
information attached to existing information attached to existing MPD objects (e.g. song files,
<application>MPD</application> objects (e.g. song files,
directories, albums). Clients can create arbitrary name/value directories, albums). Clients can create arbitrary name/value
pairs. <application>MPD</application> itself does not assume pairs. MPD itself does not assume any special meaning in
any special meaning in them. them.
</para> </para>
<para> <para>
The goal is to allow clients to share additional (possibly The goal is to allow clients to share additional (possibly
dynamic) information about songs, which is neither stored on dynamic) information about songs, which is neither stored on
the client (not available to other clients), nor stored in the the client (not available to other clients), nor stored in the
song files (<application>MPD</application> has no write song files (MPD has no write access).
access).
</para> </para>
<para> <para>
@@ -2121,7 +1842,7 @@ OK
</variablelist> </variablelist>
</section> </section>
<section id="connection_commands"> <section>
<title>Connection settings</title> <title>Connection settings</title>
<variablelist> <variablelist>
@@ -2133,8 +1854,7 @@ OK
</term> </term>
<listitem> <listitem>
<para> <para>
Closes the connection to <application>MPD</application>. Closes the connection to MPD. MPD will try to send the
<application>MPD</application> will try to send the
remaining output buffer before it actually closes the remaining output buffer before it actually closes the
connection, but that cannot be guaranteed. This command connection, but that cannot be guaranteed. This command
will not generate a response. will not generate a response.
@@ -2149,7 +1869,7 @@ OK
</term> </term>
<listitem> <listitem>
<para> <para>
Kills <application>MPD</application>. Kills MPD.
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>
@@ -2183,7 +1903,7 @@ OK
</variablelist> </variablelist>
</section> </section>
<section id="output_commands"> <section>
<title>Audio output devices</title> <title>Audio output devices</title>
<variablelist> <variablelist>
@@ -2237,38 +1957,12 @@ OK
<para> <para>
Shows information about all outputs. Shows information about all outputs.
</para> </para>
<screen>
outputid: 0
outputname: My ALSA Device
outputenabled: 0
OK
</screen>
<para>
Return information:
</para>
<itemizedlist>
<listitem>
<para>
<varname>outputid</varname>: ID of the output. May change between executions
</para>
</listitem>
<listitem>
<para>
<varname>outputname</varname>: Name of the output. It can be any.
</para>
</listitem>
<listitem>
<para>
<varname>outputenabled</varname>: Status of the output. 0 if disabled, 1 if enabled.
</para>
</listitem>
</itemizedlist>
</listitem> </listitem>
</varlistentry> </varlistentry>
</variablelist> </variablelist>
</section> </section>
<section id="reflection_commands"> <section>
<title>Reflection</title> <title>Reflection</title>
<variablelist> <variablelist>
@@ -2384,7 +2078,7 @@ suffix: mpc</programlisting>
</variablelist> </variablelist>
</section> </section>
<section id="client_to_client"> <section>
<title>Client to client</title> <title>Client to client</title>
<para> <para>

File diff suppressed because it is too large Load Diff

View File

@@ -54,12 +54,10 @@
# modified version of the Autoconf Macro, you may extend this special # modified version of the Autoconf Macro, you may extend this special
# exception to the GPL to apply to your modified version as well. # exception to the GPL to apply to your modified version as well.
#serial 4 #serial 2
AC_DEFUN([AX_APPEND_COMPILE_FLAGS], AC_DEFUN([AX_APPEND_COMPILE_FLAGS],
[AX_REQUIRE_DEFINED([AX_CHECK_COMPILE_FLAG]) [for flag in $1; do
AX_REQUIRE_DEFINED([AX_APPEND_FLAG])
for flag in $1; do
AX_CHECK_COMPILE_FLAG([$flag], [AX_APPEND_FLAG([$flag], [$2])], [], [$3]) AX_CHECK_COMPILE_FLAG([$flag], [AX_APPEND_FLAG([$flag], [$2])], [], [$3])
done done
])dnl AX_APPEND_COMPILE_FLAGS ])dnl AX_APPEND_COMPILE_FLAGS

View File

@@ -52,12 +52,10 @@
# modified version of the Autoconf Macro, you may extend this special # modified version of the Autoconf Macro, you may extend this special
# exception to the GPL to apply to your modified version as well. # exception to the GPL to apply to your modified version as well.
#serial 4 #serial 2
AC_DEFUN([AX_APPEND_LINK_FLAGS], AC_DEFUN([AX_APPEND_LINK_FLAGS],
[AX_REQUIRE_DEFINED([AX_CHECK_LINK_FLAG]) [for flag in $1; do
AX_REQUIRE_DEFINED([AX_APPEND_FLAG])
for flag in $1; do
AX_CHECK_LINK_FLAG([$flag], [AX_APPEND_FLAG([$flag], [m4_default([$2], [LDFLAGS])])], [], [$3]) AX_CHECK_LINK_FLAG([$flag], [AX_APPEND_FLAG([$flag], [m4_default([$2], [LDFLAGS])])], [], [$3])
done done
])dnl AX_APPEND_LINK_FLAGS ])dnl AX_APPEND_LINK_FLAGS

View File

@@ -1,272 +0,0 @@
# ===========================================================================
# http://www.gnu.org/software/autoconf-archive/ax_boost_base.html
# ===========================================================================
#
# SYNOPSIS
#
# AX_BOOST_BASE([MINIMUM-VERSION], [ACTION-IF-FOUND], [ACTION-IF-NOT-FOUND])
#
# DESCRIPTION
#
# Test for the Boost C++ libraries of a particular version (or newer)
#
# If no path to the installed boost library is given the macro searchs
# under /usr, /usr/local, /opt and /opt/local and evaluates the
# $BOOST_ROOT environment variable. Further documentation is available at
# <http://randspringer.de/boost/index.html>.
#
# This macro calls:
#
# AC_SUBST(BOOST_CPPFLAGS) / AC_SUBST(BOOST_LDFLAGS)
#
# And sets:
#
# HAVE_BOOST
#
# LICENSE
#
# Copyright (c) 2008 Thomas Porschberg <thomas@randspringer.de>
# Copyright (c) 2009 Peter Adolphs
#
# Copying and distribution of this file, with or without modification, are
# permitted in any medium without royalty provided the copyright notice
# and this notice are preserved. This file is offered as-is, without any
# warranty.
#serial 23
AC_DEFUN([AX_BOOST_BASE],
[
AC_ARG_WITH([boost],
[AS_HELP_STRING([--with-boost@<:@=ARG@:>@],
[use Boost library from a standard location (ARG=yes),
from the specified location (ARG=<path>),
or disable it (ARG=no)
@<:@ARG=yes@:>@ ])],
[
if test "$withval" = "no"; then
want_boost="no"
elif test "$withval" = "yes"; then
want_boost="yes"
ac_boost_path=""
else
want_boost="yes"
ac_boost_path="$withval"
fi
],
[want_boost="yes"])
AC_ARG_WITH([boost-libdir],
AS_HELP_STRING([--with-boost-libdir=LIB_DIR],
[Force given directory for boost libraries. Note that this will override library path detection, so use this parameter only if default library detection fails and you know exactly where your boost libraries are located.]),
[
if test -d "$withval"
then
ac_boost_lib_path="$withval"
else
AC_MSG_ERROR(--with-boost-libdir expected directory name)
fi
],
[ac_boost_lib_path=""]
)
if test "x$want_boost" = "xyes"; then
boost_lib_version_req=ifelse([$1], ,1.20.0,$1)
boost_lib_version_req_shorten=`expr $boost_lib_version_req : '\([[0-9]]*\.[[0-9]]*\)'`
boost_lib_version_req_major=`expr $boost_lib_version_req : '\([[0-9]]*\)'`
boost_lib_version_req_minor=`expr $boost_lib_version_req : '[[0-9]]*\.\([[0-9]]*\)'`
boost_lib_version_req_sub_minor=`expr $boost_lib_version_req : '[[0-9]]*\.[[0-9]]*\.\([[0-9]]*\)'`
if test "x$boost_lib_version_req_sub_minor" = "x" ; then
boost_lib_version_req_sub_minor="0"
fi
WANT_BOOST_VERSION=`expr $boost_lib_version_req_major \* 100000 \+ $boost_lib_version_req_minor \* 100 \+ $boost_lib_version_req_sub_minor`
AC_MSG_CHECKING(for boostlib >= $boost_lib_version_req)
succeeded=no
dnl On 64-bit systems check for system libraries in both lib64 and lib.
dnl The former is specified by FHS, but e.g. Debian does not adhere to
dnl this (as it rises problems for generic multi-arch support).
dnl The last entry in the list is chosen by default when no libraries
dnl are found, e.g. when only header-only libraries are installed!
libsubdirs="lib"
ax_arch=`uname -m`
case $ax_arch in
x86_64|ppc64|s390x|sparc64|aarch64)
libsubdirs="lib64 lib lib64"
;;
esac
dnl allow for real multi-arch paths e.g. /usr/lib/x86_64-linux-gnu. Give
dnl them priority over the other paths since, if libs are found there, they
dnl are almost assuredly the ones desired.
AC_REQUIRE([AC_CANONICAL_HOST])
libsubdirs="lib/${host_cpu}-${host_os} $libsubdirs"
case ${host_cpu} in
i?86)
libsubdirs="lib/i386-${host_os} $libsubdirs"
;;
esac
dnl first we check the system location for boost libraries
dnl this location ist chosen if boost libraries are installed with the --layout=system option
dnl or if you install boost with RPM
if test "$ac_boost_path" != ""; then
BOOST_CPPFLAGS="-I$ac_boost_path/include"
for ac_boost_path_tmp in $libsubdirs; do
if test -d "$ac_boost_path"/"$ac_boost_path_tmp" ; then
BOOST_LDFLAGS="-L$ac_boost_path/$ac_boost_path_tmp"
break
fi
done
elif test "$cross_compiling" != yes; then
for ac_boost_path_tmp in /usr /usr/local /opt /opt/local ; do
if test -d "$ac_boost_path_tmp/include/boost" && test -r "$ac_boost_path_tmp/include/boost"; then
for libsubdir in $libsubdirs ; do
if ls "$ac_boost_path_tmp/$libsubdir/libboost_"* >/dev/null 2>&1 ; then break; fi
done
BOOST_LDFLAGS="-L$ac_boost_path_tmp/$libsubdir"
BOOST_CPPFLAGS="-I$ac_boost_path_tmp/include"
break;
fi
done
fi
dnl overwrite ld flags if we have required special directory with
dnl --with-boost-libdir parameter
if test "$ac_boost_lib_path" != ""; then
BOOST_LDFLAGS="-L$ac_boost_lib_path"
fi
CPPFLAGS_SAVED="$CPPFLAGS"
CPPFLAGS="$CPPFLAGS $BOOST_CPPFLAGS"
export CPPFLAGS
LDFLAGS_SAVED="$LDFLAGS"
LDFLAGS="$LDFLAGS $BOOST_LDFLAGS"
export LDFLAGS
AC_REQUIRE([AC_PROG_CXX])
AC_LANG_PUSH(C++)
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[
@%:@include <boost/version.hpp>
]], [[
#if BOOST_VERSION >= $WANT_BOOST_VERSION
// Everything is okay
#else
# error Boost version is too old
#endif
]])],[
AC_MSG_RESULT(yes)
succeeded=yes
found_system=yes
],[
])
AC_LANG_POP([C++])
dnl if we found no boost with system layout we search for boost libraries
dnl built and installed without the --layout=system option or for a staged(not installed) version
if test "x$succeeded" != "xyes"; then
_version=0
if test "$ac_boost_path" != ""; then
if test -d "$ac_boost_path" && test -r "$ac_boost_path"; then
for i in `ls -d $ac_boost_path/include/boost-* 2>/dev/null`; do
_version_tmp=`echo $i | sed "s#$ac_boost_path##" | sed 's/\/include\/boost-//' | sed 's/_/./'`
V_CHECK=`expr $_version_tmp \> $_version`
if test "$V_CHECK" = "1" ; then
_version=$_version_tmp
fi
VERSION_UNDERSCORE=`echo $_version | sed 's/\./_/'`
BOOST_CPPFLAGS="-I$ac_boost_path/include/boost-$VERSION_UNDERSCORE"
done
fi
else
if test "$cross_compiling" != yes; then
for ac_boost_path in /usr /usr/local /opt /opt/local ; do
if test -d "$ac_boost_path" && test -r "$ac_boost_path"; then
for i in `ls -d $ac_boost_path/include/boost-* 2>/dev/null`; do
_version_tmp=`echo $i | sed "s#$ac_boost_path##" | sed 's/\/include\/boost-//' | sed 's/_/./'`
V_CHECK=`expr $_version_tmp \> $_version`
if test "$V_CHECK" = "1" ; then
_version=$_version_tmp
best_path=$ac_boost_path
fi
done
fi
done
VERSION_UNDERSCORE=`echo $_version | sed 's/\./_/'`
BOOST_CPPFLAGS="-I$best_path/include/boost-$VERSION_UNDERSCORE"
if test "$ac_boost_lib_path" = ""; then
for libsubdir in $libsubdirs ; do
if ls "$best_path/$libsubdir/libboost_"* >/dev/null 2>&1 ; then break; fi
done
BOOST_LDFLAGS="-L$best_path/$libsubdir"
fi
fi
if test "x$BOOST_ROOT" != "x"; then
for libsubdir in $libsubdirs ; do
if ls "$BOOST_ROOT/stage/$libsubdir/libboost_"* >/dev/null 2>&1 ; then break; fi
done
if test -d "$BOOST_ROOT" && test -r "$BOOST_ROOT" && test -d "$BOOST_ROOT/stage/$libsubdir" && test -r "$BOOST_ROOT/stage/$libsubdir"; then
version_dir=`expr //$BOOST_ROOT : '.*/\(.*\)'`
stage_version=`echo $version_dir | sed 's/boost_//' | sed 's/_/./g'`
stage_version_shorten=`expr $stage_version : '\([[0-9]]*\.[[0-9]]*\)'`
V_CHECK=`expr $stage_version_shorten \>\= $_version`
if test "$V_CHECK" = "1" -a "$ac_boost_lib_path" = "" ; then
AC_MSG_NOTICE(We will use a staged boost library from $BOOST_ROOT)
BOOST_CPPFLAGS="-I$BOOST_ROOT"
BOOST_LDFLAGS="-L$BOOST_ROOT/stage/$libsubdir"
fi
fi
fi
fi
CPPFLAGS="$CPPFLAGS $BOOST_CPPFLAGS"
export CPPFLAGS
LDFLAGS="$LDFLAGS $BOOST_LDFLAGS"
export LDFLAGS
AC_LANG_PUSH(C++)
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[
@%:@include <boost/version.hpp>
]], [[
#if BOOST_VERSION >= $WANT_BOOST_VERSION
// Everything is okay
#else
# error Boost version is too old
#endif
]])],[
AC_MSG_RESULT(yes)
succeeded=yes
found_system=yes
],[
])
AC_LANG_POP([C++])
fi
if test "$succeeded" != "yes" ; then
if test "$_version" = "0" ; then
AC_MSG_NOTICE([[We could not detect the boost libraries (version $boost_lib_version_req_shorten or higher). If you have a staged boost library (still not installed) please specify \$BOOST_ROOT in your environment and do not give a PATH to --with-boost option. If you are sure you have boost installed, then check your version number looking in <boost/version.hpp>. See http://randspringer.de/boost for more documentation.]])
else
AC_MSG_NOTICE([Your boost libraries seems to old (version $_version).])
fi
# execute ACTION-IF-NOT-FOUND (if present):
ifelse([$3], , :, [$3])
else
AC_SUBST(BOOST_CPPFLAGS)
AC_SUBST(BOOST_LDFLAGS)
AC_DEFINE(HAVE_BOOST,,[define if the Boost library is available])
# execute ACTION-IF-FOUND (if present):
ifelse([$2], , :, [$2])
fi
CPPFLAGS="$CPPFLAGS_SAVED"
LDFLAGS="$LDFLAGS_SAVED"
fi
])

View File

@@ -4,7 +4,7 @@
# #
# SYNOPSIS # SYNOPSIS
# #
# AX_CHECK_COMPILE_FLAG(FLAG, [ACTION-SUCCESS], [ACTION-FAILURE], [EXTRA-FLAGS], [INPUT]) # AX_CHECK_COMPILE_FLAG(FLAG, [ACTION-SUCCESS], [ACTION-FAILURE], [EXTRA-FLAGS])
# #
# DESCRIPTION # DESCRIPTION
# #
@@ -19,8 +19,6 @@
# the flags: "CFLAGS EXTRA-FLAGS FLAG". This can for example be used to # the flags: "CFLAGS EXTRA-FLAGS FLAG". This can for example be used to
# force the compiler to issue an error when a bad flag is given. # force the compiler to issue an error when a bad flag is given.
# #
# INPUT gives an alternative input source to AC_COMPILE_IFELSE.
#
# NOTE: Implementation based on AX_CFLAGS_GCC_OPTION. Please keep this # NOTE: Implementation based on AX_CFLAGS_GCC_OPTION. Please keep this
# macro in sync with AX_CHECK_{PREPROC,LINK}_FLAG. # macro in sync with AX_CHECK_{PREPROC,LINK}_FLAG.
# #
@@ -55,7 +53,7 @@
# modified version of the Autoconf Macro, you may extend this special # modified version of the Autoconf Macro, you may extend this special
# exception to the GPL to apply to your modified version as well. # exception to the GPL to apply to your modified version as well.
#serial 3 #serial 2
AC_DEFUN([AX_CHECK_COMPILE_FLAG], AC_DEFUN([AX_CHECK_COMPILE_FLAG],
[AC_PREREQ(2.59)dnl for _AC_LANG_PREFIX [AC_PREREQ(2.59)dnl for _AC_LANG_PREFIX
@@ -63,7 +61,7 @@ AS_VAR_PUSHDEF([CACHEVAR],[ax_cv_check_[]_AC_LANG_ABBREV[]flags_$4_$1])dnl
AC_CACHE_CHECK([whether _AC_LANG compiler accepts $1], CACHEVAR, [ AC_CACHE_CHECK([whether _AC_LANG compiler accepts $1], CACHEVAR, [
ax_check_save_flags=$[]_AC_LANG_PREFIX[]FLAGS ax_check_save_flags=$[]_AC_LANG_PREFIX[]FLAGS
_AC_LANG_PREFIX[]FLAGS="$[]_AC_LANG_PREFIX[]FLAGS $4 $1" _AC_LANG_PREFIX[]FLAGS="$[]_AC_LANG_PREFIX[]FLAGS $4 $1"
AC_COMPILE_IFELSE([m4_default([$5],[AC_LANG_PROGRAM()])], AC_COMPILE_IFELSE([AC_LANG_PROGRAM()],
[AS_VAR_SET(CACHEVAR,[yes])], [AS_VAR_SET(CACHEVAR,[yes])],
[AS_VAR_SET(CACHEVAR,[no])]) [AS_VAR_SET(CACHEVAR,[no])])
_AC_LANG_PREFIX[]FLAGS=$ax_check_save_flags]) _AC_LANG_PREFIX[]FLAGS=$ax_check_save_flags])

View File

@@ -4,7 +4,7 @@
# #
# SYNOPSIS # SYNOPSIS
# #
# AX_CHECK_LINK_FLAG(FLAG, [ACTION-SUCCESS], [ACTION-FAILURE], [EXTRA-FLAGS], [INPUT]) # AX_CHECK_LINK_FLAG(FLAG, [ACTION-SUCCESS], [ACTION-FAILURE], [EXTRA-FLAGS])
# #
# DESCRIPTION # DESCRIPTION
# #
@@ -19,8 +19,6 @@
# EXTRA-FLAGS FLAG". This can for example be used to force the linker to # EXTRA-FLAGS FLAG". This can for example be used to force the linker to
# issue an error when a bad flag is given. # issue an error when a bad flag is given.
# #
# INPUT gives an alternative input source to AC_LINK_IFELSE.
#
# NOTE: Implementation based on AX_CFLAGS_GCC_OPTION. Please keep this # NOTE: Implementation based on AX_CFLAGS_GCC_OPTION. Please keep this
# macro in sync with AX_CHECK_{PREPROC,COMPILE}_FLAG. # macro in sync with AX_CHECK_{PREPROC,COMPILE}_FLAG.
# #
@@ -55,14 +53,14 @@
# modified version of the Autoconf Macro, you may extend this special # modified version of the Autoconf Macro, you may extend this special
# exception to the GPL to apply to your modified version as well. # exception to the GPL to apply to your modified version as well.
#serial 3 #serial 2
AC_DEFUN([AX_CHECK_LINK_FLAG], AC_DEFUN([AX_CHECK_LINK_FLAG],
[AS_VAR_PUSHDEF([CACHEVAR],[ax_cv_check_ldflags_$4_$1])dnl [AS_VAR_PUSHDEF([CACHEVAR],[ax_cv_check_ldflags_$4_$1])dnl
AC_CACHE_CHECK([whether the linker accepts $1], CACHEVAR, [ AC_CACHE_CHECK([whether the linker accepts $1], CACHEVAR, [
ax_check_save_flags=$LDFLAGS ax_check_save_flags=$LDFLAGS
LDFLAGS="$LDFLAGS $4 $1" LDFLAGS="$LDFLAGS $4 $1"
AC_LINK_IFELSE([m4_default([$5],[AC_LANG_PROGRAM()])], AC_LINK_IFELSE([AC_LANG_PROGRAM()],
[AS_VAR_SET(CACHEVAR,[yes])], [AS_VAR_SET(CACHEVAR,[yes])],
[AS_VAR_SET(CACHEVAR,[no])]) [AS_VAR_SET(CACHEVAR,[no])])
LDFLAGS=$ax_check_save_flags]) LDFLAGS=$ax_check_save_flags])

View File

@@ -1,332 +0,0 @@
# ===========================================================================
# http://www.gnu.org/software/autoconf-archive/ax_pthread.html
# ===========================================================================
#
# SYNOPSIS
#
# AX_PTHREAD([ACTION-IF-FOUND[, ACTION-IF-NOT-FOUND]])
#
# DESCRIPTION
#
# This macro figures out how to build C programs using POSIX threads. It
# sets the PTHREAD_LIBS output variable to the threads library and linker
# flags, and the PTHREAD_CFLAGS output variable to any special C compiler
# flags that are needed. (The user can also force certain compiler
# flags/libs to be tested by setting these environment variables.)
#
# Also sets PTHREAD_CC to any special C compiler that is needed for
# multi-threaded programs (defaults to the value of CC otherwise). (This
# is necessary on AIX to use the special cc_r compiler alias.)
#
# NOTE: You are assumed to not only compile your program with these flags,
# but also link it with them as well. e.g. you should link with
# $PTHREAD_CC $CFLAGS $PTHREAD_CFLAGS $LDFLAGS ... $PTHREAD_LIBS $LIBS
#
# If you are only building threads programs, you may wish to use these
# variables in your default LIBS, CFLAGS, and CC:
#
# LIBS="$PTHREAD_LIBS $LIBS"
# CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
# CC="$PTHREAD_CC"
#
# In addition, if the PTHREAD_CREATE_JOINABLE thread-attribute constant
# has a nonstandard name, defines PTHREAD_CREATE_JOINABLE to that name
# (e.g. PTHREAD_CREATE_UNDETACHED on AIX).
#
# Also HAVE_PTHREAD_PRIO_INHERIT is defined if pthread is found and the
# PTHREAD_PRIO_INHERIT symbol is defined when compiling with
# PTHREAD_CFLAGS.
#
# ACTION-IF-FOUND is a list of shell commands to run if a threads library
# is found, and ACTION-IF-NOT-FOUND is a list of commands to run it if it
# is not found. If ACTION-IF-FOUND is not specified, the default action
# will define HAVE_PTHREAD.
#
# Please let the authors know if this macro fails on any platform, or if
# you have any other suggestions or comments. This macro was based on work
# by SGJ on autoconf scripts for FFTW (http://www.fftw.org/) (with help
# from M. Frigo), as well as ac_pthread and hb_pthread macros posted by
# Alejandro Forero Cuervo to the autoconf macro repository. We are also
# grateful for the helpful feedback of numerous users.
#
# Updated for Autoconf 2.68 by Daniel Richard G.
#
# LICENSE
#
# Copyright (c) 2008 Steven G. Johnson <stevenj@alum.mit.edu>
# Copyright (c) 2011 Daniel Richard G. <skunk@iSKUNK.ORG>
#
# 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 3 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, see <http://www.gnu.org/licenses/>.
#
# As a special exception, the respective Autoconf Macro's copyright owner
# gives unlimited permission to copy, distribute and modify the configure
# scripts that are the output of Autoconf when processing the Macro. You
# need not follow the terms of the GNU General Public License when using
# or distributing such scripts, even though portions of the text of the
# Macro appear in them. The GNU General Public License (GPL) does govern
# all other use of the material that constitutes the Autoconf Macro.
#
# This special exception to the GPL applies to versions of the Autoconf
# Macro released by the Autoconf Archive. When you make and distribute a
# modified version of the Autoconf Macro, you may extend this special
# exception to the GPL to apply to your modified version as well.
#serial 21
AU_ALIAS([ACX_PTHREAD], [AX_PTHREAD])
AC_DEFUN([AX_PTHREAD], [
AC_REQUIRE([AC_CANONICAL_HOST])
AC_LANG_PUSH([C])
ax_pthread_ok=no
# We used to check for pthread.h first, but this fails if pthread.h
# requires special compiler flags (e.g. on True64 or Sequent).
# It gets checked for in the link test anyway.
# First of all, check if the user has set any of the PTHREAD_LIBS,
# etcetera environment variables, and if threads linking works using
# them:
if test x"$PTHREAD_LIBS$PTHREAD_CFLAGS" != x; then
save_CFLAGS="$CFLAGS"
CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
save_LIBS="$LIBS"
LIBS="$PTHREAD_LIBS $LIBS"
AC_MSG_CHECKING([for pthread_join in LIBS=$PTHREAD_LIBS with CFLAGS=$PTHREAD_CFLAGS])
AC_TRY_LINK_FUNC([pthread_join], [ax_pthread_ok=yes])
AC_MSG_RESULT([$ax_pthread_ok])
if test x"$ax_pthread_ok" = xno; then
PTHREAD_LIBS=""
PTHREAD_CFLAGS=""
fi
LIBS="$save_LIBS"
CFLAGS="$save_CFLAGS"
fi
# We must check for the threads library under a number of different
# names; the ordering is very important because some systems
# (e.g. DEC) have both -lpthread and -lpthreads, where one of the
# libraries is broken (non-POSIX).
# Create a list of thread flags to try. Items starting with a "-" are
# C compiler flags, and other items are library names, except for "none"
# which indicates that we try without any flags at all, and "pthread-config"
# which is a program returning the flags for the Pth emulation library.
ax_pthread_flags="pthreads none -Kthread -kthread lthread -pthread -pthreads -mthreads pthread --thread-safe -mt pthread-config"
# The ordering *is* (sometimes) important. Some notes on the
# individual items follow:
# pthreads: AIX (must check this before -lpthread)
# none: in case threads are in libc; should be tried before -Kthread and
# other compiler flags to prevent continual compiler warnings
# -Kthread: Sequent (threads in libc, but -Kthread needed for pthread.h)
# -kthread: FreeBSD kernel threads (preferred to -pthread since SMP-able)
# lthread: LinuxThreads port on FreeBSD (also preferred to -pthread)
# -pthread: Linux/gcc (kernel threads), BSD/gcc (userland threads)
# -pthreads: Solaris/gcc
# -mthreads: Mingw32/gcc, Lynx/gcc
# -mt: Sun Workshop C (may only link SunOS threads [-lthread], but it
# doesn't hurt to check since this sometimes defines pthreads too;
# also defines -D_REENTRANT)
# ... -mt is also the pthreads flag for HP/aCC
# pthread: Linux, etcetera
# --thread-safe: KAI C++
# pthread-config: use pthread-config program (for GNU Pth library)
case ${host_os} in
solaris*)
# On Solaris (at least, for some versions), libc contains stubbed
# (non-functional) versions of the pthreads routines, so link-based
# tests will erroneously succeed. (We need to link with -pthreads/-mt/
# -lpthread.) (The stubs are missing pthread_cleanup_push, or rather
# a function called by this macro, so we could check for that, but
# who knows whether they'll stub that too in a future libc.) So,
# we'll just look for -pthreads and -lpthread first:
ax_pthread_flags="-pthreads pthread -mt -pthread $ax_pthread_flags"
;;
darwin*)
ax_pthread_flags="-pthread $ax_pthread_flags"
;;
esac
# Clang doesn't consider unrecognized options an error unless we specify
# -Werror. We throw in some extra Clang-specific options to ensure that
# this doesn't happen for GCC, which also accepts -Werror.
AC_MSG_CHECKING([if compiler needs -Werror to reject unknown flags])
save_CFLAGS="$CFLAGS"
ax_pthread_extra_flags="-Werror"
CFLAGS="$CFLAGS $ax_pthread_extra_flags -Wunknown-warning-option -Wsizeof-array-argument"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([int foo(void);],[foo()])],
[AC_MSG_RESULT([yes])],
[ax_pthread_extra_flags=
AC_MSG_RESULT([no])])
CFLAGS="$save_CFLAGS"
if test x"$ax_pthread_ok" = xno; then
for flag in $ax_pthread_flags; do
case $flag in
none)
AC_MSG_CHECKING([whether pthreads work without any flags])
;;
-*)
AC_MSG_CHECKING([whether pthreads work with $flag])
PTHREAD_CFLAGS="$flag"
;;
pthread-config)
AC_CHECK_PROG([ax_pthread_config], [pthread-config], [yes], [no])
if test x"$ax_pthread_config" = xno; then continue; fi
PTHREAD_CFLAGS="`pthread-config --cflags`"
PTHREAD_LIBS="`pthread-config --ldflags` `pthread-config --libs`"
;;
*)
AC_MSG_CHECKING([for the pthreads library -l$flag])
PTHREAD_LIBS="-l$flag"
;;
esac
save_LIBS="$LIBS"
save_CFLAGS="$CFLAGS"
LIBS="$PTHREAD_LIBS $LIBS"
CFLAGS="$CFLAGS $PTHREAD_CFLAGS $ax_pthread_extra_flags"
# Check for various functions. We must include pthread.h,
# since some functions may be macros. (On the Sequent, we
# need a special flag -Kthread to make this header compile.)
# We check for pthread_join because it is in -lpthread on IRIX
# while pthread_create is in libc. We check for pthread_attr_init
# due to DEC craziness with -lpthreads. We check for
# pthread_cleanup_push because it is one of the few pthread
# functions on Solaris that doesn't have a non-functional libc stub.
# We try pthread_create on general principles.
AC_LINK_IFELSE([AC_LANG_PROGRAM([#include <pthread.h>
static void routine(void *a) { a = 0; }
static void *start_routine(void *a) { return a; }],
[pthread_t th; pthread_attr_t attr;
pthread_create(&th, 0, start_routine, 0);
pthread_join(th, 0);
pthread_attr_init(&attr);
pthread_cleanup_push(routine, 0);
pthread_cleanup_pop(0) /* ; */])],
[ax_pthread_ok=yes],
[])
LIBS="$save_LIBS"
CFLAGS="$save_CFLAGS"
AC_MSG_RESULT([$ax_pthread_ok])
if test "x$ax_pthread_ok" = xyes; then
break;
fi
PTHREAD_LIBS=""
PTHREAD_CFLAGS=""
done
fi
# Various other checks:
if test "x$ax_pthread_ok" = xyes; then
save_LIBS="$LIBS"
LIBS="$PTHREAD_LIBS $LIBS"
save_CFLAGS="$CFLAGS"
CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
# Detect AIX lossage: JOINABLE attribute is called UNDETACHED.
AC_MSG_CHECKING([for joinable pthread attribute])
attr_name=unknown
for attr in PTHREAD_CREATE_JOINABLE PTHREAD_CREATE_UNDETACHED; do
AC_LINK_IFELSE([AC_LANG_PROGRAM([#include <pthread.h>],
[int attr = $attr; return attr /* ; */])],
[attr_name=$attr; break],
[])
done
AC_MSG_RESULT([$attr_name])
if test "$attr_name" != PTHREAD_CREATE_JOINABLE; then
AC_DEFINE_UNQUOTED([PTHREAD_CREATE_JOINABLE], [$attr_name],
[Define to necessary symbol if this constant
uses a non-standard name on your system.])
fi
AC_MSG_CHECKING([if more special flags are required for pthreads])
flag=no
case ${host_os} in
aix* | freebsd* | darwin*) flag="-D_THREAD_SAFE";;
osf* | hpux*) flag="-D_REENTRANT";;
solaris*)
if test "$GCC" = "yes"; then
flag="-D_REENTRANT"
else
# TODO: What about Clang on Solaris?
flag="-mt -D_REENTRANT"
fi
;;
esac
AC_MSG_RESULT([$flag])
if test "x$flag" != xno; then
PTHREAD_CFLAGS="$flag $PTHREAD_CFLAGS"
fi
AC_CACHE_CHECK([for PTHREAD_PRIO_INHERIT],
[ax_cv_PTHREAD_PRIO_INHERIT], [
AC_LINK_IFELSE([AC_LANG_PROGRAM([[#include <pthread.h>]],
[[int i = PTHREAD_PRIO_INHERIT;]])],
[ax_cv_PTHREAD_PRIO_INHERIT=yes],
[ax_cv_PTHREAD_PRIO_INHERIT=no])
])
AS_IF([test "x$ax_cv_PTHREAD_PRIO_INHERIT" = "xyes"],
[AC_DEFINE([HAVE_PTHREAD_PRIO_INHERIT], [1], [Have PTHREAD_PRIO_INHERIT.])])
LIBS="$save_LIBS"
CFLAGS="$save_CFLAGS"
# More AIX lossage: compile with *_r variant
if test "x$GCC" != xyes; then
case $host_os in
aix*)
AS_CASE(["x/$CC"],
[x*/c89|x*/c89_128|x*/c99|x*/c99_128|x*/cc|x*/cc128|x*/xlc|x*/xlc_v6|x*/xlc128|x*/xlc128_v6],
[#handle absolute path differently from PATH based program lookup
AS_CASE(["x$CC"],
[x/*],
[AS_IF([AS_EXECUTABLE_P([${CC}_r])],[PTHREAD_CC="${CC}_r"])],
[AC_CHECK_PROGS([PTHREAD_CC],[${CC}_r],[$CC])])])
;;
esac
fi
fi
test -n "$PTHREAD_CC" || PTHREAD_CC="$CC"
AC_SUBST([PTHREAD_LIBS])
AC_SUBST([PTHREAD_CFLAGS])
AC_SUBST([PTHREAD_CC])
# Finally, execute ACTION-IF-FOUND/ACTION-IF-NOT-FOUND:
if test x"$ax_pthread_ok" = xyes; then
ifelse([$1],,[AC_DEFINE([HAVE_PTHREAD],[1],[Define if you have POSIX threads libraries and header files.])],[$1])
:
else
ax_pthread_ok=no
$2
fi
AC_LANG_POP
])dnl AX_PTHREAD

View File

@@ -1,37 +0,0 @@
# ===========================================================================
# http://www.gnu.org/software/autoconf-archive/ax_require_defined.html
# ===========================================================================
#
# SYNOPSIS
#
# AX_REQUIRE_DEFINED(MACRO)
#
# DESCRIPTION
#
# AX_REQUIRE_DEFINED is a simple helper for making sure other macros have
# been defined and thus are available for use. This avoids random issues
# where a macro isn't expanded. Instead the configure script emits a
# non-fatal:
#
# ./configure: line 1673: AX_CFLAGS_WARN_ALL: command not found
#
# It's like AC_REQUIRE except it doesn't expand the required macro.
#
# Here's an example:
#
# AX_REQUIRE_DEFINED([AX_CHECK_LINK_FLAG])
#
# LICENSE
#
# Copyright (c) 2014 Mike Frysinger <vapier@gentoo.org>
#
# Copying and distribution of this file, with or without modification, are
# permitted in any medium without royalty provided the copyright notice
# and this notice are preserved. This file is offered as-is, without any
# warranty.
#serial 1
AC_DEFUN([AX_REQUIRE_DEFINED], [dnl
m4_ifndef([$1], [m4_fatal([macro ]$1[ is not defined; is a m4 file missing?])])
])dnl AX_REQUIRE_DEFINED

View File

@@ -1,9 +0,0 @@
AC_DEFUN([MPD_DEPENDS], [
if test x$$2 = xno; then
if test x$$1 = xauto; then
$1=no
elif test x$$1 = xyes; then
AC_MSG_ERROR([$3])
fi
fi
])

View File

@@ -10,16 +10,3 @@ AC_DEFUN([MPD_OPTIONAL_FUNC], [
[AC_CHECK_FUNC([$2], [AC_CHECK_FUNC([$2],
[AC_DEFINE([$3], 1, [Define to use $1])],)]) [AC_DEFINE([$3], 1, [Define to use $1])],)])
]) ])
dnl MPD_OPTIONAL_FUNC_NODEF(name, func)
dnl
dnl Allow the user to enable or disable the use of a function.
dnl Works similar to MPD_OPTIONAL_FUNC, however MPD_OPTIONAL_FUNC_NODEF
dnl does not invoke AC_DEFINE when function is enabled. Shell variable
dnl enable_$name is set to "yes" instead.
AC_DEFUN([MPD_OPTIONAL_FUNC_NODEF], [
AC_ARG_ENABLE([$1],
AS_HELP_STRING([--enable-$1],
[use the function "$1" (default: auto)]),,
[AC_CHECK_FUNC([$2], [enable_$1=yes],)])
])

117
m4/pkg.m4
View File

@@ -1,5 +1,4 @@
# pkg.m4 - Macros to locate and utilise pkg-config. -*- Autoconf -*- # pkg.m4 - Macros to locate and utilise pkg-config. -*- Autoconf -*-
# serial 1 (pkg-config-0.24)
# #
# Copyright © 2004 Scott James Remnant <scott@netsplit.com>. # Copyright © 2004 Scott James Remnant <scott@netsplit.com>.
# #
@@ -26,12 +25,8 @@
# ---------------------------------- # ----------------------------------
AC_DEFUN([PKG_PROG_PKG_CONFIG], AC_DEFUN([PKG_PROG_PKG_CONFIG],
[m4_pattern_forbid([^_?PKG_[A-Z_]+$]) [m4_pattern_forbid([^_?PKG_[A-Z_]+$])
m4_pattern_allow([^PKG_CONFIG(_(PATH|LIBDIR|SYSROOT_DIR|ALLOW_SYSTEM_(CFLAGS|LIBS)))?$]) m4_pattern_allow([^PKG_CONFIG(_PATH)?$])
m4_pattern_allow([^PKG_CONFIG_(DISABLE_UNINSTALLED|TOP_BUILD_DIR|DEBUG_SPEW)$]) AC_ARG_VAR([PKG_CONFIG], [path to pkg-config utility])dnl
AC_ARG_VAR([PKG_CONFIG], [path to pkg-config utility])
AC_ARG_VAR([PKG_CONFIG_PATH], [directories to add to pkg-config's search path])
AC_ARG_VAR([PKG_CONFIG_LIBDIR], [path overriding pkg-config's built-in search path])
if test "x$ac_cv_env_PKG_CONFIG_set" != "xset"; then if test "x$ac_cv_env_PKG_CONFIG_set" != "xset"; then
AC_PATH_TOOL([PKG_CONFIG], [pkg-config]) AC_PATH_TOOL([PKG_CONFIG], [pkg-config])
fi fi
@@ -44,6 +39,7 @@ if test -n "$PKG_CONFIG"; then
AC_MSG_RESULT([no]) AC_MSG_RESULT([no])
PKG_CONFIG="" PKG_CONFIG=""
fi fi
fi[]dnl fi[]dnl
])# PKG_PROG_PKG_CONFIG ])# PKG_PROG_PKG_CONFIG
@@ -52,32 +48,34 @@ fi[]dnl
# Check to see whether a particular set of modules exists. Similar # Check to see whether a particular set of modules exists. Similar
# to PKG_CHECK_MODULES(), but does not set variables or print errors. # to PKG_CHECK_MODULES(), but does not set variables or print errors.
# #
# Please remember that m4 expands AC_REQUIRE([PKG_PROG_PKG_CONFIG]) #
# only at the first occurence in configure.ac, so if the first place # Similar to PKG_CHECK_MODULES, make sure that the first instance of
# it's called might be skipped (such as if it is within an "if", you # this or PKG_CHECK_MODULES is called, or make sure to call
# have to call PKG_CHECK_EXISTS manually # PKG_CHECK_EXISTS manually
# -------------------------------------------------------------- # --------------------------------------------------------------
AC_DEFUN([PKG_CHECK_EXISTS], AC_DEFUN([PKG_CHECK_EXISTS],
[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl [AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl
if test -n "$PKG_CONFIG" && \ if test -n "$PKG_CONFIG" && \
AC_RUN_LOG([$PKG_CONFIG --exists --print-errors "$1"]); then AC_RUN_LOG([$PKG_CONFIG --exists --print-errors "$1"]); then
m4_default([$2], [:]) m4_ifval([$2], [$2], [:])
m4_ifvaln([$3], [else m4_ifvaln([$3], [else
$3])dnl $3])dnl
fi]) fi])
# _PKG_CONFIG([VARIABLE], [COMMAND], [MODULES]) # _PKG_CONFIG([VARIABLE], [COMMAND], [MODULES])
# --------------------------------------------- # ---------------------------------------------
m4_define([_PKG_CONFIG], m4_define([_PKG_CONFIG],
[if test -n "$$1"; then [if test -n "$PKG_CONFIG"; then
pkg_cv_[]$1="$$1" if test -n "$$1"; then
elif test -n "$PKG_CONFIG"; then pkg_cv_[]$1="$$1"
PKG_CHECK_EXISTS([$3], else
[pkg_cv_[]$1=`$PKG_CONFIG --[]$2 "$3" 2>/dev/null` PKG_CHECK_EXISTS([$3],
test "x$?" != "x0" && pkg_failed=yes ], [pkg_cv_[]$1=`$PKG_CONFIG --[]$2 "$3" 2>/dev/null`],
[pkg_failed=yes]) [pkg_failed=yes])
else fi
pkg_failed=untried else
pkg_failed=untried
fi[]dnl fi[]dnl
])# _PKG_CONFIG ])# _PKG_CONFIG
@@ -119,17 +117,16 @@ and $1[]_LIBS to avoid the need to call pkg-config.
See the pkg-config man page for more details.]) See the pkg-config man page for more details.])
if test $pkg_failed = yes; then if test $pkg_failed = yes; then
AC_MSG_RESULT([no])
_PKG_SHORT_ERRORS_SUPPORTED _PKG_SHORT_ERRORS_SUPPORTED
if test $_pkg_short_errors_supported = yes; then if test $_pkg_short_errors_supported = yes; then
$1[]_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "$2" 2>&1` $1[]_PKG_ERRORS=`$PKG_CONFIG --short-errors --errors-to-stdout --print-errors "$2"`
else else
$1[]_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "$2" 2>&1` $1[]_PKG_ERRORS=`$PKG_CONFIG --errors-to-stdout --print-errors "$2"`
fi fi
# Put the nasty error message in config.log where it belongs # Put the nasty error message in config.log where it belongs
echo "$$1[]_PKG_ERRORS" >&AS_MESSAGE_LOG_FD echo "$$1[]_PKG_ERRORS" >&AS_MESSAGE_LOG_FD
m4_default([$4], [AC_MSG_ERROR( ifelse([$4], , [AC_MSG_ERROR(dnl
[Package requirements ($2) were not met: [Package requirements ($2) were not met:
$$1_PKG_ERRORS $$1_PKG_ERRORS
@@ -137,78 +134,24 @@ $$1_PKG_ERRORS
Consider adjusting the PKG_CONFIG_PATH environment variable if you Consider adjusting the PKG_CONFIG_PATH environment variable if you
installed software in a non-standard prefix. installed software in a non-standard prefix.
_PKG_TEXT])[]dnl _PKG_TEXT
]) ])],
[AC_MSG_RESULT([no])
$4])
elif test $pkg_failed = untried; then elif test $pkg_failed = untried; then
AC_MSG_RESULT([no]) ifelse([$4], , [AC_MSG_FAILURE(dnl
m4_default([$4], [AC_MSG_FAILURE(
[The pkg-config script could not be found or is too old. Make sure it [The pkg-config script could not be found or is too old. Make sure it
is in your PATH or set the PKG_CONFIG environment variable to the full is in your PATH or set the PKG_CONFIG environment variable to the full
path to pkg-config. path to pkg-config.
_PKG_TEXT _PKG_TEXT
To get pkg-config, see <http://pkg-config.freedesktop.org/>.])[]dnl To get pkg-config, see <http://www.freedesktop.org/software/pkgconfig>.])],
]) [$4])
else else
$1[]_CFLAGS=$pkg_cv_[]$1[]_CFLAGS $1[]_CFLAGS=$pkg_cv_[]$1[]_CFLAGS
$1[]_LIBS=$pkg_cv_[]$1[]_LIBS $1[]_LIBS=$pkg_cv_[]$1[]_LIBS
AC_MSG_RESULT([yes]) AC_MSG_RESULT([yes])
$3 ifelse([$3], , :, [$3])
fi[]dnl fi[]dnl
])# PKG_CHECK_MODULES ])# PKG_CHECK_MODULES
# PKG_INSTALLDIR(DIRECTORY)
# -------------------------
# Substitutes the variable pkgconfigdir as the location where a module
# should install pkg-config .pc files. By default the directory is
# $libdir/pkgconfig, but the default can be changed by passing
# DIRECTORY. The user can override through the --with-pkgconfigdir
# parameter.
AC_DEFUN([PKG_INSTALLDIR],
[m4_pushdef([pkg_default], [m4_default([$1], ['${libdir}/pkgconfig'])])
m4_pushdef([pkg_description],
[pkg-config installation directory @<:@]pkg_default[@:>@])
AC_ARG_WITH([pkgconfigdir],
[AS_HELP_STRING([--with-pkgconfigdir], pkg_description)],,
[with_pkgconfigdir=]pkg_default)
AC_SUBST([pkgconfigdir], [$with_pkgconfigdir])
m4_popdef([pkg_default])
m4_popdef([pkg_description])
]) dnl PKG_INSTALLDIR
# PKG_NOARCH_INSTALLDIR(DIRECTORY)
# -------------------------
# Substitutes the variable noarch_pkgconfigdir as the location where a
# module should install arch-independent pkg-config .pc files. By
# default the directory is $datadir/pkgconfig, but the default can be
# changed by passing DIRECTORY. The user can override through the
# --with-noarch-pkgconfigdir parameter.
AC_DEFUN([PKG_NOARCH_INSTALLDIR],
[m4_pushdef([pkg_default], [m4_default([$1], ['${datadir}/pkgconfig'])])
m4_pushdef([pkg_description],
[pkg-config arch-independent installation directory @<:@]pkg_default[@:>@])
AC_ARG_WITH([noarch-pkgconfigdir],
[AS_HELP_STRING([--with-noarch-pkgconfigdir], pkg_description)],,
[with_noarch_pkgconfigdir=]pkg_default)
AC_SUBST([noarch_pkgconfigdir], [$with_noarch_pkgconfigdir])
m4_popdef([pkg_default])
m4_popdef([pkg_description])
]) dnl PKG_NOARCH_INSTALLDIR
# PKG_CHECK_VAR(VARIABLE, MODULE, CONFIG-VARIABLE,
# [ACTION-IF-FOUND], [ACTION-IF-NOT-FOUND])
# -------------------------------------------
# Retrieves the value of the pkg-config variable for the given module.
AC_DEFUN([PKG_CHECK_VAR],
[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl
AC_ARG_VAR([$1], [value of $3 for $2, overriding pkg-config])dnl
_PKG_CONFIG([$1], [variable="][$3]["], [$2])
AS_VAR_COPY([$1], [pkg_cv_][$1])
AS_VAR_IF([$1], [""], [$5], [$4])dnl
])# PKG_CHECK_VAR

View File

@@ -1,4 +1,5 @@
# Check if "struct ucred" is available. # Check if "struct ucred" is available. If not, try harder with
# _GNU_SOURCE.
# #
# Author: Max Kellermann <max@duempel.org> # Author: Max Kellermann <max@duempel.org>
@@ -9,6 +10,19 @@ AC_DEFUN([STRUCT_UCRED],[
[struct ucred cred;], [struct ucred cred;],
mpd_cv_have_struct_ucred=yes, mpd_cv_have_struct_ucred=yes,
mpd_cv_have_struct_ucred=no) mpd_cv_have_struct_ucred=no)
if test x$mpd_cv_have_struct_ucred = xno; then
# glibc 2.8 forces _GNU_SOURCE on us
AC_TRY_COMPILE(
[#define _GNU_SOURCE
#include <sys/socket.h>],
[struct ucred cred;],
mpd_cv_have_struct_ucred=yes,
mpd_cv_have_struct_ucred=no)
if test x$mpd_cv_have_struct_ucred = xyes; then
# :(
CFLAGS="$CFLAGS -D_GNU_SOURCE"
fi
fi
]) ])
AC_MSG_RESULT($mpd_cv_have_struct_ucred) AC_MSG_RESULT($mpd_cv_have_struct_ucred)

9
mpd.service.in Normal file
View File

@@ -0,0 +1,9 @@
[Unit]
Description=Music Player Daemon
After=network.target sound.target
[Service]
ExecStart=@prefix@/bin/mpd --no-daemon
[Install]
WantedBy=multi-user.target

857
mpd.svg
View File

@@ -1,857 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Sodipodi ("http://www.sodipodi.com/") -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
version="1.0"
x="0"
y="0"
width="128"
height="128"
id="svg1"
sodipodi:version="0.32"
sodipodi:docname="mpd.svg"
inkscape:version="0.47pre4 r22446"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-test5.png"
inkscape:export-xdpi="76.799988"
inkscape:export-ydpi="76.799988">
<sodipodi:namedview
id="base"
inkscape:zoom="2.6884788"
inkscape:cx="71.610485"
inkscape:cy="61.484977"
inkscape:window-width="1680"
inkscape:window-height="994"
inkscape:window-x="0"
inkscape:window-y="0"
showguides="true"
inkscape:guide-bbox="true"
showgrid="false"
inkscape:window-maximized="1"
inkscape:current-layer="svg1" />
<defs
id="defs3">
<inkscape:perspective
sodipodi:type="inkscape:persp3d"
inkscape:vp_x="0 : 80 : 1"
inkscape:vp_y="0 : 1000 : 0"
inkscape:vp_z="160 : 80 : 1"
inkscape:persp3d-origin="80 : 53.333333 : 1"
id="perspective118" />
<linearGradient
id="linearGradient919">
<stop
style="stop-color:#000000;stop-opacity:0.86092716;"
offset="0.0000000"
id="stop920" />
<stop
style="stop-color:#ffffff;stop-opacity:0.0000000;"
offset="1.0000000"
id="stop921" />
</linearGradient>
<linearGradient
id="linearGradient1068">
<stop
offset="0.0000000"
style="stop-color:#d2d2d2;stop-opacity:1.0000000;"
id="stop1070" />
<stop
offset="1.0000000"
style="stop-color:#ffffff;stop-opacity:1.0000000;"
id="stop1069" />
</linearGradient>
<linearGradient
id="linearGradient1065">
<stop
offset="0.0000000"
style="stop-color:#ffffff;stop-opacity:1.0000000;"
id="stop1067" />
<stop
offset="1.0000000"
style="stop-color:#c2bfbf;stop-opacity:0.99607843;"
id="stop1066" />
</linearGradient>
<linearGradient
id="linearGradient1060">
<stop
offset="0.0000000"
style="stop-color:#878787;stop-opacity:1.0000000;"
id="stop1063" />
<stop
offset="1.0000000"
style="stop-color:#000000;stop-opacity:0.99607843;"
id="stop1061" />
</linearGradient>
<linearGradient
id="linearGradient645">
<stop
style="stop-color:#aca597;stop-opacity:1.0000000;"
offset="0.0000000"
id="stop646" />
<stop
style="stop-color:#ffffff;stop-opacity:1.0000000;"
offset="1.0000000"
id="stop647" />
</linearGradient>
<linearGradient
id="linearGradient593">
<stop
style="stop-color:#478acf;stop-opacity:1.0000000;"
offset="0.0000000"
id="stop594" />
<stop
style="stop-color:#65c6f7;stop-opacity:1.0000000;"
offset="1.0000000"
id="stop595" />
</linearGradient>
<linearGradient
id="linearGradient574">
<stop
style="stop-color:#85ad92;stop-opacity:1.0000;"
offset="0"
id="stop575" />
<stop
style="stop-color:#559db2;stop-opacity:0.7725;"
offset="1"
id="stop576" />
</linearGradient>
<linearGradient
id="linearGradient570">
<stop
style="stop-color:#999999;stop-opacity:0.7176;"
offset="0"
id="stop571" />
<stop
style="stop-color:#ffffff;stop-opacity:0.3725;"
offset="1"
id="stop572" />
</linearGradient>
<linearGradient
id="linearGradient573"
xlink:href="#linearGradient1068"
x1="40.458553"
y1="389.65582"
x2="36.063946"
y2="357.28375"
gradientTransform="matrix(2.3025192,0,0,0.29683004,-0.91913426,-1.5117091)"
gradientUnits="userSpaceOnUse" />
<linearGradient
id="linearGradient1213"
xlink:href="#linearGradient1068"
x1="123.71407"
y1="141.41566"
x2="98.353867"
y2="113.41083"
gradientTransform="matrix(0.91680324,0,0,0.74547827,-0.91913426,-1.5117091)"
gradientUnits="userSpaceOnUse" />
<radialGradient
id="radialGradient581"
xlink:href="#linearGradient919"
cx="0.095785439"
cy="0.16814159"
r="1.5409589"
fx="0.095785439"
fy="0.16814159" />
<linearGradient
id="linearGradient580"
xlink:href="#linearGradient1068"
x1="132.0352"
y1="135.68469"
x2="119.62381"
y2="111.07157"
gradientTransform="matrix(0.90170536,0,0,0.75796032,-0.91913426,-1.5117091)"
gradientUnits="userSpaceOnUse" />
<linearGradient
xlink:href="#linearGradient1060"
id="linearGradient901"
x1="0.93491787"
y1="0.92044502"
x2="-0.052546836"
y2="0.20347559" />
<linearGradient
xlink:href="#linearGradient593"
id="linearGradient902" />
<linearGradient
xlink:href="#linearGradient1068"
id="linearGradient916"
x1="0.14831461"
y1="-1.6875"
x2="0.43370786"
y2="1.8125" />
<defs
id="defs890">
<linearGradient
id="linearGradient922"
x1="0"
y1="0.5"
x2="1"
y2="0.5"
gradientUnits="objectBoundingBox"
spreadMethod="pad"
xlink:href="#linearGradient1065" />
<linearGradient
id="linearGradient908"
x1="0"
y1="0.5"
x2="1"
y2="0.5"
gradientUnits="objectBoundingBox"
spreadMethod="pad"
xlink:href="#linearGradient1060" />
<linearGradient
id="linearGradient894"
x1="0"
y1="0.5"
x2="1"
y2="0.5"
gradientUnits="objectBoundingBox"
spreadMethod="pad"
xlink:href="#linearGradient1068" />
<linearGradient
xlink:href="#linearGradient894"
id="linearGradient897"
x1="0.5955056"
y1="-0.33587787"
x2="0.61348313"
y2="1.1908396" />
<linearGradient
xlink:href="#linearGradient894"
id="linearGradient898"
x1="0.96449792"
y1="1.0278323"
x2="0.46738392"
y2="0.21800731" />
<linearGradient
xlink:href="#linearGradient908"
id="linearGradient907"
x1="0.57078654"
y1="2.3770492"
x2="0.33258426"
y2="0.49180329" />
<linearGradient
xlink:href="#linearGradient922"
id="linearGradient921"
x1="0.47058824"
y1="0.15384616"
x2="0.46547315"
y2="0.98380566" />
<linearGradient
xlink:href="#linearGradient922"
id="linearGradient948" />
<defs
id="defs987">
<linearGradient
id="linearGradient855"
x1="0"
y1="0.5"
x2="1"
y2="0.5"
gradientUnits="objectBoundingBox"
spreadMethod="pad"
xlink:href="#linearGradient908" />
<linearGradient
id="linearGradient1188"
x1="0"
y1="0.5"
x2="1"
y2="0.5"
gradientUnits="objectBoundingBox"
spreadMethod="pad"
xlink:href="#linearGradient922" />
<linearGradient
id="linearGradient831">
<stop
style="stop-color:#94897f;stop-opacity:1.0000000;"
offset="0.0000000"
id="stop832" />
<stop
style="stop-color:#fff5fe;stop-opacity:1.0000000;"
offset="1.0000000"
id="stop833" />
</linearGradient>
<linearGradient
xlink:href="#linearGradient1188"
id="linearGradient834"
x1="0.87550199"
y1="0.34817815"
x2="-0.29317269"
y2="0.93522269"
gradientUnits="objectBoundingBox"
spreadMethod="pad" />
<radialGradient
xlink:href="#linearGradient1188"
id="radialGradient835"
r="0.55628061"
fy="0.28125"
fx="0.59090906"
cy="0.28125"
cx="0.59090906"
spreadMethod="pad" />
<linearGradient
xlink:href="#linearGradient1188"
id="linearGradient893"
x1="0.12793733"
y1="0.76923078"
x2="0.49608356"
y2="0.70850199" />
<linearGradient
xlink:href="#linearGradient855"
id="linearGradient625"
x1="0.035955057"
y1="1.0276498"
x2="0.053932585"
y2="-0.359447" />
<linearGradient
xlink:href="#linearGradient1188"
id="linearGradient627"
x1="1.2826855"
y1="0.12550607"
x2="-0.15547703"
y2="0.96356273" />
<radialGradient
xlink:href="#linearGradient1188"
id="radialGradient628"
r="1.5982224"
fy="0.4866707"
fx="0.36789617"
cy="0.4866707"
cx="0.36789617"
gradientTransform="scale(0.877379,1.139758)" />
<linearGradient
xlink:href="#linearGradient1188"
id="linearGradient628"
x1="0.76923078"
y1="0.14979757"
x2="0.41909814"
y2="0.73279351" />
</defs>
<sodipodi:namedview
id="namedview898"
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="0.0"
inkscape:pageshadow="2"
inkscape:zoom="3.4732669"
inkscape:cx="50.051177"
inkscape:cy="18.096983"
inkscape:window-width="1022"
inkscape:window-height="670"
showguides="false"
snaptoguides="false"
showgrid="false"
snaptogrid="false"
inkscape:window-x="0"
inkscape:window-y="25">
<sodipodi:guide
orientation="vertical"
position="28.705556"
id="guide879" />
<sodipodi:guide
orientation="horizontal"
position="30.130655"
id="guide880" />
</sodipodi:namedview>
</defs>
<sodipodi:namedview
id="namedview1003"
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="0.0"
inkscape:pageshadow="2"
inkscape:zoom="1.3368738"
inkscape:cx="24.541029"
inkscape:cy="14.368596"
inkscape:window-width="640"
inkscape:window-height="499"
showguides="true"
snaptoguides="true"
inkscape:window-x="138"
inkscape:window-y="169" />
<linearGradient
xlink:href="#linearGradient1060"
id="linearGradient1304"
x1="-0.20218579"
y1="0.21681416"
x2="0.67759562"
y2="0.57522124" />
<linearGradient
xlink:href="#linearGradient1065"
id="linearGradient1322"
x1="0.32404181"
y1="0.77876109"
x2="0.24041812"
y2="0.26548672" />
<defs
id="defs989">
<linearGradient
id="linearGradient850">
<stop
style="stop-color:#eed680;stop-opacity:1.0000000;"
offset="0.0000000"
id="stop852" />
<stop
style="stop-color:#dfb546;stop-opacity:1.0000000;"
offset="0.68035328"
id="stop858" />
<stop
style="stop-color:#d8a429;stop-opacity:1.0000000;"
offset="0.77277374"
id="stop859" />
<stop
style="stop-color:#d1940c;stop-opacity:1.0000000;"
offset="1.0000000"
id="stop857" />
</linearGradient>
<linearGradient
xlink:href="#linearGradient850"
id="linearGradient569"
x1="0.11875"
y1="0.12612613"
x2="0.59375"
y2="0.66066068"
spreadMethod="pad" />
<linearGradient
id="linearGradient839">
<stop
style="stop-color:#46a046;stop-opacity:1.0000000;"
offset="0.0000000"
id="stop840" />
<stop
style="stop-color:#df421e;stop-opacity:1.0000000;"
offset="0.39364964"
id="stop841" />
<stop
style="stop-color:#ada7c8;stop-opacity:1.0000000;"
offset="0.72036445"
id="stop842" />
<stop
style="stop-color:#eed680;stop-opacity:1.0000000;"
offset="1.0000000"
id="stop843" />
</linearGradient>
<linearGradient
xlink:href="#linearGradient839"
id="linearGradient836"
x1="1.3267924e-17"
y1="0.5"
x2="1"
y2="0.5" />
<defs
id="defs604">
<linearGradient
id="linearGradient622">
<stop
style="stop-color:#f8e29d;stop-opacity:0.4471;"
offset="0"
id="stop623" />
<stop
style="stop-color:#272d2d;stop-opacity:0.4784;"
offset="1"
id="stop624" />
</linearGradient>
<linearGradient
id="linearGradient617">
<stop
style="stop-color:#ffffff;stop-opacity:1;"
offset="0"
id="stop618" />
<stop
style="stop-color:#000000;stop-opacity:1;"
offset="1"
id="stop619" />
</linearGradient>
<linearGradient
id="linearGradient613">
<stop
style="stop-color:#ffffff;stop-opacity:0.6235;"
offset="0"
id="stop614" />
<stop
style="stop-color:#5d6567;stop-opacity:1;"
offset="1"
id="stop615" />
</linearGradient>
<linearGradient
id="linearGradient607">
<stop
style="stop-color:#d7d5d5;stop-opacity:1;"
offset="0"
id="stop608" />
<stop
style="stop-color:#000000;stop-opacity:0.4039;"
offset="1"
id="stop609" />
</linearGradient>
<radialGradient
xlink:href="#linearGradient607"
id="radialGradient610"
cx="1.4287461"
cy="0.75323397"
r="0.85534656"
fx="1.4287461"
fy="0.75323397"
gradientTransform="matrix(1,2.268336e-6,-1.975559e-5,1,5.713033e-8,3.856326e-8)" />
<linearGradient
xlink:href="#linearGradient617"
id="linearGradient612"
x1="7.7024956"
y1="-2.0263922"
x2="62.759903"
y2="56.137772"
gradientTransform="scale(0.9953779,1.0046436)"
gradientUnits="userSpaceOnUse" />
<radialGradient
xlink:href="#linearGradient613"
id="radialGradient616"
cx="58.70882"
cy="53.831562"
r="43.551846"
fx="58.70882"
fy="53.831562"
gradientTransform="scale(0.99517298,1.0048504)"
gradientUnits="userSpaceOnUse" />
<linearGradient
xlink:href="#linearGradient617"
id="linearGradient621" />
<linearGradient
xlink:href="#linearGradient617"
id="linearGradient626"
x1="72.060211"
y1="55.161442"
x2="32.409"
y2="12.126946"
gradientTransform="matrix(0.995134,-1.068631e-5,-1.31398e-7,1.00489,0,0)"
gradientUnits="userSpaceOnUse" />
<linearGradient
xlink:href="#linearGradient607"
id="linearGradient687"
x1="67.707405"
y1="49.314793"
x2="-10.031048"
y2="4.6068792"
gradientTransform="scale(0.99522839,1.0047945)"
gradientUnits="userSpaceOnUse" />
<linearGradient
xlink:href="#linearGradient617"
id="linearGradient742"
x1="-7.4378386"
y1="25.923714"
x2="18.009745"
y2="10.089797"
gradientTransform="scale(0.889853,1.123781)" />
</defs>
<sodipodi:namedview
id="namedview889"
showguides="true"
snaptoguides="true"
inkscape:zoom="7.5625000"
inkscape:cx="24.000000"
inkscape:cy="24.000000"
inkscape:window-width="640"
inkscape:window-height="496"
inkscape:window-x="0"
inkscape:window-y="26" />
</defs>
<sodipodi:namedview
id="namedview1023"
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="0.0"
inkscape:pageshadow="2"
inkscape:zoom="3.5521067"
inkscape:cx="66.459318"
inkscape:cy="62.629296"
inkscape:window-width="1150"
inkscape:window-height="752"
showgrid="true"
snaptogrid="true"
inkscape:window-x="0"
inkscape:window-y="29">
<inkscape:grid
id="GridFromPre046Settings"
type="xygrid"
originx="0px"
originy="0px"
spacingx="1.0000000mm"
spacingy="1.0000000mm"
color="#0000ff"
empcolor="#0000ff"
opacity="0.2"
empopacity="0.4"
empspacing="5" />
</sodipodi:namedview>
<linearGradient
inkscape:collect="always"
xlink:href="#linearGradient1068"
id="linearGradient2924"
x1="41.673889"
y1="320.40921"
x2="36.082947"
y2="279.22458"
gradientTransform="matrix(2.3376099,0,0,0.29237422,-0.91913426,-1.5117091)"
gradientUnits="userSpaceOnUse" />
<linearGradient
inkscape:collect="always"
xlink:href="#linearGradient1068"
id="linearGradient2926"
x1="134.95444"
y1="108.16693"
x2="102.05431"
y2="71.835884"
gradientTransform="matrix(0.91680324,0,0,0.74547824,-0.91913426,-1.5117091)"
gradientUnits="userSpaceOnUse" />
<linearGradient
inkscape:collect="always"
xlink:href="#linearGradient1068"
id="linearGradient2928"
x1="145.32188"
y1="101.97199"
x2="129.22044"
y2="70.041069"
gradientTransform="matrix(0.90170536,0,0,0.75796032,-0.91913426,-1.5117091)"
gradientUnits="userSpaceOnUse" />
</defs>
<rect
style="fill-opacity:0.47154475;fill-rule:evenodd;stroke-width:3pt"
id="rect918"
width="48.72493"
height="42.16835"
ry="0.74231374"
x="67.536102"
y="66.474693"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="0.7811048" />
<rect
style="fill-opacity:0.47154475;fill-rule:evenodd;stroke-width:3pt"
id="rect1006"
width="63.211483"
height="54.705563"
ry="0.74231374"
x="64.47226"
y="30.558294"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="0.7811048" />
<rect
style="fill:#000000;fill-opacity:0.47058824;fill-rule:evenodd"
id="rect1005"
width="57.843418"
height="9.0050545"
ry="0.62889248"
x="65.398254"
y="82.153206"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="0.66175652" />
<rect
style="fill:url(#linearGradient2924);fill-opacity:0.75;fill-rule:evenodd;stroke:#000000;stroke-width:0.82671446"
id="rect1007"
width="54.910637"
height="6.1445785"
ry="0.42912331"
x="64.622299"
y="82.282539"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="0.44939452" />
<rect
width="57.905403"
height="47.084496"
ry="1.7822117"
x="63.784973"
y="32.456562"
style="font-size:12px;fill:url(#linearGradient2926);fill-rule:evenodd;stroke:#000000;stroke-width:0"
id="rect1009"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="1.6336281" />
<rect
style="fill:#000000;fill-opacity:0.47058824;fill-rule:evenodd"
id="rect971"
width="44.58709"
height="6.9413123"
ry="0.62889248"
x="68.249886"
y="106.24529"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="0.66175652" />
<rect
width="64.637024"
height="54.068516"
ry="1.4120796"
x="59.853096"
y="28.740753"
style="font-size:12px;fill:url(#linearGradient2928);fill-rule:evenodd;stroke:#000000;stroke-width:1.65869105"
id="rect1008"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="1.3970968" />
<rect
width="51.129478"
height="39.964478"
ry="0.5422883"
x="66.358932"
y="34.89621"
style="font-size:12px;fill:#00b4ed;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.79054338;stroke-linejoin:round"
id="rect976"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="0.5422883" />
<metadata
id="metadata982">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
</cc:Work>
</rdf:RDF>
</metadata>
<rect
width="44.634872"
height="36.293858"
ry="1.7822117"
x="67.006332"
y="67.937927"
style="font-size:12px;fill:url(#linearGradient1213);fill-rule:evenodd;stroke:#000000;stroke-width:0"
id="rect575"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="1.633628" />
<path
sodipodi:type="arc"
style="font-size:12px;fill:#444040;fill-opacity:0.47058824;fill-rule:evenodd"
id="path672"
d="m 68.473,57.85183 a 23.629898,3.2222576 0 1 1 -47.259797,0 23.629898,3.2222576 0 1 1 47.259797,0 z"
sodipodi:cx="44.843102"
sodipodi:cy="57.85183"
sodipodi:rx="23.629898"
sodipodi:ry="3.2222576"
transform="matrix(1.4221482,0,-0.30247168,1.9834766,9.6201687,-10.428817)"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big2.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998" />
<path
sodipodi:type="arc"
style="font-size:12px;fill:#4e4d4b;fill-rule:evenodd;stroke:#000000;stroke-width:2.30019999;stroke-opacity:0.9565"
id="path625"
d="m 58.291138,27.531645 a 19.367088,19.556963 0 1 1 -38.734177,0 19.367088,19.556963 0 1 1 38.734177,0 z"
sodipodi:cx="38.924049"
sodipodi:cy="27.531645"
sodipodi:rx="19.367088"
sodipodi:ry="19.556963"
transform="matrix(-1.0172416,-0.47376693,-0.5523759,1.3286212,116.84611,57.272851)"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big2.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998" />
<path
sodipodi:type="arc"
style="font-size:12px;fill:url(#linearGradient612);fill-rule:evenodd;stroke:#000000;stroke-width:2.06100011;stroke-opacity:0.9565"
id="path605"
d="m 58.291138,27.531645 a 19.367088,19.556963 0 1 1 -38.734177,0 19.367088,19.556963 0 1 1 38.734177,0 z"
sodipodi:cx="38.924049"
sodipodi:cy="27.531645"
sodipodi:rx="19.367088"
sodipodi:ry="19.556963"
transform="matrix(-1.4321234,-0.79696518,-1.1299666,2.2349846,128.07685,29.383033)"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big2.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998" />
<path
sodipodi:type="arc"
style="font-size:12px;fill:url(#radialGradient616);fill-rule:evenodd;stroke:#000000;stroke-width:0.317;stroke-opacity:0.97829997"
id="path606"
d="m 58.291138,27.531645 a 19.367088,19.556963 0 1 1 -38.734177,0 19.367088,19.556963 0 1 1 38.734177,0 z"
sodipodi:cx="38.924049"
sodipodi:cy="27.531645"
sodipodi:rx="19.367088"
sodipodi:ry="19.556963"
transform="matrix(-1.1546358,-0.69851175,-0.95634664,1.9588777,108.06887,31.115628)"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big2.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998" />
<path
sodipodi:type="arc"
style="font-size:12px;fill-rule:evenodd;stroke-width:1.63499999"
id="path686"
d="m 58.291138,27.531645 a 19.367088,19.556963 0 1 1 -38.734177,0 19.367088,19.556963 0 1 1 38.734177,0 z"
sodipodi:cx="38.924049"
sodipodi:cy="27.531645"
sodipodi:rx="19.367088"
sodipodi:ry="19.556963"
transform="matrix(-0.39495459,-0.4546194,-0.52881207,0.94219495,73.198184,52.427791)"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big2.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998" />
<path
sodipodi:type="arc"
style="font-size:12px;fill:url(#linearGradient687);fill-rule:evenodd;stroke:#3f3b3b;stroke-width:0.77380002"
id="path611"
d="m 58.291138,27.531645 a 19.367088,19.556963 0 1 1 -38.734177,0 19.367088,19.556963 0 1 1 38.734177,0 z"
sodipodi:cx="38.924049"
sodipodi:cy="27.531645"
sodipodi:rx="19.367088"
sodipodi:ry="19.556963"
transform="matrix(-0.36949013,-0.40957751,-0.49471918,0.84885391,70.248021,52.066881)"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big2.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998" />
<rect
style="fill:url(#linearGradient573);fill-opacity:0.75;fill-rule:evenodd;stroke:#000000;stroke-width:0.82671446"
id="rect934"
width="42.326431"
height="4.7363882"
ry="0.42912331"
x="67.651756"
y="106.34497"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="0.44939449" />
<rect
width="49.823761"
height="41.677303"
ry="1.4120796"
x="63.975548"
y="65.073692"
style="font-size:12px;fill:url(#linearGradient580);fill-rule:evenodd;stroke:#000000;stroke-width:1.27855873;stroke-opacity:1"
id="rect562"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="1.3970969" />
<rect
width="39.411831"
height="30.805574"
ry="0.5422883"
x="68.990387"
y="70.097008"
style="font-size:12px;fill:#003d88;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.61407685;stroke-linejoin:round;stroke-miterlimit:4;stroke-opacity:0.93023257"
id="rect975"
inkscape:export-filename="/cowserver/documents/httpd/vhosts/images/mpd-big7.png"
inkscape:export-xdpi="721.66998"
inkscape:export-ydpi="721.66998"
rx="0.5422883" />
</svg>

Before

Width:  |  Height:  |  Size: 27 KiB

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -23,15 +23,12 @@
class Mutex; class Mutex;
class Cond; class Cond;
class Error; class Error;
struct ArchivePlugin;
class ArchiveVisitor;
class InputStream;
class ArchiveFile { class ArchiveFile {
public: public:
const ArchivePlugin &plugin; const struct archive_plugin &plugin;
ArchiveFile(const ArchivePlugin &_plugin) ArchiveFile(const struct archive_plugin &_plugin)
:plugin(_plugin) {} :plugin(_plugin) {}
protected: protected:

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -21,14 +21,14 @@
#include "ArchiveList.hxx" #include "ArchiveList.hxx"
#include "ArchivePlugin.hxx" #include "ArchivePlugin.hxx"
#include "util/StringUtil.hxx" #include "util/StringUtil.hxx"
#include "plugins/Bzip2ArchivePlugin.hxx" #include "archive/Bzip2ArchivePlugin.hxx"
#include "plugins/Iso9660ArchivePlugin.hxx" #include "archive/Iso9660ArchivePlugin.hxx"
#include "plugins/ZzipArchivePlugin.hxx" #include "archive/ZzipArchivePlugin.hxx"
#include "util/Macros.hxx" #include "util/Macros.hxx"
#include <string.h> #include <string.h>
const ArchivePlugin *const archive_plugins[] = { const struct archive_plugin *const archive_plugins[] = {
#ifdef HAVE_BZ2 #ifdef HAVE_BZ2
&bz2_archive_plugin, &bz2_archive_plugin,
#endif #endif
@@ -48,7 +48,7 @@ static bool archive_plugins_enabled[ARRAY_SIZE(archive_plugins) - 1];
archive_plugins_for_each(plugin) \ archive_plugins_for_each(plugin) \
if (archive_plugins_enabled[archive_plugin_iterator - archive_plugins]) if (archive_plugins_enabled[archive_plugin_iterator - archive_plugins])
const ArchivePlugin * const struct archive_plugin *
archive_plugin_from_suffix(const char *suffix) archive_plugin_from_suffix(const char *suffix)
{ {
if (suffix == nullptr) if (suffix == nullptr)
@@ -62,7 +62,7 @@ archive_plugin_from_suffix(const char *suffix)
return nullptr; return nullptr;
} }
const ArchivePlugin * const struct archive_plugin *
archive_plugin_from_name(const char *name) archive_plugin_from_name(const char *name)
{ {
archive_plugins_for_each_enabled(plugin) archive_plugins_for_each_enabled(plugin)
@@ -75,7 +75,7 @@ archive_plugin_from_name(const char *name)
void archive_plugin_init_all(void) void archive_plugin_init_all(void)
{ {
for (unsigned i = 0; archive_plugins[i] != nullptr; ++i) { for (unsigned i = 0; archive_plugins[i] != nullptr; ++i) {
const ArchivePlugin *plugin = archive_plugins[i]; const struct archive_plugin *plugin = archive_plugins[i];
if (plugin->init == nullptr || archive_plugins[i]->init()) if (plugin->init == nullptr || archive_plugins[i]->init())
archive_plugins_enabled[i] = true; archive_plugins_enabled[i] = true;
} }

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -20,22 +20,22 @@
#ifndef MPD_ARCHIVE_LIST_HXX #ifndef MPD_ARCHIVE_LIST_HXX
#define MPD_ARCHIVE_LIST_HXX #define MPD_ARCHIVE_LIST_HXX
struct ArchivePlugin; struct archive_plugin;
extern const ArchivePlugin *const archive_plugins[]; extern const struct archive_plugin *const archive_plugins[];
#define archive_plugins_for_each(plugin) \ #define archive_plugins_for_each(plugin) \
for (const ArchivePlugin *plugin, \ for (const struct archive_plugin *plugin, \
*const*archive_plugin_iterator = &archive_plugins[0]; \ *const*archive_plugin_iterator = &archive_plugins[0]; \
(plugin = *archive_plugin_iterator) != nullptr; \ (plugin = *archive_plugin_iterator) != nullptr; \
++archive_plugin_iterator) ++archive_plugin_iterator)
/* interface for using plugins */ /* interface for using plugins */
const ArchivePlugin * const struct archive_plugin *
archive_plugin_from_suffix(const char *suffix); archive_plugin_from_suffix(const char *suffix);
const ArchivePlugin * const struct archive_plugin *
archive_plugin_from_name(const char *name); archive_plugin_from_name(const char *name);
/* this is where we "load" all the "plugins" ;-) */ /* this is where we "load" all the "plugins" ;-) */

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -24,6 +24,7 @@
#include <string.h> #include <string.h>
#include <sys/stat.h> #include <sys/stat.h>
#include <unistd.h>
#include <errno.h> #include <errno.h>
gcc_pure gcc_pure

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -20,18 +20,17 @@
#include "config.h" #include "config.h"
#include "ArchivePlugin.hxx" #include "ArchivePlugin.hxx"
#include "ArchiveFile.hxx" #include "ArchiveFile.hxx"
#include "fs/Path.hxx"
#include "util/Error.hxx" #include "util/Error.hxx"
#include <assert.h> #include <assert.h>
ArchiveFile * ArchiveFile *
archive_file_open(const ArchivePlugin *plugin, Path path, archive_file_open(const struct archive_plugin *plugin, const char *path,
Error &error) Error &error)
{ {
assert(plugin != nullptr); assert(plugin != nullptr);
assert(plugin->open != nullptr); assert(plugin->open != nullptr);
assert(!path.IsNull()); assert(path != nullptr);
ArchiveFile *file = plugin->open(path, error); ArchiveFile *file = plugin->open(path, error);
assert((file == nullptr) == error.IsDefined()); assert((file == nullptr) == error.IsDefined());

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -20,11 +20,12 @@
#ifndef MPD_ARCHIVE_PLUGIN_HXX #ifndef MPD_ARCHIVE_PLUGIN_HXX
#define MPD_ARCHIVE_PLUGIN_HXX #define MPD_ARCHIVE_PLUGIN_HXX
struct InputStream;
class ArchiveFile; class ArchiveFile;
class Path; class ArchiveVisitor;
class Error; class Error;
struct ArchivePlugin { struct archive_plugin {
const char *name; const char *name;
/** /**
@@ -45,7 +46,7 @@ struct ArchivePlugin {
* returns pointer to handle used is all operations with this archive * returns pointer to handle used is all operations with this archive
* or nullptr when opening fails * or nullptr when opening fails
*/ */
ArchiveFile *(*open)(Path path_fs, Error &error); ArchiveFile *(*open)(const char *path_fs, Error &error);
/** /**
* suffixes handled by this plugin. * suffixes handled by this plugin.
@@ -55,7 +56,7 @@ struct ArchivePlugin {
}; };
ArchiveFile * ArchiveFile *
archive_file_open(const ArchivePlugin *plugin, Path path, archive_file_open(const struct archive_plugin *plugin, const char *path,
Error &error); Error &error);
#endif #endif

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -21,9 +21,9 @@
#include "AudioConfig.hxx" #include "AudioConfig.hxx"
#include "AudioFormat.hxx" #include "AudioFormat.hxx"
#include "AudioParser.hxx" #include "AudioParser.hxx"
#include "config/ConfigData.hxx" #include "ConfigData.hxx"
#include "config/ConfigGlobal.hxx" #include "ConfigGlobal.hxx"
#include "config/ConfigOption.hxx" #include "ConfigOption.hxx"
#include "util/Error.hxx" #include "util/Error.hxx"
#include "system/FatalError.hxx" #include "system/FatalError.hxx"

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -19,6 +19,7 @@
#include "config.h" #include "config.h"
#include "AvahiPoll.hxx" #include "AvahiPoll.hxx"
#include "event/Loop.hxx"
#include "event/SocketMonitor.hxx" #include "event/SocketMonitor.hxx"
#include "event/TimeoutMonitor.hxx" #include "event/TimeoutMonitor.hxx"
@@ -57,6 +58,10 @@ public:
Schedule(FromAvahiWatchEvent(_event)); Schedule(FromAvahiWatchEvent(_event));
} }
~AvahiWatch() {
Steal();
}
static void WatchUpdate(AvahiWatch *w, AvahiWatchEvent event) { static void WatchUpdate(AvahiWatch *w, AvahiWatchEvent event) {
w->Schedule(FromAvahiWatchEvent(event)); w->Schedule(FromAvahiWatchEvent(event));
} }

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,226 +0,0 @@
/*
* Copyright (C) 2003-2014 The Music Player Daemon Project
* http://www.musicpd.org
*
* 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.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#ifndef MPD_CHRONO_HXX
#define MPD_CHRONO_HXX
#include "Compiler.h"
#include <chrono>
#include <utility>
#include <cstdint>
#if defined(__GNUC__) && !GCC_CHECK_VERSION(4,7) && !defined(__clang__)
/* std::chrono::duration operators are "constexpr" since gcc 4.7 */
#define chrono_constexpr gcc_pure
#else
#define chrono_constexpr constexpr
#endif
/**
* A time stamp within a song. Granularity is 1 millisecond and the
* maximum value is about 49 days.
*/
class SongTime : public std::chrono::duration<std::uint32_t, std::milli> {
typedef std::chrono::duration<std::uint32_t, std::milli> Base;
typedef Base::rep rep;
public:
SongTime() = default;
template<typename T>
explicit constexpr SongTime(T t):Base(t) {}
static constexpr SongTime zero() {
return SongTime(Base::zero());
}
static constexpr SongTime FromS(unsigned s) {
return SongTime(rep(s) * 1000);
}
static constexpr SongTime FromS(float s) {
return SongTime(rep(s * 1000));
}
static constexpr SongTime FromS(double s) {
return SongTime(rep(s * 1000));
}
static constexpr SongTime FromMS(rep ms) {
return SongTime(ms);
}
constexpr rep ToS() const {
return count() / rep(1000);
}
constexpr rep RoundS() const {
return (count() + 500) / rep(1000);
}
constexpr rep ToMS() const {
return count();
}
template<typename T=rep>
constexpr T ToScale(unsigned scale) const {
return count() * T(scale) / 1000;
}
/**
* Convert a scalar value with the given scale to a #SongTime
* instance.
*
* @param value the input value
* @param scale the value's scale in Hz
*/
template<typename T=rep>
static constexpr SongTime FromScale(T value, unsigned scale) {
return SongTime(value * T(1000) / T(scale));
}
constexpr double ToDoubleS() const {
return double(count()) / 1000.;
};
constexpr bool IsZero() const {
return count() == 0;
}
constexpr bool IsPositive() const {
return count() > 0;
}
chrono_constexpr SongTime operator+(const SongTime &other) const {
return SongTime(*(const Base *)this + (const Base &)other);
}
chrono_constexpr SongTime operator-(const SongTime &other) const {
return SongTime(*(const Base *)this - (const Base &)other);
}
};
/**
* A variant of #SongTime that is based on a signed integer. It can
* be used for relative values.
*/
class SignedSongTime : public std::chrono::duration<std::int32_t, std::milli> {
typedef std::chrono::duration<std::int32_t, std::milli> Base;
typedef Base::rep rep;
public:
SignedSongTime() = default;
template<typename T>
explicit constexpr SignedSongTime(T t):Base(t) {}
/**
* Allow implicit conversion from SongTime to SignedSongTime.
*/
constexpr SignedSongTime(SongTime t):Base(t) {}
static constexpr SignedSongTime zero() {
return SignedSongTime(Base::zero());
}
/**
* Generate a negative value.
*/
static constexpr SignedSongTime Negative() {
return SignedSongTime(-1);
}
static constexpr SignedSongTime FromS(int s) {
return SignedSongTime(rep(s) * 1000);
}
static constexpr SignedSongTime FromS(unsigned s) {
return SignedSongTime(rep(s) * 1000);
}
static constexpr SignedSongTime FromS(float s) {
return SignedSongTime(rep(s * 1000));
}
static constexpr SignedSongTime FromS(double s) {
return SignedSongTime(rep(s * 1000));
}
static constexpr SignedSongTime FromMS(rep ms) {
return SignedSongTime(ms);
}
constexpr rep ToS() const {
return count() / rep(1000);
}
constexpr rep RoundS() const {
return (count() + 500) / rep(1000);
}
constexpr rep ToMS() const {
return count();
}
template<typename T=rep>
constexpr T ToScale(unsigned scale) const {
return count() * T(scale) / 1000;
}
/**
* Convert a scalar value with the given scale to a
* #SignedSongTime instance.
*
* @param value the input value
* @param scale the value's scale in Hz
*/
template<typename T=rep>
static constexpr SignedSongTime FromScale(T value, unsigned scale) {
return SignedSongTime(value * T(1000) / T(scale));
}
constexpr double ToDoubleS() const {
return double(count()) / 1000.;
};
constexpr bool IsZero() const {
return count() == 0;
}
constexpr bool IsPositive() const {
return count() > 0;
}
constexpr bool IsNegative() const {
return count() < 0;
}
chrono_constexpr SignedSongTime operator+(const SignedSongTime &other) const {
return SignedSongTime(*(const Base *)this + (const Base &)other);
}
chrono_constexpr SignedSongTime operator-(const SignedSongTime &other) const {
return SignedSongTime(*(const Base *)this - (const Base &)other);
}
};
#undef chrono_constexpr
#endif

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -18,7 +18,7 @@
*/ */
#include "config.h" #include "config.h"
#include "Domain.hxx" #include "ClientInternal.hxx"
#include "util/Domain.hxx" #include "util/Domain.hxx"
const Domain smbclient_domain("smbclient"); const Domain client_domain("client");

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -27,8 +27,6 @@
#include "event/TimeoutMonitor.hxx" #include "event/TimeoutMonitor.hxx"
#include "Compiler.h" #include "Compiler.h"
#include <boost/intrusive/list.hpp>
#include <set> #include <set>
#include <string> #include <string>
#include <list> #include <list>
@@ -38,25 +36,14 @@
struct sockaddr; struct sockaddr;
class EventLoop; class EventLoop;
class Path;
struct Partition; struct Partition;
class Database;
class Storage;
class Client final class Client final : private FullyBufferedSocket, TimeoutMonitor {
: FullyBufferedSocket, TimeoutMonitor,
public boost::intrusive::list_base_hook<boost::intrusive::link_mode<boost::intrusive::normal_link>> {
public: public:
Partition &partition; Partition &partition;
struct playlist &playlist; struct playlist &playlist;
struct PlayerControl &player_control; struct PlayerControl &player_control;
struct Disposer {
void operator()(Client *client) const {
delete client;
}
};
unsigned permission; unsigned permission;
/** the uid of the client process, or -1 if unknown */ /** the uid of the client process, or -1 if unknown */
@@ -95,11 +82,6 @@ public:
Client(EventLoop &loop, Partition &partition, Client(EventLoop &loop, Partition &partition,
int fd, int uid, int num); int fd, int uid, int num);
~Client() {
if (FullyBufferedSocket::IsDefined())
FullyBufferedSocket::Close();
}
bool IsConnected() const { bool IsConnected() const {
return FullyBufferedSocket::IsDefined(); return FullyBufferedSocket::IsDefined();
} }
@@ -127,7 +109,7 @@ public:
* a local (UNIX domain) socket? * a local (UNIX domain) socket?
*/ */
bool IsLocal() const { bool IsLocal() const {
return uid > 0; return uid >= 0;
} }
unsigned GetPermission() const { unsigned GetPermission() const {
@@ -169,27 +151,6 @@ public:
void UnsubscribeAll(); void UnsubscribeAll();
bool PushMessage(const ClientMessage &msg); bool PushMessage(const ClientMessage &msg);
/**
* Is this client allowed to use the specified local file?
*
* Note that this function is vulnerable to timing/symlink attacks.
* We cannot fix this as long as there are plugins that open a file by
* its name, and not by file descriptor / callbacks.
*
* @param path_fs the absolute path name in filesystem encoding
* @return true if access is allowed
*/
bool AllowFile(Path path_fs, Error &error) const;
/**
* Wrapper for Instance::GetDatabase().
*/
gcc_pure
const Database *GetDatabase(Error &error) const;
gcc_pure
const Storage *GetStorage() const;
private: private:
/* virtual methods from class BufferedSocket */ /* virtual methods from class BufferedSocket */
virtual InputResult OnSocketInput(void *data, size_t length) override; virtual InputResult OnSocketInput(void *data, size_t length) override;
@@ -204,7 +165,7 @@ void client_manager_init(void);
void void
client_new(EventLoop &loop, Partition &partition, client_new(EventLoop &loop, Partition &partition,
int fd, const sockaddr *sa, size_t sa_length, int uid); int fd, const struct sockaddr *sa, size_t sa_length, int uid);
/** /**
* Write a C string to the client. * Write a C string to the client.

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -18,30 +18,36 @@
*/ */
#include "config.h" #include "config.h"
#include "ClientFile.hxx"
#include "Client.hxx" #include "Client.hxx"
#include "protocol/Ack.hxx" #include "protocol/Ack.hxx"
#include "fs/Path.hxx" #include "fs/Path.hxx"
#include "fs/FileSystem.hxx" #include "fs/FileSystem.hxx"
#include "util/Error.hxx" #include "util/Error.hxx"
#include "util/Domain.hxx"
#include <sys/stat.h> #include <sys/stat.h>
#include <sys/types.h>
#include <errno.h>
#include <unistd.h> #include <unistd.h>
bool bool
Client::AllowFile(Path path_fs, Error &error) const client_allow_file(const Client &client, Path path_fs, Error &error)
{ {
#ifdef WIN32 #ifdef WIN32
(void)client;
(void)path_fs; (void)path_fs;
error.Set(ack_domain, ACK_ERROR_PERMISSION, "Access denied"); error.Set(ack_domain, ACK_ERROR_PERMISSION, "Access denied");
return false; return false;
#else #else
const int uid = client.GetUID();
if (uid >= 0 && (uid_t)uid == geteuid()) if (uid >= 0 && (uid_t)uid == geteuid())
/* always allow access if user runs his own MPD /* always allow access if user runs his own MPD
instance */ instance */
return true; return true;
if (uid <= 0) { if (uid < 0) {
/* unauthenticated client */ /* unauthenticated client */
error.Set(ack_domain, ACK_ERROR_PERMISSION, "Access denied"); error.Set(ack_domain, ACK_ERROR_PERMISSION, "Access denied");
return false; return false;

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -17,22 +17,24 @@
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/ */
#ifndef MPD_INPUT_LOCAL_OPEN_HXX #ifndef MPD_CLIENT_FILE_HXX
#define MPD_INPUT_LOCAL_OPEN_HXX #define MPD_CLIENT_FILE_HXX
#include "check.h" class Client;
class InputStream;
class Path; class Path;
class Mutex;
class Cond;
class Error; class Error;
/** /**
* Open a "local" file. This is a wrapper for the input plugins * Is this client allowed to use the specified local file?
* "file" and "archive". *
* Note that this function is vulnerable to timing/symlink attacks.
* We cannot fix this as long as there are plugins that open a file by
* its name, and not by file descriptor / callbacks.
*
* @param path_fs the absolute path name in filesystem encoding
* @return true if access is allowed
*/ */
InputStream * bool
OpenLocalInputStream(Path path, Mutex &mutex, Cond &cond, Error &error); client_allow_file(const Client &client, Path path_fs, Error &error);
#endif #endif

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -19,7 +19,8 @@
#include "config.h" #include "config.h"
#include "ClientInternal.hxx" #include "ClientInternal.hxx"
#include "config/ConfigGlobal.hxx" #include "ClientList.hxx"
#include "ConfigGlobal.hxx"
#define CLIENT_TIMEOUT_DEFAULT (60) #define CLIENT_TIMEOUT_DEFAULT (60)
#define CLIENT_MAX_COMMAND_LIST_DEFAULT (2048*1024) #define CLIENT_MAX_COMMAND_LIST_DEFAULT (2048*1024)

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -28,15 +28,22 @@
void void
ClientList::Remove(Client &client) ClientList::Remove(Client &client)
{ {
assert(size > 0);
assert(!list.empty()); assert(!list.empty());
list.erase(list.iterator_to(client)); auto i = std::find(list.begin(), list.end(), &client);
assert(i != list.end());
list.erase(i);
--size;
} }
void void
ClientList::CloseAll() ClientList::CloseAll()
{ {
list.clear_and_dispose(Client::Disposer()); while (!list.empty())
list.front()->Close();
assert(size == 0);
} }
void void
@@ -44,6 +51,6 @@ ClientList::IdleAdd(unsigned flags)
{ {
assert(flags != 0); assert(flags != 0);
for (auto &client : list) for (const auto &client : list)
client.IdleAdd(flags); client->IdleAdd(flags);
} }

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -20,39 +20,38 @@
#ifndef MPD_CLIENT_LIST_HXX #ifndef MPD_CLIENT_LIST_HXX
#define MPD_CLIENT_LIST_HXX #define MPD_CLIENT_LIST_HXX
#include "Client.hxx" #include <list>
class Client; class Client;
class ClientList { class ClientList {
typedef boost::intrusive::list<Client,
boost::intrusive::constant_time_size<true>> List;
const unsigned max_size; const unsigned max_size;
List list; unsigned size;
std::list<Client *> list;
public: public:
ClientList(unsigned _max_size) ClientList(unsigned _max_size)
:max_size(_max_size) {} :max_size(_max_size), size(0) {}
~ClientList() { ~ClientList() {
CloseAll(); CloseAll();
} }
List::iterator begin() { std::list<Client *>::iterator begin() {
return list.begin(); return list.begin();
} }
List::iterator end() { std::list<Client *>::iterator end() {
return list.end(); return list.end();
} }
bool IsFull() const { bool IsFull() const {
return list.size() >= max_size; return size >= max_size;
} }
void Add(Client &client) { void Add(Client &client) {
list.push_front(client); list.push_front(&client);
++size;
} }
void Remove(Client &client); void Remove(Client &client);

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -24,12 +24,6 @@
#include <string> #include <string>
#ifdef WIN32
/* fuck WIN32! */
#include <windows.h>
#undef GetMessage
#endif
/** /**
* A client-to-client message. * A client-to-client message.
*/ */

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -28,12 +28,16 @@
#include "util/Error.hxx" #include "util/Error.hxx"
#include "Log.hxx" #include "Log.hxx"
#include <glib.h>
#include <assert.h> #include <assert.h>
#include <sys/types.h>
#ifdef WIN32 #ifdef WIN32
#include <winsock2.h> #include <winsock2.h>
#else #else
#include <sys/socket.h> #include <sys/socket.h>
#endif #endif
#include <unistd.h>
#ifdef HAVE_LIBWRAP #ifdef HAVE_LIBWRAP
#include <tcpd.h> #include <tcpd.h>
@@ -61,14 +65,15 @@ client_new(EventLoop &loop, Partition &partition,
int fd, const struct sockaddr *sa, size_t sa_length, int uid) int fd, const struct sockaddr *sa, size_t sa_length, int uid)
{ {
static unsigned int next_client_num; static unsigned int next_client_num;
const auto remote = sockaddr_to_string(sa, sa_length); char *remote;
assert(fd >= 0); assert(fd >= 0);
#ifdef HAVE_LIBWRAP #ifdef HAVE_LIBWRAP
if (sa->sa_family != AF_UNIX) { if (sa->sa_family != AF_UNIX) {
// TODO: shall we obtain the program name from argv[0]? char *hostaddr = sockaddr_to_string(sa, sa_length,
const char *progname = "mpd"; IgnoreError());
const char *progname = g_get_prgname();
struct request_info req; struct request_info req;
request_init(&req, RQ_FILE, fd, RQ_DAEMON, progname, 0); request_init(&req, RQ_FILE, fd, RQ_DAEMON, progname, 0);
@@ -79,11 +84,14 @@ client_new(EventLoop &loop, Partition &partition,
/* tcp wrappers says no */ /* tcp wrappers says no */
FormatWarning(client_domain, FormatWarning(client_domain,
"libwrap refused connection (libwrap=%s) from %s", "libwrap refused connection (libwrap=%s) from %s",
progname, remote.c_str()); progname, hostaddr);
g_free(hostaddr);
close_socket(fd); close_socket(fd);
return; return;
} }
g_free(hostaddr);
} }
#endif /* HAVE_WRAP */ #endif /* HAVE_WRAP */
@@ -101,8 +109,9 @@ client_new(EventLoop &loop, Partition &partition,
client_list.Add(*client); client_list.Add(*client);
FormatInfo(client_domain, "[%u] opened from %s", remote = sockaddr_to_string(sa, sa_length, IgnoreError());
client->num, remote.c_str()); FormatInfo(client_domain, "[%u] opened from %s", client->num, remote);
g_free(remote);
} }
void void

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -19,11 +19,11 @@
#include "config.h" #include "config.h"
#include "ClientInternal.hxx" #include "ClientInternal.hxx"
#include "Partition.hxx" #include "Main.hxx"
#include "Instance.hxx"
#include "event/Loop.hxx" #include "event/Loop.hxx"
#include "util/StringUtil.hxx" #include "util/CharUtil.hxx"
#include <assert.h>
#include <string.h> #include <string.h>
BufferedSocket::InputResult BufferedSocket::InputResult
@@ -39,10 +39,11 @@ Client::OnSocketInput(void *data, size_t length)
BufferedSocket::ConsumeInput(newline + 1 - p); BufferedSocket::ConsumeInput(newline + 1 - p);
/* skip whitespace at the end of the line */ /* skip whitespace at the end of the line */
char *end = StripRight(p, newline); while (newline > p && IsWhitespaceOrNull(newline[-1]))
--newline;
/* terminate the string at the end of the line */ /* terminate the string at the end of the line */
*end = 0; *newline = 0;
CommandResult result = client_process_line(*this, p); CommandResult result = client_process_line(*this, p);
switch (result) { switch (result) {
@@ -53,7 +54,7 @@ Client::OnSocketInput(void *data, size_t length)
case CommandResult::KILL: case CommandResult::KILL:
Close(); Close();
partition.instance.event_loop->Break(); main_loop->Break();
return InputResult::CLOSED; return InputResult::CLOSED;
case CommandResult::FINISH: case CommandResult::FINISH:

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -22,6 +22,11 @@
#include "Idle.hxx" #include "Idle.hxx"
#include <assert.h> #include <assert.h>
#include <string.h>
bool Unsubscribe(const char *channel);
void UnsubscribeAll();
bool PushMessage(const ClientMessage &msg);
Client::SubscribeResult Client::SubscribeResult
Client::Subscribe(const char *channel) Client::Subscribe(const char *channel)

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -22,115 +22,57 @@
#include "ls.hxx" #include "ls.hxx"
#include "LogInit.hxx" #include "LogInit.hxx"
#include "Log.hxx" #include "Log.hxx"
#include "config/ConfigGlobal.hxx" #include "ConfigGlobal.hxx"
#include "decoder/DecoderList.hxx" #include "DecoderList.hxx"
#include "decoder/DecoderPlugin.hxx" #include "DecoderPlugin.hxx"
#include "output/Registry.hxx" #include "OutputList.hxx"
#include "output/OutputPlugin.hxx" #include "OutputPlugin.hxx"
#include "input/Registry.hxx" #include "InputRegistry.hxx"
#include "input/InputPlugin.hxx" #include "InputPlugin.hxx"
#include "playlist/PlaylistRegistry.hxx" #include "PlaylistRegistry.hxx"
#include "playlist/PlaylistPlugin.hxx" #include "PlaylistPlugin.hxx"
#include "fs/AllocatedPath.hxx" #include "fs/AllocatedPath.hxx"
#include "fs/Traits.hxx" #include "fs/Traits.hxx"
#include "fs/FileSystem.hxx" #include "fs/FileSystem.hxx"
#include "fs/StandardDirectory.hxx"
#include "util/Error.hxx" #include "util/Error.hxx"
#include "util/Domain.hxx" #include "util/Domain.hxx"
#include "util/OptionDef.hxx" #include "system/FatalError.hxx"
#include "util/OptionParser.hxx"
#ifdef ENABLE_DATABASE
#include "db/Registry.hxx"
#include "db/DatabasePlugin.hxx"
#include "storage/Registry.hxx"
#include "storage/StoragePlugin.hxx"
#endif
#ifdef ENABLE_NEIGHBOR_PLUGINS
#include "neighbor/Registry.hxx"
#include "neighbor/NeighborPlugin.hxx"
#endif
#ifdef ENABLE_ENCODER #ifdef ENABLE_ENCODER
#include "encoder/EncoderList.hxx" #include "EncoderList.hxx"
#include "encoder/EncoderPlugin.hxx" #include "EncoderPlugin.hxx"
#endif #endif
#ifdef ENABLE_ARCHIVE #ifdef ENABLE_ARCHIVE
#include "archive/ArchiveList.hxx" #include "ArchiveList.hxx"
#include "archive/ArchivePlugin.hxx" #include "ArchivePlugin.hxx"
#endif #endif
#include <glib.h>
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#ifdef WIN32 #ifdef WIN32
#define CONFIG_FILE_LOCATION "mpd\\mpd.conf" #define CONFIG_FILE_LOCATION "\\mpd\\mpd.conf"
#define APP_CONFIG_FILE_LOCATION "conf\\mpd.conf"
#else #else
#define USER_CONFIG_FILE_LOCATION1 ".mpdconf" #define USER_CONFIG_FILE_LOCATION1 ".mpdconf"
#define USER_CONFIG_FILE_LOCATION2 ".mpd/mpd.conf" #define USER_CONFIG_FILE_LOCATION2 ".mpd/mpd.conf"
#define USER_CONFIG_FILE_LOCATION_XDG "mpd/mpd.conf" #define USER_CONFIG_FILE_LOCATION_XDG "mpd/mpd.conf"
#endif #endif
static constexpr OptionDef opt_kill(
"kill", "kill the currently running mpd session");
static constexpr OptionDef opt_no_config(
"no-config", "don't read from config");
static constexpr OptionDef opt_no_daemon(
"no-daemon", "don't detach from console");
static constexpr OptionDef opt_stdout(
"stdout", nullptr); // hidden, compatibility with old versions
static constexpr OptionDef opt_stderr(
"stderr", "print messages to stderr");
static constexpr OptionDef opt_verbose(
"verbose", 'v', "verbose logging");
static constexpr OptionDef opt_version(
"version", 'V', "print version number");
static constexpr OptionDef opt_help(
"help", 'h', "show help options");
static constexpr OptionDef opt_help_alt(
nullptr, '?', nullptr); // hidden, standard alias for --help
static constexpr Domain cmdline_domain("cmdline"); static constexpr Domain cmdline_domain("cmdline");
gcc_noreturn gcc_noreturn
static void version(void) static void version(void)
{ {
puts("Music Player Daemon " VERSION puts("Music Player Daemon " VERSION "\n"
#ifdef GIT_COMMIT
" (" GIT_COMMIT ")"
#endif
"\n"
"\n" "\n"
"Copyright (C) 2003-2007 Warren Dukes <warren.dukes@gmail.com>\n" "Copyright (C) 2003-2007 Warren Dukes <warren.dukes@gmail.com>\n"
"Copyright (C) 2008-2014 Max Kellermann <max@duempel.org>\n" "Copyright (C) 2008-2014 Max Kellermann <max@duempel.org>\n"
"This is free software; see the source for copying conditions. There is NO\n" "This is free software; see the source for copying conditions. There is NO\n"
"warranty; not even MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n"); "warranty; not even MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n"
"\n"
#ifdef ENABLE_DATABASE
puts("\n"
"Database plugins:");
for (auto i = database_plugins; *i != nullptr; ++i)
printf(" %s", (*i)->name);
puts("\n\n"
"Storage plugins:");
for (auto i = storage_plugins; *i != nullptr; ++i)
printf(" %s", (*i)->name);
#endif
#ifdef ENABLE_NEIGHBOR_PLUGINS
puts("\n\n"
"Neighbor plugins:");
for (auto i = neighbor_plugins; *i != nullptr; ++i)
printf(" %s", (*i)->name);
#endif
puts("\n\n"
"Decoders plugins:"); "Decoders plugins:");
decoder_plugins_for_each([](const DecoderPlugin &plugin){ decoder_plugins_for_each([](const DecoderPlugin &plugin){
@@ -190,165 +132,122 @@ static void version(void)
exit(EXIT_SUCCESS); exit(EXIT_SUCCESS);
} }
static void PrintOption(const OptionDef &opt) static const char *summary =
"Music Player Daemon - a daemon for playing music.";
gcc_pure
static AllocatedPath
PathBuildChecked(const AllocatedPath &a, PathTraits::const_pointer b)
{ {
if (opt.HasShortOption()) if (a.IsNull())
printf(" -%c, --%-12s%s\n", return AllocatedPath::Null();
opt.GetShortOption(),
opt.GetLongOption(),
opt.GetDescription());
else
printf(" --%-16s%s\n",
opt.GetLongOption(),
opt.GetDescription());
}
gcc_noreturn return AllocatedPath::Build(a, b);
static void help(void)
{
puts("Usage:\n"
" mpd [OPTION...] [path/to/mpd.conf]\n"
"\n"
"Music Player Daemon - a daemon for playing music.\n"
"\n"
"Options:");
PrintOption(opt_help);
PrintOption(opt_kill);
PrintOption(opt_no_config);
PrintOption(opt_no_daemon);
PrintOption(opt_stderr);
PrintOption(opt_verbose);
PrintOption(opt_version);
exit(EXIT_SUCCESS);
}
class ConfigLoader
{
Error &error;
bool result;
public:
ConfigLoader(Error &_error) : error(_error), result(false) { }
bool GetResult() const { return result; }
bool TryFile(const Path path);
bool TryFile(const AllocatedPath &base_path,
PathTraitsFS::const_pointer path);
};
bool ConfigLoader::TryFile(Path path)
{
if (FileExists(path)) {
result = ReadConfigFile(path, error);
return true;
}
return false;
}
bool ConfigLoader::TryFile(const AllocatedPath &base_path,
PathTraitsFS::const_pointer path)
{
if (base_path.IsNull())
return false;
auto full_path = AllocatedPath::Build(base_path, path);
return TryFile(full_path);
} }
bool bool
parse_cmdline(int argc, char **argv, struct options *options, parse_cmdline(int argc, char **argv, struct options *options,
Error &error) Error &error)
{ {
bool use_config_file = true; GOptionContext *context;
bool ret;
static gboolean option_version,
option_no_daemon,
option_no_config;
const GOptionEntry entries[] = {
{ "kill", 0, 0, G_OPTION_ARG_NONE, &options->kill,
"kill the currently running mpd session", nullptr },
{ "no-config", 0, 0, G_OPTION_ARG_NONE, &option_no_config,
"don't read from config", nullptr },
{ "no-daemon", 0, 0, G_OPTION_ARG_NONE, &option_no_daemon,
"don't detach from console", nullptr },
{ "stdout", 0, 0, G_OPTION_ARG_NONE, &options->log_stderr,
nullptr, nullptr },
{ "stderr", 0, 0, G_OPTION_ARG_NONE, &options->log_stderr,
"print messages to stderr", nullptr },
{ "verbose", 'v', 0, G_OPTION_ARG_NONE, &options->verbose,
"verbose logging", nullptr },
{ "version", 'V', 0, G_OPTION_ARG_NONE, &option_version,
"print version number", nullptr },
{ nullptr, 0, 0, G_OPTION_ARG_NONE, nullptr, nullptr, nullptr }
};
options->kill = false; options->kill = false;
options->daemon = true; options->daemon = true;
options->log_stderr = false; options->log_stderr = false;
options->verbose = false; options->verbose = false;
// First pass: handle command line options context = g_option_context_new("[path/to/mpd.conf]");
OptionParser parser(argc, argv); g_option_context_add_main_entries(context, entries, nullptr);
while (parser.HasEntries()) {
if (!parser.ParseNext())
continue;
if (parser.CheckOption(opt_kill)) {
options->kill = true;
continue;
}
if (parser.CheckOption(opt_no_config)) {
use_config_file = false;
continue;
}
if (parser.CheckOption(opt_no_daemon)) {
options->daemon = false;
continue;
}
if (parser.CheckOption(opt_stderr, opt_stdout)) {
options->log_stderr = true;
continue;
}
if (parser.CheckOption(opt_verbose)) {
options->verbose = true;
continue;
}
if (parser.CheckOption(opt_version))
version();
if (parser.CheckOption(opt_help, opt_help_alt))
help();
error.Format(cmdline_domain, "invalid option: %s", g_option_context_set_summary(context, summary);
parser.GetOption());
return false; GError *gerror = nullptr;
} ret = g_option_context_parse(context, &argc, &argv, &gerror);
g_option_context_free(context);
if (!ret)
FatalError("option parsing failed", gerror);
if (option_version)
version();
/* initialize the logging library, so the configuration file /* initialize the logging library, so the configuration file
parser can use it already */ parser can use it already */
log_early_init(options->verbose); log_early_init(options->verbose);
if (!use_config_file) { options->daemon = !option_no_daemon;
if (option_no_config) {
LogDebug(cmdline_domain, LogDebug(cmdline_domain,
"Ignoring config, using daemon defaults"); "Ignoring config, using daemon defaults");
return true; return true;
} } else if (argc <= 1) {
/* default configuration file path */
// Second pass: find non-option parameters (i.e. config file) #ifdef WIN32
const char *config_file = nullptr; AllocatedPath path = PathBuildChecked(AllocatedPath::FromUTF8(g_get_user_config_dir()),
for (int i = 1; i < argc; ++i) { CONFIG_FILE_LOCATION);
if (OptionParser::IsOption(argv[i])) if (!path.IsNull() && FileExists(path))
continue; return ReadConfigFile(path, error);
if (config_file == nullptr) {
config_file = argv[i]; const char *const*system_config_dirs =
continue; g_get_system_config_dirs();
for (unsigned i = 0; system_config_dirs[i] != nullptr; ++i) {
path = PathBuildChecked(AllocatedPath::FromUTF8(system_config_dirs[i]),
CONFIG_FILE_LOCATION);
if (!path.IsNull() && FileExists(path))
return ReadConfigFile(path, error);
} }
#else
AllocatedPath path = PathBuildChecked(AllocatedPath::FromUTF8(g_get_user_config_dir()),
USER_CONFIG_FILE_LOCATION_XDG);
if (!path.IsNull() && FileExists(path))
return ReadConfigFile(path, error);
path = PathBuildChecked(AllocatedPath::FromUTF8(g_get_home_dir()),
USER_CONFIG_FILE_LOCATION1);
if (!path.IsNull() && FileExists(path))
return ReadConfigFile(path, error);
path = PathBuildChecked(AllocatedPath::FromUTF8(g_get_home_dir()),
USER_CONFIG_FILE_LOCATION2);
if (!path.IsNull() && FileExists(path))
return ReadConfigFile(path, error);
path = AllocatedPath::FromUTF8(SYSTEM_CONFIG_FILE_LOCATION);
if (!path.IsNull() && FileExists(path))
return ReadConfigFile(path, error);
#endif
error.Set(cmdline_domain, "No configuration file found");
return false;
} else if (argc == 2) {
/* specified configuration file */
return ReadConfigFile(Path::FromFS(argv[1]), error);
} else {
error.Set(cmdline_domain, "too many arguments"); error.Set(cmdline_domain, "too many arguments");
return false; return false;
} }
if (config_file != nullptr) {
/* use specified configuration file */
return ReadConfigFile(Path::FromFS(config_file), error);
}
/* use default configuration file path */
ConfigLoader loader(error);
bool found =
#ifdef WIN32
loader.TryFile(GetUserConfigDir(), CONFIG_FILE_LOCATION) ||
loader.TryFile(GetSystemConfigDir(), CONFIG_FILE_LOCATION) ||
loader.TryFile(GetAppBaseDir(), APP_CONFIG_FILE_LOCATION);
#else
loader.TryFile(GetUserConfigDir(),
USER_CONFIG_FILE_LOCATION_XDG) ||
loader.TryFile(GetHomeDir(), USER_CONFIG_FILE_LOCATION1) ||
loader.TryFile(GetHomeDir(), USER_CONFIG_FILE_LOCATION2) ||
loader.TryFile(Path::FromFS(SYSTEM_CONFIG_FILE_LOCATION));
#endif
if (!found) {
error.Set(cmdline_domain, "No configuration file found");
return false;
}
return loader.GetResult();
} }

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -20,13 +20,15 @@
#ifndef MPD_COMMAND_LINE_HXX #ifndef MPD_COMMAND_LINE_HXX
#define MPD_COMMAND_LINE_HXX #define MPD_COMMAND_LINE_HXX
#include <glib.h>
class Error; class Error;
struct options { struct options {
bool kill; gboolean kill;
bool daemon; gboolean daemon;
bool log_stderr; gboolean log_stderr;
bool verbose; gboolean verbose;
}; };
bool bool

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -26,6 +26,7 @@
#include "system/FatalError.hxx" #include "system/FatalError.hxx"
#include <assert.h> #include <assert.h>
#include <string.h>
#include <stdlib.h> #include <stdlib.h>
int int
@@ -63,7 +64,7 @@ block_param::GetBoolValue() const
} }
config_param::config_param(const char *_value, int _line) config_param::config_param(const char *_value, int _line)
:next(nullptr), value(_value), line(_line), used(false) {} :next(nullptr), value(_value), line(_line) {}
config_param::~config_param() config_param::~config_param()
{ {

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -19,6 +19,7 @@
#include "config.h" #include "config.h"
#include "ConfigFile.hxx" #include "ConfigFile.hxx"
#include "ConfigError.hxx"
#include "ConfigData.hxx" #include "ConfigData.hxx"
#include "ConfigTemplates.hxx" #include "ConfigTemplates.hxx"
#include "util/Tokenizer.hxx" #include "util/Tokenizer.hxx"
@@ -31,7 +32,9 @@
#include "Log.hxx" #include "Log.hxx"
#include <assert.h> #include <assert.h>
#include <string.h>
#include <stdio.h> #include <stdio.h>
#include <errno.h>
#define MAX_STRING_SIZE MPD_PATH_MAX+80 #define MAX_STRING_SIZE MPD_PATH_MAX+80
@@ -96,7 +99,7 @@ config_read_block(FILE *fp, int *count, char *string, Error &error)
} }
(*count)++; (*count)++;
line = StripLeft(line); line = strchug_fast(line);
if (*line == 0 || *line == CONF_COMMENT) if (*line == 0 || *line == CONF_COMMENT)
continue; continue;
@@ -104,7 +107,7 @@ config_read_block(FILE *fp, int *count, char *string, Error &error)
/* end of this block; return from the function /* end of this block; return from the function
(and from this "while" loop) */ (and from this "while" loop) */
line = StripLeft(line + 1); line = strchug_fast(line + 1);
if (*line != 0 && *line != CONF_COMMENT) { if (*line != 0 && *line != CONF_COMMENT) {
delete ret; delete ret;
error.Format(config_file_domain, error.Format(config_file_domain,
@@ -155,7 +158,7 @@ ReadConfigFile(ConfigData &config_data, FILE *fp, Error &error)
count++; count++;
line = StripLeft(string); line = strchug_fast(string);
if (*line == 0 || *line == CONF_COMMENT) if (*line == 0 || *line == CONF_COMMENT)
continue; continue;
@@ -205,7 +208,7 @@ ReadConfigFile(ConfigData &config_data, FILE *fp, Error &error)
return false; return false;
} }
line = StripLeft(tokenizer.Rest() + 1); line = strchug_fast(tokenizer.Rest() + 1);
if (*line != 0 && *line != CONF_COMMENT) { if (*line != 0 && *line != CONF_COMMENT) {
error.Format(config_file_domain, error.Format(config_file_domain,
"line %i: Unknown tokens after '{'", "line %i: Unknown tokens after '{'",

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -30,6 +30,8 @@
#include "system/FatalError.hxx" #include "system/FatalError.hxx"
#include "Log.hxx" #include "Log.hxx"
#include <assert.h>
#include <string.h>
#include <stdlib.h> #include <stdlib.h>
static ConfigData config_data; static ConfigData config_data;
@@ -74,32 +76,17 @@ void config_global_check(void)
Check(p); Check(p);
} }
const config_param * const struct config_param *
config_get_param(ConfigOption option) config_get_next_param(ConfigOption option, const struct config_param * last)
{ {
config_param *param = config_data.params[unsigned(option)]; config_param *param = last != nullptr
? last->next
: config_data.params[unsigned(option)];
if (param != nullptr) if (param != nullptr)
param->used = true; param->used = true;
return param; return param;
} }
const config_param *
config_find_block(ConfigOption option, const char *key, const char *value)
{
for (const config_param *param = config_get_param(option);
param != nullptr; param = param->next) {
const char *value2 = param->GetBlockValue(key);
if (value2 == nullptr)
FormatFatalError("block without '%s' name in line %d",
key, param->line);
if (strcmp(value2, value) == 0)
return param;
}
return nullptr;
}
const char * const char *
config_get_string(ConfigOption option, const char *default_value) config_get_string(ConfigOption option, const char *default_value)
{ {

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -26,7 +26,6 @@
class Error; class Error;
class Path; class Path;
class AllocatedPath; class AllocatedPath;
struct config_param;
void config_global_init(void); void config_global_init(void);
void config_global_finish(void); void config_global_finish(void);
@@ -40,20 +39,19 @@ void config_global_check(void);
bool bool
ReadConfigFile(Path path, Error &error); ReadConfigFile(Path path, Error &error);
/* don't free the returned value
set _last_ to nullptr to get first entry */
gcc_pure gcc_pure
const config_param * const struct config_param *
config_get_param(enum ConfigOption option); config_get_next_param(enum ConfigOption option,
const struct config_param *last);
/**
* Find a block with a matching attribute.
*
* @param option the blocks to search
* @param key the attribute name
* @param value the expected attribute value
*/
gcc_pure gcc_pure
const config_param * static inline const struct config_param *
config_find_block(ConfigOption option, const char *key, const char *value); config_get_param(enum ConfigOption option)
{
return config_get_next_param(option, nullptr);
}
/* Note on gcc_pure: Some of the functions declared pure are not /* Note on gcc_pure: Some of the functions declared pure are not
really pure in strict sense. They have side effect such that they really pure in strict sense. They have side effect such that they

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -32,7 +32,6 @@ enum ConfigOption {
CONF_LOG_FILE, CONF_LOG_FILE,
CONF_PID_FILE, CONF_PID_FILE,
CONF_STATE_FILE, CONF_STATE_FILE,
CONF_STATE_FILE_INTERVAL,
CONF_RESTORE_PAUSED, CONF_RESTORE_PAUSED,
CONF_USER, CONF_USER,
CONF_GROUP, CONF_GROUP,
@@ -78,7 +77,6 @@ enum ConfigOption {
CONF_DESPOTIFY_HIGH_BITRATE, CONF_DESPOTIFY_HIGH_BITRATE,
CONF_AUDIO_FILTER, CONF_AUDIO_FILTER,
CONF_DATABASE, CONF_DATABASE,
CONF_NEIGHBORS,
CONF_MAX CONF_MAX
}; };

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -22,10 +22,11 @@
#include "fs/AllocatedPath.hxx" #include "fs/AllocatedPath.hxx"
#include "fs/Traits.hxx" #include "fs/Traits.hxx"
#include "fs/Domain.hxx" #include "fs/Domain.hxx"
#include "fs/StandardDirectory.hxx"
#include "util/Error.hxx" #include "util/Error.hxx"
#include "ConfigGlobal.hxx" #include "ConfigGlobal.hxx"
#include <glib.h>
#include <assert.h> #include <assert.h>
#include <string.h> #include <string.h>
@@ -38,14 +39,14 @@
static AllocatedPath static AllocatedPath
GetHome(const char *user, Error &error) GetHome(const char *user, Error &error)
{ {
AllocatedPath result = GetHomeDir(user); passwd *pw = getpwnam(user);
if (result.IsNull()) { if (pw == nullptr) {
error.Format(path_domain, error.Format(path_domain,
"no such user: %s", user); "no such user: %s", user);
return AllocatedPath::Null(); return AllocatedPath::Null();
} }
return result; return AllocatedPath::FromFS(pw->pw_dir);
} }
/** /**
@@ -54,14 +55,14 @@ GetHome(const char *user, Error &error)
static AllocatedPath static AllocatedPath
GetHome(Error &error) GetHome(Error &error)
{ {
AllocatedPath result = GetHomeDir(); const char *home = g_get_home_dir();
if (result.IsNull()) { if (home == nullptr) {
error.Set(path_domain, error.Set(path_domain,
"problems getting home for current user"); "problems getting home for current user");
return AllocatedPath::Null(); return AllocatedPath::Null();
} }
return result; return AllocatedPath::FromUTF8(home, error);
} }
/** /**
@@ -118,7 +119,7 @@ ParsePath(const char *path, Error &error)
return AllocatedPath::Null(); return AllocatedPath::Null();
return AllocatedPath::Build(home, path2); return AllocatedPath::Build(home, path2);
} else if (!PathTraitsUTF8::IsAbsolute(path)) { } else if (!PathTraits::IsAbsoluteUTF8(path)) {
error.Format(path_domain, error.Format(path_domain,
"not an absolute path: %s", path); "not an absolute path: %s", path);
return AllocatedPath::Null(); return AllocatedPath::Null();

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -32,7 +32,6 @@ const ConfigTemplate config_templates[] = {
{ "log_file", false, false }, { "log_file", false, false },
{ "pid_file", false, false }, { "pid_file", false, false },
{ "state_file", false, false }, { "state_file", false, false },
{ "state_file_interval", false, false },
{ "restore_paused", false, false }, { "restore_paused", false, false },
{ "user", false, false }, { "user", false, false },
{ "group", false, false }, { "group", false, false },
@@ -78,7 +77,6 @@ const ConfigTemplate config_templates[] = {
{ "despotify_high_bitrate", false, false }, { "despotify_high_bitrate", false, false },
{ "filter", true, true }, { "filter", true, true },
{ "database", false, true }, { "database", false, true },
{ "neighbors", true, true },
}; };
static constexpr unsigned n_config_templates = static constexpr unsigned n_config_templates =

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -20,6 +20,8 @@
#ifndef MPD_CONFIG_TEMPLATES_HXX #ifndef MPD_CONFIG_TEMPLATES_HXX
#define MPD_CONFIG_TEMPLATES_HXX #define MPD_CONFIG_TEMPLATES_HXX
#include "ConfigOption.hxx"
struct ConfigTemplate { struct ConfigTemplate {
const char *const name; const char *const name;
const bool repeatable; const bool repeatable;

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -19,7 +19,6 @@
#include "config.h" #include "config.h"
#include "CrossFade.hxx" #include "CrossFade.hxx"
#include "Chrono.hxx"
#include "MusicChunk.hxx" #include "MusicChunk.hxx"
#include "AudioFormat.hxx" #include "AudioFormat.hxx"
#include "util/NumberParser.hxx" #include "util/NumberParser.hxx"
@@ -27,6 +26,8 @@
#include "Log.hxx" #include "Log.hxx"
#include <assert.h> #include <assert.h>
#include <string.h>
#include <stdlib.h>
static constexpr Domain cross_fade_domain("cross_fade"); static constexpr Domain cross_fade_domain("cross_fade");
@@ -86,7 +87,7 @@ mixramp_interpolate(const char *ramp_list, float required_db)
} }
unsigned unsigned
CrossFadeSettings::Calculate(SignedSongTime total_time, CrossFadeSettings::Calculate(float total_time,
float replay_gain_db, float replay_gain_prev_db, float replay_gain_db, float replay_gain_prev_db,
const char *mixramp_start, const char *mixramp_prev_end, const char *mixramp_start, const char *mixramp_prev_end,
const AudioFormat af, const AudioFormat af,
@@ -96,8 +97,7 @@ CrossFadeSettings::Calculate(SignedSongTime total_time,
unsigned int chunks = 0; unsigned int chunks = 0;
float chunks_f; float chunks_f;
if (total_time.IsNegative() || if (duration < 0 || duration >= total_time ||
duration < 0 || duration >= total_time.ToDoubleS() ||
/* we can't crossfade when the audio formats are different */ /* we can't crossfade when the audio formats are different */
af != old_format) af != old_format)
return 0; return 0;

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -23,7 +23,6 @@
#include "Compiler.h" #include "Compiler.h"
struct AudioFormat; struct AudioFormat;
class SignedSongTime;
struct CrossFadeSettings { struct CrossFadeSettings {
/** /**
@@ -61,7 +60,7 @@ struct CrossFadeSettings {
* should be disabled for this song change * should be disabled for this song change
*/ */
gcc_pure gcc_pure
unsigned Calculate(SignedSongTime total_time, unsigned Calculate(float total_time,
float replay_gain_db, float replay_gain_prev_db, float replay_gain_db, float replay_gain_prev_db,
const char *mixramp_start, const char *mixramp_start,
const char *mixramp_prev_end, const char *mixramp_prev_end,

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -23,15 +23,19 @@
#include "fs/AllocatedPath.hxx" #include "fs/AllocatedPath.hxx"
#include "fs/FileSystem.hxx" #include "fs/FileSystem.hxx"
#include "util/Domain.hxx" #include "util/Domain.hxx"
#include "PidFile.hxx"
#include "Log.hxx" #include "Log.hxx"
#include <glib.h>
#include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <unistd.h> #include <unistd.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h> #include <fcntl.h>
#ifndef WIN32 #ifndef WIN32
#include <sys/wait.h>
#include <signal.h> #include <signal.h>
#include <pwd.h> #include <pwd.h>
#include <grp.h> #include <grp.h>
@@ -56,11 +60,6 @@ static AllocatedPath pidfile = AllocatedPath::Null();
/* whether "group" conf. option was given */ /* whether "group" conf. option was given */
static bool had_group = false; static bool had_group = false;
/**
* The write end of a pipe that is used to notify the parent process
* that initialization has finished and that it should detach.
*/
static int detach_fd = -1;
void void
daemonize_kill(void) daemonize_kill(void)
@@ -136,93 +135,73 @@ daemonize_set_user(void)
} }
} }
void static void
daemonize_begin(bool detach) daemonize_detach(void)
{ {
/* release the current working directory */
if (chdir("/") < 0)
FatalError("problems changing to root directory");
if (!detach)
/* the rest of this function deals with detaching the
process */
return;
/* do this before daemonizing so we can fail gracefully if we
can't write to the pid file */
PidFile pidfile2(pidfile);
/* flush all file handles before duplicating the buffers */ /* flush all file handles before duplicating the buffers */
fflush(nullptr); fflush(nullptr);
/* create a pipe to synchronize the parent and the child */ #ifdef HAVE_DAEMON
int fds[2]; if (daemon(0, 1))
if (pipe(fds) < 0) FatalSystemError("daemon() failed");
FatalSystemError("pipe() failed");
/* move to a child process */ #elif defined(HAVE_FORK)
pid_t pid = fork(); /* detach from parent process */
if (pid < 0)
switch (fork()) {
case -1:
FatalSystemError("fork() failed"); FatalSystemError("fork() failed");
case 0:
if (pid == 0) { break;
/* in the child process */ default:
/* exit the parent process */
pidfile2.Close(); _exit(EXIT_SUCCESS);
close(fds[0]);
detach_fd = fds[1];
/* detach from the current session */
setsid();
/* continue starting MPD */
return;
} }
/* in the parent process */ /* release the current working directory */
close(fds[1]); if (chdir("/") < 0)
FatalError("problems changing to root directory");
int result; /* detach from the current session */
ssize_t nbytes = read(fds[0], &result, sizeof(result));
if (nbytes == (ssize_t)sizeof(result)) {
/* the child process was successful */
pidfile2.Write(pid);
exit(EXIT_SUCCESS);
}
/* something bad happened in the child process */ setsid();
pidfile2.Delete(pidfile); #else
FatalError("no support for daemonizing");
#endif
int status; LogDebug(daemon_domain, "daemonized");
pid_t pid2 = waitpid(pid, &status, 0);
if (pid2 < 0)
FatalSystemError("waitpid() failed");
if (WIFSIGNALED(status))
FormatFatalError("MPD died from signal %d%s", WTERMSIG(status),
WCOREDUMP(status) ? " (core dumped)" : "");
exit(WEXITSTATUS(status));
} }
void void
daemonize_commit() daemonize(bool detach)
{ {
if (detach_fd >= 0) { FILE *fp = nullptr;
/* tell the parent process to let go of us and exit
indicating success */ if (!pidfile.IsNull()) {
int result = 0; /* do this before daemon'izing so we can fail gracefully if we can't
write(detach_fd, &result, sizeof(result)); * write to the pid file */
close(detach_fd); LogDebug(daemon_domain, "opening pid file");
} else fp = FOpen(pidfile, "w+");
/* the pidfile was not written by the parent because if (!fp) {
there is no parent - do it now */ const std::string utf8 = pidfile.ToUTF8();
PidFile(pidfile).Write(); FormatFatalSystemError("Failed to create pid file \"%s\"",
pidfile.c_str());
}
}
if (detach)
daemonize_detach();
if (!pidfile.IsNull()) {
LogDebug(daemon_domain, "writing pid file");
fprintf(fp, "%lu\n", (unsigned long)getpid());
fclose(fp);
}
} }
void void
@@ -236,10 +215,10 @@ daemonize_init(const char *user, const char *group, AllocatedPath &&_pidfile)
user_uid = pwd->pw_uid; user_uid = pwd->pw_uid;
user_gid = pwd->pw_gid; user_gid = pwd->pw_gid;
user_name = strdup(user); user_name = g_strdup(user);
/* this is needed by libs such as arts */ /* this is needed by libs such as arts */
setenv("HOME", pwd->pw_dir, true); g_setenv("HOME", pwd->pw_dir, true);
} }
if (group) { if (group) {
@@ -262,7 +241,7 @@ daemonize_finish(void)
pidfile = AllocatedPath::Null(); pidfile = AllocatedPath::Null();
} }
free(user_name); g_free(user_name);
} }
#endif #endif

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -81,19 +81,11 @@ daemonize_set_user(void)
#ifndef WIN32 #ifndef WIN32
void void
daemonize_begin(bool detach); daemonize(bool detach);
#else #else
static inline void static inline void
daemonize_begin(bool detach) daemonize(bool detach)
{ (void)detach; } { (void)detach; }
#endif #endif
#ifndef WIN32
void
daemonize_commit();
#else
static inline void
daemonize_commit() {}
#endif
#endif #endif

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -30,8 +30,6 @@ enum db_error {
DB_DISABLED, DB_DISABLED,
DB_NOT_FOUND, DB_NOT_FOUND,
DB_CONFLICT,
}; };
extern const Domain db_domain; extern const Domain db_domain;

159
src/DatabaseGlue.cxx Normal file
View File

@@ -0,0 +1,159 @@
/*
* Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org
*
* 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.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "config.h"
#include "DatabaseGlue.hxx"
#include "DatabaseSimple.hxx"
#include "DatabaseRegistry.hxx"
#include "DatabaseSave.hxx"
#include "DatabaseError.hxx"
#include "Directory.hxx"
#include "util/Error.hxx"
#include "ConfigData.hxx"
#include "Stats.hxx"
#include "DatabasePlugin.hxx"
#include "db/SimpleDatabasePlugin.hxx"
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <assert.h>
#include <string.h>
#include <errno.h>
static Database *db;
static bool db_is_open;
static bool is_simple;
bool
DatabaseGlobalInit(const config_param &param, Error &error)
{
assert(db == nullptr);
assert(!db_is_open);
const char *plugin_name =
param.GetBlockValue("plugin", "simple");
is_simple = strcmp(plugin_name, "simple") == 0;
const DatabasePlugin *plugin = GetDatabasePluginByName(plugin_name);
if (plugin == nullptr) {
error.Format(db_domain,
"No such database plugin: %s", plugin_name);
return false;
}
db = plugin->create(param, error);
return db != nullptr;
}
void
DatabaseGlobalDeinit(void)
{
if (db_is_open)
db->Close();
if (db != nullptr)
delete db;
}
const Database *
GetDatabase()
{
assert(db == nullptr || db_is_open);
return db;
}
const Database *
GetDatabase(Error &error)
{
assert(db == nullptr || db_is_open);
if (db == nullptr)
error.Set(db_domain, DB_DISABLED, "No database");
return db;
}
bool
db_is_simple(void)
{
assert(db == nullptr || db_is_open);
return is_simple;
}
Directory *
db_get_root(void)
{
assert(db != nullptr);
assert(db_is_simple());
return ((SimpleDatabase *)db)->GetRoot();
}
Directory *
db_get_directory(const char *name)
{
if (db == nullptr)
return nullptr;
Directory *music_root = db_get_root();
if (name == nullptr)
return music_root;
return music_root->LookupDirectory(name);
}
bool
db_save(Error &error)
{
assert(db != nullptr);
assert(db_is_open);
assert(db_is_simple());
return ((SimpleDatabase *)db)->Save(error);
}
bool
DatabaseGlobalOpen(Error &error)
{
assert(db != nullptr);
assert(!db_is_open);
if (!db->Open(error))
return false;
db_is_open = true;
stats_update();
return true;
}
bool
db_exists()
{
assert(db != nullptr);
assert(db_is_open);
assert(db_is_simple());
return ((SimpleDatabase *)db)->GetUpdateStamp() > 0;
}

View File

@@ -1,5 +1,5 @@
/* /*
* Copyright (C) 2003-2014 The Music Player Daemon Project * Copyright (C) 2003-2013 The Music Player Daemon Project
* http://www.musicpd.org * http://www.musicpd.org
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
@@ -17,34 +17,43 @@
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/ */
#ifndef MPD_DATABASE_SONG_HXX #ifndef MPD_DATABASE_GLUE_HXX
#define MPD_DATABASE_SONG_HXX #define MPD_DATABASE_GLUE_HXX
#include "Compiler.h" #include "Compiler.h"
struct LightSong; struct config_param;
class Database; class Database;
class Storage;
class DetachedSong;
class Error; class Error;
/** /**
* "Detach" the #Song object, i.e. convert it to a #DetachedSong * Initialize the database library.
* instance. *
* @param param the database configuration block
*/ */
gcc_pure bool
DetachedSong DatabaseGlobalInit(const config_param &param, Error &error);
DatabaseDetachSong(const Storage &storage, const LightSong &song);
void
DatabaseGlobalDeinit(void);
bool
DatabaseGlobalOpen(Error &error);
/** /**
* Look up a song in the database and convert it to a #DetachedSong * Returns the global #Database instance. May return nullptr if this MPD
* instance. The caller is responsible for freeing it. * configuration has no database (no music_directory was configured).
*
* @return nullptr on error
*/ */
gcc_malloc gcc_nonnull_all gcc_pure
DetachedSong * const Database *
DatabaseDetachSong(const Database &db, const Storage &storage, const char *uri, GetDatabase();
Error &error);
/**
* Returns the global #Database instance. May return nullptr if this MPD
* configuration has no database (no music_directory was configured).
*/
gcc_pure
const Database *
GetDatabase(Error &error);
#endif #endif

Some files were not shown because too many files have changed in this diff Show More