Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
M
mpd
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Иван Мажукин
mpd
Commits
58dbe4bb
Commit
58dbe4bb
authored
Oct 28, 2004
by
Warren Dukes
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
merge shank-rewrite-config changes
git-svn-id:
https://svn.musicpd.org/mpd/trunk@2375
09075e82-0dd4-0310-85a5-a0d7c8717e4f
parent
8f40569a
Show whitespace changes
Inline
Side-by-side
Showing
24 changed files
with
877 additions
and
555 deletions
+877
-555
TODO
TODO
+2
-0
mpdconf.example
doc/mpdconf.example
+31
-35
audio.c
src/audio.c
+83
-24
audioOutput.c
src/audioOutput.c
+35
-5
audioOutput.h
src/audioOutput.h
+6
-2
audioOutput_ao.c
src/audioOutput_ao.c
+25
-10
audioOutput_shout.c
src/audioOutput_shout.c
+35
-49
conf.c
src/conf.c
+318
-204
conf.h
src/conf.h
+62
-49
directory.c
src/directory.c
+2
-1
inputStream_http.c
src/inputStream_http.c
+57
-45
interface.c
src/interface.c
+46
-15
list.c
src/list.c
+1
-1
list.h
src/list.h
+1
-0
listen.c
src/listen.c
+12
-8
log.c
src/log.c
+12
-4
main.c
src/main.c
+21
-14
path.c
src/path.c
+5
-4
permission.c
src/permission.c
+19
-22
playerData.c
src/playerData.c
+22
-8
playlist.c
src/playlist.c
+23
-15
replayGain.c
src/replayGain.c
+15
-11
tag.c
src/tag.c
+0
-12
volume.c
src/volume.c
+44
-17
No files found.
TODO
View file @
58dbe4bb
0.12
0.12
----
----
*) Fix id3v1 encoding
*) Abstract audio stuff into a plugin oriented thing
*) Abstract audio stuff into a plugin oriented thing
*) audio_ao & audio_oss & audio_shout
*) audio_ao & audio_oss & audio_shout
*) allow for sending to multiple audio devices
*) allow for sending to multiple audio devices
...
...
doc/mpdconf.example
View file @
58dbe4bb
...
@@ -71,28 +71,25 @@ error_file "~/.mpd/mpd.error"
...
@@ -71,28 +71,25 @@ error_file "~/.mpd/mpd.error"
################## AUDIO OUTPUT ##########################
################## AUDIO OUTPUT ##########################
#
#
# libao (ao_driver) supports any of the following:
# libao (ao_driver) supports any of the following:
#
# * Null output (handy for testing without a sound device)
# * WAV files
# * AU files
# * OSS (Open Sound System, used on Linux and FreeBSD)
# * aRts
# * esd (ESounD or Enlighten Sound Daemon)
# * ALSA (Advanced Linux Sound Architecture)
# * AIX
# * Sun/NetBSD/OpenBSD
# * IRIX
# * NAS (Network Audio Server)
#
# Refer to libao documentation for more information
# Refer to libao documentation for more information
#
#
# OSS Audio Output
# OSS Audio Output
#ao_driver "oss"
#audio_output {
#ao_driver_options "dsp=/dev/dsp"
# type "ao"
# name "my OSS device"
# driver "oss"
# options "dsp=/dev/dsp"
# write_size "1024"
#}
#
#
# ALSA Audio Output
# ALSA Audio Output
#ao_driver "alsa09"
#audio_output {
#ao_driver_options "dev=hw:0,0"
# type "ao"
# name "my ALSA device"
# driver "alsa09"
# options "dev=hw:0,0"
# write_size "1024"
#}
#
#
# Set this if you have problems
# Set this if you have problems
# playing audio files.
# playing audio files.
...
@@ -101,11 +98,24 @@ error_file "~/.mpd/mpd.error"
...
@@ -101,11 +98,24 @@ error_file "~/.mpd/mpd.error"
#
#
#audio_output_format "44100:16:2"
#audio_output_format "44100:16:2"
#
#
# You should not need mess with
##########################################################
# this value unless you know
# what you're doing.
################# SHOUT STREAMING ########################
#
# Set this to allow mpd to stream its output to icecast2
# (i.e. mpd is a icecast2 source)
#
#
#audio_write_size "1024"
#audio_output {
# type "shout"
# name "my cool stream"
# host "hostname"
# port "8000"
# user "source"
# password "hackme"
# quality "5.0"
# format "44100:16:1"
#}
#
#
##########################################################
##########################################################
...
@@ -179,20 +189,6 @@ error_file "~/.mpd/mpd.error"
...
@@ -179,20 +189,6 @@ error_file "~/.mpd/mpd.error"
##########################################
##########################################
################ SHOUT OPTIONS #####################
#
#shout_host "host"
#shout_port "8000"
#shout_user "source"
#shout_password "hackme"
#shout_name "My MPD!"
#shout_mount "/mpd.ogg"
#shout_quality "0.5"
#shout_format "44100:16:1"
#
####################################################
################ MISCELLANEOUS OPTIONS ###################
################ MISCELLANEOUS OPTIONS ###################
#
#
# This setting exists as precaution against attacks.
# This setting exists as precaution against attacks.
...
...
src/audio.c
View file @
58dbe4bb
...
@@ -31,9 +31,6 @@ static AudioFormat audio_format;
...
@@ -31,9 +31,6 @@ static AudioFormat audio_format;
static
AudioFormat
*
audio_configFormat
=
NULL
;
static
AudioFormat
*
audio_configFormat
=
NULL
;
static
AudioOutput
*
aoOutput
=
NULL
;
static
AudioOutput
*
shoutOutput
=
NULL
;
void
copyAudioFormat
(
AudioFormat
*
dest
,
AudioFormat
*
src
)
{
void
copyAudioFormat
(
AudioFormat
*
dest
,
AudioFormat
*
src
)
{
if
(
!
src
)
return
;
if
(
!
src
)
return
;
...
@@ -42,17 +39,34 @@ void copyAudioFormat(AudioFormat * dest, AudioFormat * src) {
...
@@ -42,17 +39,34 @@ void copyAudioFormat(AudioFormat * dest, AudioFormat * src) {
dest
->
channels
=
src
->
channels
;
dest
->
channels
=
src
->
channels
;
}
}
static
AudioOutput
**
audioOutputArray
=
NULL
;
static
int
audioOutputArraySize
=
0
;
extern
AudioOutputPlugin
aoPlugin
;
extern
AudioOutputPlugin
aoPlugin
;
extern
AudioOutputPlugin
shoutPlugin
;
extern
AudioOutputPlugin
shoutPlugin
;
void
initAudioDriver
()
{
void
initAudioDriver
()
{
ConfigParam
*
param
=
NULL
;
int
i
;
initAudioOutputPlugins
();
initAudioOutputPlugins
();
loadAudioOutputPlugin
(
&
aoPlugin
);
loadAudioOutputPlugin
(
&
aoPlugin
);
loadAudioOutputPlugin
(
&
shoutPlugin
);
loadAudioOutputPlugin
(
&
shoutPlugin
);
aoOutput
=
newAudioOutput
(
"ao"
);
while
((
param
=
getNextConfigParam
(
CONF_AUDIO_OUTPUT
,
param
)))
{
assert
(
aoOutput
);
i
=
audioOutputArraySize
++
;
shoutOutput
=
newAudioOutput
(
"shout"
);
audioOutputArray
=
realloc
(
audioOutputArray
,
audioOutputArraySize
*
sizeof
(
AudioOutput
*
));
audioOutputArray
[
i
]
=
newAudioOutput
(
param
);
if
(
!
audioOutputArray
[
i
])
{
ERROR
(
"problems configuring output device defined at "
"line %i
\n
"
,
param
->
line
);
exit
(
EXIT_FAILURE
);
}
}
}
}
void
getOutputAudioFormat
(
AudioFormat
*
inAudioFormat
,
void
getOutputAudioFormat
(
AudioFormat
*
inAudioFormat
,
...
@@ -65,13 +79,17 @@ void getOutputAudioFormat(AudioFormat * inAudioFormat,
...
@@ -65,13 +79,17 @@ void getOutputAudioFormat(AudioFormat * inAudioFormat,
}
}
void
initAudioConfig
()
{
void
initAudioConfig
()
{
char
*
conf
=
getConf
()[
CONF_AUDIO_OUTPUT_FORMAT
]
;
ConfigParam
*
param
=
getConfigParam
(
CONF_AUDIO_OUTPUT_FORMAT
)
;
if
(
NULL
==
conf
)
return
;
if
(
NULL
==
param
||
NULL
==
param
->
value
)
return
;
audio_configFormat
=
malloc
(
sizeof
(
AudioFormat
));
audio_configFormat
=
malloc
(
sizeof
(
AudioFormat
));
if
(
0
!=
parseAudioConfig
(
audio_configFormat
,
conf
))
exit
(
EXIT_FAILURE
);
if
(
0
!=
parseAudioConfig
(
audio_configFormat
,
param
->
value
))
{
ERROR
(
"error parsing
\"
%s
\"
at line %i
\n
"
,
CONF_AUDIO_OUTPUT_FORMAT
,
param
->
line
);
exit
(
EXIT_FAILURE
);
}
}
}
int
parseAudioConfig
(
AudioFormat
*
audioFormat
,
char
*
conf
)
{
int
parseAudioConfig
(
AudioFormat
*
audioFormat
,
char
*
conf
)
{
...
@@ -145,10 +163,15 @@ void finishAudioConfig() {
...
@@ -145,10 +163,15 @@ void finishAudioConfig() {
}
}
void
finishAudioDriver
()
{
void
finishAudioDriver
()
{
finishAudioOutput
(
aoOutput
);
int
i
;
if
(
shoutOutput
)
finishAudioOutput
(
shoutOutput
);
shoutOutput
=
NULL
;
for
(
i
=
0
;
i
<
audioOutputArraySize
;
i
++
)
{
aoOutput
=
NULL
;
finishAudioOutput
(
audioOutputArray
[
i
]);
}
free
(
audioOutputArray
);
audioOutputArray
=
NULL
;
audioOutputArraySize
=
0
;
}
}
int
isCurrentAudioFormat
(
AudioFormat
*
audioFormat
)
{
int
isCurrentAudioFormat
(
AudioFormat
*
audioFormat
)
{
...
@@ -160,29 +183,65 @@ int isCurrentAudioFormat(AudioFormat * audioFormat) {
...
@@ -160,29 +183,65 @@ int isCurrentAudioFormat(AudioFormat * audioFormat) {
}
}
int
openAudioDevice
(
AudioFormat
*
audioFormat
)
{
int
openAudioDevice
(
AudioFormat
*
audioFormat
)
{
if
(
!
aoOutput
->
open
||
!
isCurrentAudioFormat
(
audioFormat
))
{
int
isCurrentFormat
=
isCurrentAudioFormat
(
audioFormat
);
if
(
audioFormat
)
copyAudioFormat
(
&
audio_format
,
audioFormat
);
int
ret
=
-
1
;
if
(
shoutOutput
)
openAudioOutput
(
shoutOutput
,
&
audio_format
);
int
i
;
return
openAudioOutput
(
aoOutput
,
&
audio_format
);
if
(
!
audioOutputArray
)
return
-
1
;
if
(
!
isCurrentFormat
)
{
copyAudioFormat
(
&
audio_format
,
audioFormat
);
}
}
return
0
;
for
(
i
=
0
;
i
<
audioOutputArraySize
;
i
++
)
{
if
(
!
audioOutputArray
[
i
]
->
open
||
!
isCurrentFormat
)
{
if
(
0
==
openAudioOutput
(
audioOutputArray
[
i
],
&
audio_format
))
{
ret
=
0
;
}
}
}
return
ret
;
}
}
int
playAudio
(
char
*
playChunk
,
int
size
)
{
int
playAudio
(
char
*
playChunk
,
int
size
)
{
if
(
shoutOutput
)
playAudioOutput
(
shoutOutput
,
playChunk
,
size
);
int
ret
=
-
1
;
return
playAudioOutput
(
aoOutput
,
playChunk
,
size
);
int
i
;
for
(
i
=
0
;
i
<
audioOutputArraySize
;
i
++
)
{
if
(
0
==
playAudioOutput
(
audioOutputArray
[
i
],
playChunk
,
size
))
{
ret
=
0
;
}
}
return
ret
;
}
}
int
isAudioDeviceOpen
()
{
int
isAudioDeviceOpen
()
{
return
aoOutput
->
open
;
int
ret
=
0
;
int
i
;
for
(
i
=
0
;
i
<
audioOutputArraySize
;
i
++
)
{
ret
|=
audioOutputArray
[
i
]
->
open
;
}
return
ret
;
}
}
void
closeAudioDevice
()
{
void
closeAudioDevice
()
{
if
(
shoutOutput
)
closeAudioOutput
(
shoutOutput
);
int
i
;
closeAudioOutput
(
aoOutput
);
for
(
i
=
0
;
i
<
audioOutputArraySize
;
i
++
)
{
closeAudioOutput
(
audioOutputArray
[
i
]);
}
}
}
void
sendMetadataToAudioDevice
(
MpdTag
*
tag
)
{
void
sendMetadataToAudioDevice
(
MpdTag
*
tag
)
{
if
(
shoutOutput
)
sendMetadataToAudioOutput
(
shoutOutput
,
tag
);
int
i
;
for
(
i
=
0
;
i
<
audioOutputArraySize
;
i
++
)
{
sendMetadataToAudioOutput
(
audioOutputArray
[
i
],
tag
);
}
}
}
src/audioOutput.c
View file @
58dbe4bb
#include
<audioOutput.h>
#include
"audioOutput.h"
#include <list.h>
#include "list.h"
#include "log.h"
#include <string.h>
#define AUDIO_OUTPUT_TYPE "type"
#define AUDIO_OUTPUT_NAME "name"
static
List
*
audioOutputPluginList
;
static
List
*
audioOutputPluginList
;
...
@@ -21,13 +27,32 @@ void finishAudioOutputPlugins() {
...
@@ -21,13 +27,32 @@ void finishAudioOutputPlugins() {
freeList
(
audioOutputPluginList
);
freeList
(
audioOutputPluginList
);
}
}
AudioOutput
*
newAudioOutput
(
char
*
name
)
{
#define getBlockParam(name, str) { \
BlockParam * bp; \
bp = getBlockParam(param, name); \
if(bp == NULL) { \
ERROR("couldn't find parameter \"%s\" in audio output " \
"definition begining at %i\n", \
name, param->line); \
exit(EXIT_FAILURE); \
} \
str = bp->value; \
}
AudioOutput
*
newAudioOutput
(
ConfigParam
*
param
)
{
AudioOutput
*
ret
=
NULL
;
AudioOutput
*
ret
=
NULL
;
void
*
data
=
NULL
;
void
*
data
=
NULL
;
char
*
name
=
NULL
;
char
*
type
=
NULL
;
getBlockParam
(
AUDIO_OUTPUT_NAME
,
name
);
getBlockParam
(
AUDIO_OUTPUT_TYPE
,
type
);
if
(
findInList
(
audioOutputPluginList
,
nam
e
,
&
data
))
{
if
(
findInList
(
audioOutputPluginList
,
typ
e
,
&
data
))
{
AudioOutputPlugin
*
plugin
=
(
AudioOutputPlugin
*
)
data
;
AudioOutputPlugin
*
plugin
=
(
AudioOutputPlugin
*
)
data
;
ret
=
malloc
(
sizeof
(
AudioOutput
));
ret
=
malloc
(
sizeof
(
AudioOutput
));
ret
->
name
=
strdup
(
name
);
ret
->
type
=
strdup
(
type
);
ret
->
finishDriverFunc
=
plugin
->
finishDriverFunc
;
ret
->
finishDriverFunc
=
plugin
->
finishDriverFunc
;
ret
->
openDeviceFunc
=
plugin
->
openDeviceFunc
;
ret
->
openDeviceFunc
=
plugin
->
openDeviceFunc
;
ret
->
playFunc
=
plugin
->
playFunc
;
ret
->
playFunc
=
plugin
->
playFunc
;
...
@@ -35,11 +60,16 @@ AudioOutput * newAudioOutput(char * name) {
...
@@ -35,11 +60,16 @@ AudioOutput * newAudioOutput(char * name) {
ret
->
sendMetdataFunc
=
plugin
->
sendMetdataFunc
;
ret
->
sendMetdataFunc
=
plugin
->
sendMetdataFunc
;
ret
->
open
=
0
;
ret
->
open
=
0
;
if
(
plugin
->
initDriverFunc
(
ret
)
!=
0
)
{
if
(
plugin
->
initDriverFunc
(
ret
,
param
)
!=
0
)
{
free
(
ret
);
free
(
ret
);
ret
=
NULL
;
ret
=
NULL
;
}
}
}
}
else
{
ERROR
(
"couldn't find audio output plugin for type
\"
%s
\"
at "
"line %i"
,
type
,
param
->
line
);
exit
(
EXIT_FAILURE
);
}
return
ret
;
return
ret
;
}
}
...
...
src/audioOutput.h
View file @
58dbe4bb
...
@@ -24,12 +24,14 @@
...
@@ -24,12 +24,14 @@
#include "mpd_types.h"
#include "mpd_types.h"
#include "audio.h"
#include "audio.h"
#include "tag.h"
#include "tag.h"
#include "conf.h"
#define AUDIO_AO_DRIVER_DEFAULT "default"
#define AUDIO_AO_DRIVER_DEFAULT "default"
typedef
struct
_AudioOutput
AudioOutput
;
typedef
struct
_AudioOutput
AudioOutput
;
typedef
int
(
*
AudioOutputInitDriverFunc
)
(
AudioOutput
*
audioOutput
);
typedef
int
(
*
AudioOutputInitDriverFunc
)
(
AudioOutput
*
audioOutput
,
ConfigParam
*
param
);
typedef
void
(
*
AudioOutputFinishDriverFunc
)
(
AudioOutput
*
audioOutput
);
typedef
void
(
*
AudioOutputFinishDriverFunc
)
(
AudioOutput
*
audioOutput
);
...
@@ -46,6 +48,8 @@ typedef void (* AudioOutputSendMetadataFunc) (AudioOutput * audioOutput,
...
@@ -46,6 +48,8 @@ typedef void (* AudioOutputSendMetadataFunc) (AudioOutput * audioOutput,
struct
_AudioOutput
{
struct
_AudioOutput
{
int
open
;
int
open
;
char
*
name
;
char
*
type
;
AudioOutputFinishDriverFunc
finishDriverFunc
;
AudioOutputFinishDriverFunc
finishDriverFunc
;
AudioOutputOpenDeviceFunc
openDeviceFunc
;
AudioOutputOpenDeviceFunc
openDeviceFunc
;
...
@@ -73,7 +77,7 @@ void finishAudioOutputPlugins();
...
@@ -73,7 +77,7 @@ void finishAudioOutputPlugins();
void
loadAudioOutputPlugin
(
AudioOutputPlugin
*
audioOutputPlugin
);
void
loadAudioOutputPlugin
(
AudioOutputPlugin
*
audioOutputPlugin
);
void
unloadAudioOutputPlugin
(
AudioOutputPlugin
*
audioOutputPlugin
);
void
unloadAudioOutputPlugin
(
AudioOutputPlugin
*
audioOutputPlugin
);
AudioOutput
*
newAudioOutput
(
char
*
name
);
AudioOutput
*
newAudioOutput
(
ConfigParam
*
param
);
int
openAudioOutput
(
AudioOutput
*
audioOutput
,
AudioFormat
*
audioFormat
);
int
openAudioOutput
(
AudioOutput
*
audioOutput
,
AudioFormat
*
audioFormat
);
int
playAudioOutput
(
AudioOutput
*
audioOutput
,
char
*
playChunk
,
int
size
);
int
playAudioOutput
(
AudioOutput
*
audioOutput
,
char
*
playChunk
,
int
size
);
void
closeAudioOutput
(
AudioOutput
*
audioOutput
);
void
closeAudioOutput
(
AudioOutput
*
audioOutput
);
...
...
src/audioOutput_ao.c
View file @
58dbe4bb
...
@@ -56,7 +56,9 @@ static void audioOutputAo_error() {
...
@@ -56,7 +56,9 @@ static void audioOutputAo_error() {
}
}
}
}
static
int
audioOutputAo_initDriver
(
AudioOutput
*
audioOutput
)
{
static
int
audioOutputAo_initDriver
(
AudioOutput
*
audioOutput
,
ConfigParam
*
param
)
{
ao_info
*
ai
;
ao_info
*
ai
;
char
*
dup
;
char
*
dup
;
char
*
stk1
;
char
*
stk1
;
...
@@ -66,38 +68,51 @@ static int audioOutputAo_initDriver(AudioOutput * audioOutput) {
...
@@ -66,38 +68,51 @@ static int audioOutputAo_initDriver(AudioOutput * audioOutput) {
char
*
value
;
char
*
value
;
char
*
test
;
char
*
test
;
AoData
*
ad
=
newAoData
();
AoData
*
ad
=
newAoData
();
BlockParam
*
blockParam
;
audioOutput
->
data
=
ad
;
audioOutput
->
data
=
ad
;
ad
->
writeSize
=
strtol
((
getConf
())[
CONF_AUDIO_WRITE_SIZE
],
&
test
,
10
);
if
((
blockParam
=
getBlockParam
(
param
,
"write_size"
)))
{
ad
->
writeSize
=
strtol
(
blockParam
->
value
,
&
test
,
10
);
if
(
*
test
!=
'\0'
)
{
if
(
*
test
!=
'\0'
)
{
ERROR
(
"
\"
%s
\"
is not a valid write size
\n
"
,
ERROR
(
"
\"
%s
\"
is not a valid write size at line %i
\n
"
,
(
getConf
())[
CONF_AUDIO_WRITE_SIZE
]
);
blockParam
->
value
,
blockParam
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
}
else
ad
->
writeSize
=
1024
;
if
(
driverInitCount
==
0
)
{
if
(
driverInitCount
==
0
)
{
ao_initialize
();
ao_initialize
();
}
}
driverInitCount
++
;
driverInitCount
++
;
if
(
strcmp
(
AUDIO_AO_DRIVER_DEFAULT
,(
getConf
())[
CONF_AO_DRIVER
])
==
0
)
{
blockParam
=
getBlockParam
(
param
,
"driver"
);
if
(
!
blockParam
||
0
==
strcmp
(
blockParam
->
value
,
"default"
))
{
ad
->
driverId
=
ao_default_driver_id
();
ad
->
driverId
=
ao_default_driver_id
();
}
}
else
if
((
ad
->
driverId
=
else
if
((
ad
->
driverId
=
ao_driver_id
(
(
getConf
())[
CONF_AO_DRIVER
]
))
<
0
)
{
ao_driver_id
(
blockParam
->
value
))
<
0
)
{
ERROR
(
"
\"
%s
\"
is not a valid ao driver
\n
"
,
ERROR
(
"
\"
%s
\"
is not a valid ao driver
at line %i
\n
"
,
(
getConf
())[
CONF_AO_DRIVER
]
);
blockParam
->
value
,
blockParam
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
if
((
ai
=
ao_driver_info
(
ad
->
driverId
))
==
NULL
)
{
if
((
ai
=
ao_driver_info
(
ad
->
driverId
))
==
NULL
)
{
ERROR
(
"problems getting ao_driver_info
\n
"
);
ERROR
(
"problems getting driver info for device defined at "
"line %i
\n
"
,
param
->
line
);
ERROR
(
"you may not have permission to the audio device
\n
"
);
ERROR
(
"you may not have permission to the audio device
\n
"
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
dup
=
strdup
((
getConf
())[
CONF_AO_DRIVER_OPTIONS
]);
blockParam
=
getBlockParam
(
param
,
"options"
);
if
(
blockParam
)
{
dup
=
strdup
(
blockParam
->
value
);
}
else
dup
=
strdup
(
""
);
if
(
strlen
(
dup
))
{
if
(
strlen
(
dup
))
{
stk1
=
NULL
;
stk1
=
NULL
;
n1
=
strtok_r
(
dup
,
";"
,
&
stk1
);
n1
=
strtok_r
(
dup
,
";"
,
&
stk1
);
...
...
src/audioOutput_shout.c
View file @
58dbe4bb
...
@@ -88,7 +88,16 @@ static void freeShoutData(ShoutData * sd) {
...
@@ -88,7 +88,16 @@ static void freeShoutData(ShoutData * sd) {
free
(
sd
);
free
(
sd
);
}
}
static
int
shout_initDriver
(
AudioOutput
*
audioOutput
)
{
#define checkBlockParam(name) { \
blockParam = getBlockParam(param, name); \
if(!blockParam) { \
ERROR("no \"%s\" defined for shout device defined at line " \
"%i\n", name, param->line); \
exit(EXIT_FAILURE); \
} \
}
static
int
shout_initDriver
(
AudioOutput
*
audioOutput
,
ConfigParam
*
param
)
{
ShoutData
*
sd
;
ShoutData
*
sd
;
char
*
test
;
char
*
test
;
int
port
;
int
port
;
...
@@ -97,73 +106,50 @@ static int shout_initDriver(AudioOutput * audioOutput) {
...
@@ -97,73 +106,50 @@ static int shout_initDriver(AudioOutput * audioOutput) {
char
*
passwd
;
char
*
passwd
;
char
*
user
;
char
*
user
;
char
*
name
;
char
*
name
;
BlockParam
*
blockParam
;
if
(
!
getConf
()[
CONF_SHOUT_HOST
])
{
return
-
1
;
}
sd
=
newShoutData
();
sd
=
newShoutData
();
if
(
!
getConf
()[
CONF_SHOUT_MOUNT
])
{
checkBlockParam
(
"host"
);
ERROR
(
"shout host defined but not shout mount point
\n
"
);
host
=
blockParam
->
value
;
exit
(
EXIT_FAILURE
);
}
if
(
!
getConf
()[
CONF_SHOUT_PORT
])
{
ERROR
(
"shout host defined but not shout port
\n
"
);
exit
(
EXIT_FAILURE
);
}
if
(
!
getConf
()[
CONF_SHOUT_PASSWD
])
{
checkBlockParam
(
"mount"
);
ERROR
(
"shout host defined but not shout password
\n
"
);
mount
=
blockParam
->
value
;
exit
(
EXIT_FAILURE
);
}
if
(
!
getConf
()[
CONF_SHOUT_NAME
])
{
checkBlockParam
(
"port"
);
ERROR
(
"shout host defined but not shout name
\n
"
);
exit
(
EXIT_FAILURE
);
}
if
(
!
getConf
()[
CONF_SHOUT_USER
])
{
port
=
strtol
(
blockParam
->
value
,
&
test
,
10
);
ERROR
(
"shout host defined but not shout user
\n
"
);
exit
(
EXIT_FAILURE
);
}
if
(
!
getConf
()[
CONF_SHOUT_QUALITY
])
{
if
(
*
test
!=
'\0'
||
port
<=
0
)
{
ERROR
(
"shout host defined but not shout quality
\n
"
);
ERROR
(
"shout port
\"
%s
\"
is not a positive integer, line %i
\n
"
,
blockParam
->
value
,
blockParam
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
if
(
!
getConf
()[
CONF_SHOUT_FORMAT
])
{
checkBlockParam
(
"password"
);
ERROR
(
"shout host defined but not shout format
\n
"
);
passwd
=
blockParam
->
value
;
exit
(
EXIT_FAILURE
);
}
host
=
getConf
()[
CONF_SHOUT_HOST
];
checkBlockParam
(
"name"
);
passwd
=
getConf
()[
CONF_SHOUT_PASSWD
];
name
=
blockParam
->
value
;
user
=
getConf
()[
CONF_SHOUT_USER
];
mount
=
getConf
()[
CONF_SHOUT_MOUNT
];
name
=
getConf
()[
CONF_SHOUT_NAME
];
port
=
strtol
(
getConf
()[
CONF_SHOUT_PORT
],
&
test
,
10
);
checkBlockParam
(
"user"
);
user
=
blockParam
->
value
;
if
(
*
test
!=
'\0'
||
port
<=
0
)
{
checkBlockParam
(
"quality"
);
ERROR
(
"shout port
\"
%s
\"
is not a positive integer
\n
"
,
getConf
()[
CONF_SHOUT_PORT
]);
exit
(
EXIT_FAILURE
);
}
sd
->
quality
=
strtod
(
getConf
()[
CONF_SHOUT_QUALITY
]
,
&
test
);
sd
->
quality
=
strtod
(
blockParam
->
value
,
&
test
);
if
(
*
test
!=
'\0'
||
sd
->
quality
<
0
.
0
||
sd
->
quality
>
10
.
0
)
{
if
(
*
test
!=
'\0'
||
sd
->
quality
<
0
.
0
||
sd
->
quality
>
10
.
0
)
{
ERROR
(
"shout quality
\"
%s
\"
is not a number in the range "
ERROR
(
"shout quality
\"
%s
\"
is not a number in the range "
"0-10
\n
"
,
getConf
()[
CONF_SHOUT_QUALITY
]);
"0-10, line %i
\n
"
,
blockParam
->
value
,
blockParam
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
if
(
0
!=
parseAudioConfig
(
&
(
sd
->
outAudioFormat
),
checkBlockParam
(
"format"
);
getConf
()[
CONF_SHOUT_FORMAT
])
)
{
if
(
0
!=
parseAudioConfig
(
&
(
sd
->
outAudioFormat
),
blockParam
->
value
))
{
ERROR
(
"error parsing format at line %i
\n
"
,
blockParam
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
...
@@ -276,7 +262,7 @@ static int initEncoder(ShoutData * sd) {
...
@@ -276,7 +262,7 @@ static int initEncoder(ShoutData * sd) {
vorbis_info_init
(
&
(
sd
->
vi
));
vorbis_info_init
(
&
(
sd
->
vi
));
if
(
0
!=
vorbis_encode_init_vbr
(
&
(
sd
->
vi
),
sd
->
outAudioFormat
.
channels
,
if
(
0
!=
vorbis_encode_init_vbr
(
&
(
sd
->
vi
),
sd
->
outAudioFormat
.
channels
,
sd
->
outAudioFormat
.
sampleRate
,
sd
->
quality
)
)
sd
->
outAudioFormat
.
sampleRate
,
sd
->
quality
/
10
.
0
)
)
{
{
ERROR
(
"problem seting up vorbis encoder for shout
\n
"
);
ERROR
(
"problem seting up vorbis encoder for shout
\n
"
);
vorbis_info_clear
(
&
(
sd
->
vi
));
vorbis_info_clear
(
&
(
sd
->
vi
));
...
...
src/conf.c
View file @
58dbe4bb
...
@@ -22,8 +22,7 @@
...
@@ -22,8 +22,7 @@
#include "utils.h"
#include "utils.h"
#include "buffer2array.h"
#include "buffer2array.h"
#include "audio.h"
#include "list.h"
#include "volume.h"
#include <sys/param.h>
#include <sys/param.h>
#include <stdio.h>
#include <stdio.h>
...
@@ -36,232 +35,359 @@
...
@@ -36,232 +35,359 @@
#define MAX_STRING_SIZE MAXPATHLEN+80
#define MAX_STRING_SIZE MAXPATHLEN+80
#define CONF_COMMENT '#'
#define CONF_COMMENT '#'
#define CONF_BLOCK_BEGIN "{"
#define CONF_BLOCK_END "}"
#define CONF_NUMBER_OF_PARAMS 43
#define CONF_REPEATABLE_MASK 0x01
#define CONF_NUMBER_OF_PATHS 6
#define CONF_BLOCK_MASK 0x02
#define CONF_NUMBER_OF_REQUIRED 5
#define CONF_NUMBER_OF_ALLOW_CATS 1
#define CONF_CONNECTION_TIMEOUT_DEFAULT "60"
#define CONF_MAX_CONNECTIONS_DEFAULT "5"
#define CONF_MAX_PLAYLIST_LENGTH_DEFAULT "16384"
#define CONF_BUFFER_BEFORE_PLAY_DEFAULT "25%"
#define CONF_MAX_COMMAND_LIST_SIZE_DEFAULT "2048"
#define CONF_MAX_OUTPUT_BUFFER_SIZE_DEFAULT "2048"
#define CONF_AO_DRIVER_DEFAULT AUDIO_AO_DRIVER_DEFAULT
#define CONF_AO_DRIVER_OPTIONS_DEFAULT ""
#define CONF_SAVE_ABSOLUTE_PATHS_IN_PLAYLISTS_DEFAULT "no"
#define CONF_BIND_TO_ADDRESS_DEFAULT "any"
#define CONF_USER_DEFAULT ""
#define CONF_LOG_LEVEL_DEFAULT "default"
#define CONF_AUDIO_WRITE_SIZE_DEFAULT "1024"
#define CONF_BUFFER_SIZE_DEFAULT "2048"
#ifndef NO_OSS_MIXER
#define CONF_MIXER_TYPE_DEFAULT VOLUME_MIXER_OSS
#define CONF_MIXER_DEVICE_DEFAULT ""
#else
#ifdef HAVE_ALSA
#define CONF_MIXER_TYPE_DEFAULT VOLUME_MIXER_ALSA
#define CONF_MIXER_DEVICE_DEFAULT ""
#else
#define CONF_MIXER_TYPE_DEFAULT VOLUME_MIXER_SOFTWARE
#define CONF_MIXER_DEVICE_DEFAULT ""
#endif
#endif
static
char
*
conf_params
[
CONF_NUMBER_OF_PARAMS
];
void
initConf
()
{
typedef
struct
_configEntry
{
unsigned
char
mask
;
List
*
configParamList
;
}
ConfigEntry
;
static
List
*
configEntriesList
=
NULL
;
static
ConfigParam
*
newConfigParam
(
char
*
value
,
int
line
)
{
ConfigParam
*
ret
=
malloc
(
sizeof
(
ConfigParam
));
if
(
!
value
)
ret
->
value
=
NULL
;
else
ret
->
value
=
strdup
(
value
);
ret
->
line
=
line
;
ret
->
numberOfBlockParams
=
0
;
ret
->
blockParams
=
NULL
;
return
ret
;
}
static
void
freeConfigParam
(
ConfigParam
*
param
)
{
int
i
;
int
i
;
for
(
i
=
0
;
i
<
CONF_NUMBER_OF_PARAMS
;
i
++
)
conf_params
[
i
]
=
NULL
;
if
(
param
->
value
)
free
(
param
->
value
);
/* we don't specify these on the command line */
for
(
i
=
0
;
i
<
param
->
numberOfBlockParams
;
i
++
)
{
conf_params
[
CONF_CONNECTION_TIMEOUT
]
=
strdup
(
CONF_CONNECTION_TIMEOUT_DEFAULT
);
if
(
param
->
blockParams
[
i
].
name
)
{
conf_params
[
CONF_MIXER_DEVICE
]
=
strdup
(
CONF_MIXER_DEVICE_DEFAULT
);
free
(
param
->
blockParams
[
i
].
name
);
conf_params
[
CONF_MAX_CONNECTIONS
]
=
strdup
(
CONF_MAX_CONNECTIONS_DEFAULT
);
}
conf_params
[
CONF_MAX_PLAYLIST_LENGTH
]
=
strdup
(
CONF_MAX_PLAYLIST_LENGTH_DEFAULT
);
if
(
param
->
blockParams
[
i
].
value
)
{
conf_params
[
CONF_BUFFER_BEFORE_PLAY
]
=
strdup
(
CONF_BUFFER_BEFORE_PLAY_DEFAULT
);
free
(
param
->
blockParams
[
i
].
value
);
conf_params
[
CONF_MAX_COMMAND_LIST_SIZE
]
=
strdup
(
CONF_MAX_COMMAND_LIST_SIZE_DEFAULT
);
}
conf_params
[
CONF_MAX_OUTPUT_BUFFER_SIZE
]
=
strdup
(
CONF_MAX_OUTPUT_BUFFER_SIZE_DEFAULT
);
}
conf_params
[
CONF_AO_DRIVER
]
=
strdup
(
CONF_AO_DRIVER_DEFAULT
);
conf_params
[
CONF_AO_DRIVER_OPTIONS
]
=
strdup
(
CONF_AO_DRIVER_OPTIONS_DEFAULT
);
if
(
param
->
numberOfBlockParams
)
free
(
param
->
blockParams
);
conf_params
[
CONF_SAVE_ABSOLUTE_PATHS_IN_PLAYLISTS
]
=
strdup
(
CONF_SAVE_ABSOLUTE_PATHS_IN_PLAYLISTS_DEFAULT
);
conf_params
[
CONF_BIND_TO_ADDRESS
]
=
strdup
(
CONF_BIND_TO_ADDRESS_DEFAULT
);
free
(
param
);
conf_params
[
CONF_MIXER_TYPE
]
=
strdup
(
CONF_MIXER_TYPE_DEFAULT
);
}
conf_params
[
CONF_USER
]
=
strdup
(
CONF_USER_DEFAULT
);
conf_params
[
CONF_LOG_LEVEL
]
=
strdup
(
CONF_LOG_LEVEL_DEFAULT
);
ConfigEntry
*
newConfigEntry
(
int
repeatable
,
int
block
)
{
conf_params
[
CONF_AUDIO_WRITE_SIZE
]
=
strdup
(
CONF_AUDIO_WRITE_SIZE_DEFAULT
);
ConfigEntry
*
ret
=
malloc
(
sizeof
(
ConfigEntry
));
conf_params
[
CONF_BUFFER_SIZE
]
=
strdup
(
CONF_BUFFER_SIZE_DEFAULT
);
ret
->
mask
=
0
;
ret
->
configParamList
=
makeList
((
ListFreeDataFunc
*
)
freeConfigParam
);
if
(
repeatable
)
ret
->
mask
|=
CONF_REPEATABLE_MASK
;
if
(
block
)
ret
->
mask
|=
CONF_BLOCK_MASK
;
return
ret
;
}
void
freeConfigEntry
(
ConfigEntry
*
entry
)
{
freeList
(
entry
->
configParamList
);
free
(
entry
);
}
void
registerConfigParam
(
char
*
name
,
int
repeatable
,
int
block
)
{
ConfigEntry
*
entry
;
if
(
findInList
(
configEntriesList
,
name
,
NULL
))
{
ERROR
(
"config parameter
\"
%s
\"
already registered
\n
"
,
name
);
exit
(
EXIT_FAILURE
);
}
entry
=
newConfigEntry
(
repeatable
,
block
);
insertInList
(
configEntriesList
,
name
,
entry
);
}
void
initConf
()
{
configEntriesList
=
makeList
((
ListFreeDataFunc
*
)
freeConfigEntry
);
registerConfigParam
(
CONF_PORT
,
0
,
0
);
registerConfigParam
(
CONF_MUSIC_DIR
,
0
,
0
);
registerConfigParam
(
CONF_PLAYLIST_DIR
,
0
,
0
);
registerConfigParam
(
CONF_LOG_FILE
,
0
,
0
);
registerConfigParam
(
CONF_ERROR_FILE
,
0
,
0
);
registerConfigParam
(
CONF_CONN_TIMEOUT
,
0
,
0
);
registerConfigParam
(
CONF_MIXER_DEVICE
,
0
,
0
);
registerConfigParam
(
CONF_MAX_CONN
,
0
,
0
);
registerConfigParam
(
CONF_MAX_PLAYLIST_LENGTH
,
0
,
0
);
registerConfigParam
(
CONF_BUFFER_BEFORE_PLAY
,
0
,
0
);
registerConfigParam
(
CONF_MAX_COMMAND_LIST_SIZE
,
0
,
0
);
registerConfigParam
(
CONF_MAX_OUTPUT_BUFFER_SIZE
,
0
,
0
);
registerConfigParam
(
CONF_AUDIO_OUTPUT
,
1
,
1
);
registerConfigParam
(
CONF_SAVE_ABSOLUTE_PATHS
,
0
,
0
);
registerConfigParam
(
CONF_BIND_TO_ADDRESS
,
1
,
0
);
registerConfigParam
(
CONF_MIXER_TYPE
,
0
,
0
);
registerConfigParam
(
CONF_STATE_FILE
,
0
,
0
);
registerConfigParam
(
CONF_USER
,
0
,
0
);
registerConfigParam
(
CONF_DB_FILE
,
0
,
0
);
registerConfigParam
(
CONF_LOG_LEVEL
,
0
,
0
);
registerConfigParam
(
CONF_MIXER_CONTROL
,
0
,
0
);
registerConfigParam
(
CONF_AUDIO_WRITE_SIZE
,
0
,
0
);
registerConfigParam
(
CONF_FS_CHARSET
,
0
,
0
);
registerConfigParam
(
CONF_PASSWORD
,
1
,
0
);
registerConfigParam
(
CONF_DEFAULT_PERMS
,
0
,
0
);
registerConfigParam
(
CONF_AUDIO_BUFFER_SIZE
,
0
,
0
);
registerConfigParam
(
CONF_REPLAYGAIN
,
0
,
0
);
registerConfigParam
(
CONF_AUDIO_OUTPUT_FORMAT
,
0
,
0
);
registerConfigParam
(
CONF_HTTP_PROXY_HOST
,
0
,
0
);
registerConfigParam
(
CONF_HTTP_PROXY_PORT
,
0
,
0
);
registerConfigParam
(
CONF_HTTP_PROXY_USER
,
0
,
0
);
registerConfigParam
(
CONF_HTTP_PROXY_PASSWORD
,
0
,
0
);
registerConfigParam
(
CONF_REPLAYGAIN_PREAMP
,
0
,
0
);
registerConfigParam
(
CONF_ID3V1_ENCODING
,
0
,
0
);
}
static
void
addBlockParam
(
ConfigParam
*
param
,
char
*
name
,
char
*
value
,
int
line
)
{
param
->
numberOfBlockParams
++
;
param
->
blockParams
=
realloc
(
param
->
blockParams
,
param
->
numberOfBlockParams
*
sizeof
(
BlockParam
));
param
->
blockParams
[
param
->
numberOfBlockParams
-
1
].
name
=
strdup
(
name
);
param
->
blockParams
[
param
->
numberOfBlockParams
-
1
].
value
=
strdup
(
value
);
param
->
blockParams
[
param
->
numberOfBlockParams
-
1
].
line
=
line
;
}
}
char
**
readConf
(
char
*
file
)
{
static
ConfigParam
*
readConfigBlock
(
FILE
*
fp
,
int
*
count
,
char
*
string
)
{
char
*
conf_strings
[
CONF_NUMBER_OF_PARAMS
]
=
{
ConfigParam
*
ret
=
newConfigParam
(
NULL
,
*
count
);
"port"
,
"music_directory"
,
char
**
array
;
"playlist_directory"
,
int
i
;
"log_file"
,
int
numberOfArgs
;
"error_file"
,
int
argsMinusComment
;
"connection_timeout"
,
"mixer_device"
,
while
(
myFgets
(
string
,
MAX_STRING_SIZE
,
fp
))
{
"max_connections"
,
(
*
count
)
++
;
"max_playlist_length"
,
"buffer_before_play"
,
numberOfArgs
=
buffer2array
(
string
,
&
array
);
"max_command_list_size"
,
"max_output_buffer_size"
,
for
(
i
=
0
;
i
<
numberOfArgs
;
i
++
)
{
"ao_driver"
,
if
(
array
[
i
][
0
]
==
CONF_COMMENT
)
break
;
"ao_driver_options"
,
}
"save_absolute_paths_in_playlists"
,
"bind_to_address"
,
argsMinusComment
=
i
;
"mixer_type"
,
"state_file"
,
if
(
0
==
argsMinusComment
)
continue
;
"user"
,
"db_file"
,
if
(
1
==
argsMinusComment
&&
"log_level"
,
0
==
strcmp
(
array
[
0
],
CONF_BLOCK_END
))
"mixer_control"
,
{
"audio_write_size"
,
break
;
"filesystem_charset"
,
}
"password"
,
"default_permissions"
,
if
(
2
!=
argsMinusComment
)
{
"audio_buffer_size"
,
ERROR
(
"improperly formated config file at line %i:"
"replaygain"
,
" %s
\n
"
,
count
,
string
);
"audio_output_format"
,
exit
(
EXIT_FAILURE
);
"http_proxy_host"
,
}
"http_proxy_port"
,
"http_proxy_user"
,
if
(
0
==
strcmp
(
array
[
0
],
CONF_BLOCK_BEGIN
)
||
"http_proxy_password"
,
0
==
strcmp
(
array
[
1
],
CONF_BLOCK_BEGIN
)
||
"replaygain_preamp"
,
0
==
strcmp
(
array
[
0
],
CONF_BLOCK_END
)
||
"shout_host"
,
0
==
strcmp
(
array
[
1
],
CONF_BLOCK_END
))
"shout_port"
,
{
"shout_password"
,
ERROR
(
"improperly formated config file at line %i:"
"shout_mount"
,
" %s
\n
"
,
count
,
string
);
"shout_name"
,
ERROR
(
"in block begging at line %i
\n
"
,
ret
->
line
);
"shout_user"
,
exit
(
EXIT_FAILURE
);
"shout_quality"
,
}
"id3v1_encoding"
,
"shout_format"
addBlockParam
(
ret
,
array
[
0
],
array
[
1
],
*
count
);
};
freeArgArray
(
array
,
numberOfArgs
);
int
conf_absolutePaths
[
CONF_NUMBER_OF_PATHS
]
=
{
}
CONF_MUSIC_DIRECTORY
,
CONF_PLAYLIST_DIRECTORY
,
return
ret
;
CONF_LOG_FILE
,
}
CONF_ERROR_FILE
,
CONF_STATE_FILE
,
CONF_DB_FILE
};
int
conf_required
[
CONF_NUMBER_OF_REQUIRED
]
=
{
CONF_MUSIC_DIRECTORY
,
CONF_PLAYLIST_DIRECTORY
,
CONF_LOG_FILE
,
CONF_ERROR_FILE
,
CONF_PORT
};
short
conf_allowCat
[
CONF_NUMBER_OF_ALLOW_CATS
]
=
{
CONF_PASSWORD
};
void
readConf
(
char
*
file
)
{
FILE
*
fp
;
FILE
*
fp
;
char
string
[
MAX_STRING_SIZE
+
1
];
char
string
[
MAX_STRING_SIZE
+
1
];
char
**
array
;
char
**
array
;
int
i
;
int
i
;
int
numberOfArgs
;
int
numberOfArgs
;
short
allowCat
[
CONF_NUMBER_OF_PARAMS
]
;
int
argsMinusComment
;
int
count
=
0
;
int
count
=
0
;
ConfigEntry
*
entry
;
for
(
i
=
0
;
i
<
CONF_NUMBER_OF_PARAMS
;
i
++
)
allowCat
[
i
]
=
0
;
void
*
voidPtr
;
ConfigParam
*
param
;
for
(
i
=
0
;
i
<
CONF_NUMBER_OF_ALLOW_CATS
;
i
++
)
allowCat
[
conf_allowCat
[
i
]]
=
1
;
if
(
!
(
fp
=
fopen
(
file
,
"r"
)))
{
if
(
!
(
fp
=
fopen
(
file
,
"r"
)))
{
ERROR
(
"problems opening file %s for reading
\n
"
,
file
);
ERROR
(
"problems opening file %s for reading
\n
"
,
file
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
while
(
myFgets
(
string
,
sizeof
(
string
),
fp
))
{
while
(
myFgets
(
string
,
MAX_STRING_SIZE
,
fp
))
{
count
++
;
count
++
;
if
(
string
[
0
]
==
CONF_COMMENT
)
continue
;
numberOfArgs
=
buffer2array
(
string
,
&
array
);
numberOfArgs
=
buffer2array
(
string
,
&
array
);
if
(
numberOfArgs
==
0
)
continue
;
for
(
i
=
0
;
i
<
numberOfArgs
;
i
++
)
{
if
(
2
!=
numberOfArgs
)
{
if
(
array
[
i
][
0
]
==
CONF_COMMENT
)
break
;
ERROR
(
"improperly formated config file at line %i: %s
\n
"
,
count
,
string
);
}
argsMinusComment
=
i
;
if
(
0
==
argsMinusComment
)
continue
;
if
(
2
!=
argsMinusComment
)
{
ERROR
(
"improperly formated config file at line %i:"
" %s
\n
"
,
count
,
string
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
i
=
0
;
while
(
i
<
CONF_NUMBER_OF_PARAMS
&&
0
!=
strcmp
(
conf_strings
[
i
],
array
[
0
]))
i
++
;
if
(
!
findInList
(
configEntriesList
,
array
[
0
],
&
voidPtr
))
{
if
(
i
>=
CONF_NUMBER_OF_PARAMS
)
{
ERROR
(
"unrecognized paramater in config file at line "
ERROR
(
"unrecognized paramater in conf at line %i: %s
\n
"
,
count
,
string
);
"%i: %s
\n
"
,
count
,
string
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
if
(
conf_params
[
i
]
!=
NULL
)
{
entry
=
(
ConfigEntry
*
)
voidPtr
;
if
(
allowCat
[
i
])
{
conf_params
[
i
]
=
realloc
(
conf_params
[
i
],
if
(
!
(
entry
->
mask
&
CONF_REPEATABLE_MASK
)
&&
strlen
(
conf_params
[
i
])
+
entry
->
configParamList
->
numberOfNodes
)
strlen
(
CONF_CAT_CHAR
)
+
{
strlen
(
array
[
1
])
+
1
);
param
=
entry
->
configParamList
->
firstNode
->
data
;
strcat
(
conf_params
[
i
],
CONF_CAT_CHAR
);
ERROR
(
"config paramter
\"
%s
\"
is first defined on line "
strcat
(
conf_params
[
i
],
array
[
1
]);
"%i and redefined on line %i
\n
"
,
array
[
0
],
param
->
line
,
count
);
exit
(
EXIT_FAILURE
);
}
}
else
{
free
(
conf_params
[
i
]);
if
(
entry
->
mask
&
CONF_BLOCK_MASK
)
{
conf_params
[
i
]
=
strdup
(
array
[
1
]);
if
(
0
!=
strcmp
(
array
[
1
],
CONF_BLOCK_BEGIN
))
{
ERROR
(
"improperly formated config file at "
"line %i: %s
\n
"
,
count
,
string
);
exit
(
EXIT_FAILURE
);
}
}
param
=
readConfigBlock
(
fp
,
&
count
,
string
);
}
}
else
conf_params
[
i
]
=
strdup
(
array
[
1
]);
else
param
=
newConfigParam
(
array
[
1
],
count
);
free
(
array
[
0
]);
free
(
array
[
1
]);
insertInListWithoutKey
(
entry
->
configParamList
,
param
);
free
(
array
);
freeArgArray
(
array
,
numberOfArgs
);
}
}
}
ConfigParam
*
getNextConfigParam
(
char
*
name
,
ConfigParam
*
last
)
{
void
*
voidPtr
;
ConfigEntry
*
entry
;
ListNode
*
node
;
ConfigParam
*
param
;
if
(
!
findInList
(
configEntriesList
,
name
,
&
voidPtr
))
return
NULL
;
entry
=
voidPtr
;
node
=
entry
->
configParamList
->
firstNode
;
if
(
last
)
{
while
(
node
!=
NULL
)
{
param
=
node
->
data
;
node
=
node
->
nextNode
;
if
(
param
==
last
)
break
;
}
}
if
(
node
==
NULL
)
return
NULL
;
param
=
node
->
data
;
return
param
;
}
fclose
(
fp
);
char
*
getConfigParamValue
(
char
*
name
)
{
ConfigParam
*
param
=
getConfigParam
(
name
);
for
(
i
=
0
;
i
<
CONF_NUMBER_OF_REQUIRED
;
i
++
)
{
if
(
!
param
)
return
NULL
;
if
(
conf_params
[
conf_required
[
i
]]
==
NULL
)
{
ERROR
(
"%s is unassigned in conf file
\n
"
,
return
param
->
value
;
conf_strings
[
conf_required
[
i
]]);
}
char
*
forceAndGetConfigParamValue
(
char
*
name
)
{
ConfigParam
*
param
=
getConfigParam
(
name
);
if
(
!
param
)
{
ERROR
(
"
\"
%s
\"
not found in config file
\n
"
,
name
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
return
param
->
value
;
}
BlockParam
*
getBlockParam
(
ConfigParam
*
param
,
char
*
name
)
{
BlockParam
*
ret
=
NULL
;
int
i
;
for
(
i
=
0
;
i
<
param
->
numberOfBlockParams
;
i
++
)
{
if
(
0
==
strcmp
(
name
,
param
->
blockParams
[
i
].
name
))
{
if
(
ret
)
{
ERROR
(
"
\"
%s
\"
first defined on line %i, and "
"redefined on line %i
\n
"
,
name
,
ret
->
line
,
param
->
blockParams
[
i
].
line
);
}
ret
=
param
->
blockParams
+
i
;
}
}
}
for
(
i
=
0
;
i
<
CONF_NUMBER_OF_PATHS
;
i
++
)
{
return
ret
;
if
(
conf_params
[
conf_absolutePaths
[
i
]]
&&
}
conf_params
[
conf_absolutePaths
[
i
]][
0
]
!=
'/'
&&
conf_params
[
conf_absolutePaths
[
i
]][
0
]
!=
'~'
)
char
*
parseConfigFilePath
(
char
*
name
,
int
force
)
{
{
ConfigParam
*
param
=
getConfigParam
(
name
);
ERROR
(
"
\"
%s
\"
is not an absolute path
\n
"
,
char
*
path
;
conf_params
[
conf_absolutePaths
[
i
]]);
if
(
!
param
&&
force
)
{
ERROR
(
"config parameter
\"
%s
\"
not found
\n
"
,
name
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
/* Parse ~ in path */
else
if
(
conf_params
[
conf_absolutePaths
[
i
]]
&&
if
(
!
param
)
return
NULL
;
conf_params
[
conf_absolutePaths
[
i
]][
0
]
==
'~'
)
{
path
=
param
->
value
;
if
(
path
[
0
]
!=
'/'
&&
path
[
0
]
!=
'~'
)
{
ERROR
(
"
\"
%s
\"
is not an absolute path at line %i
\n
"
,
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
}
// Parse ~ in path
else
if
(
path
[
0
]
==
'~'
)
{
struct
passwd
*
pwd
=
NULL
;
struct
passwd
*
pwd
=
NULL
;
char
*
p
ath
;
char
*
newP
ath
;
int
pos
=
1
;
int
pos
=
1
;
if
(
conf_params
[
conf_absolutePaths
[
i
]][
1
]
==
'/'
||
if
(
path
[
1
]
==
'/'
||
path
[
1
]
==
'\0'
)
{
conf_params
[
conf_absolutePaths
[
i
]][
1
]
==
'\0'
)
ConfigParam
*
userParam
=
getConfigParam
(
CONF_USER
);
{
if
(
conf_params
[
CONF_USER
]
&&
if
(
userParam
)
{
strlen
(
conf_params
[
CONF_USER
]))
pwd
=
getpwnam
(
userParam
->
value
);
{
pwd
=
getpwnam
(
conf_params
[
CONF_USER
]);
if
(
!
pwd
)
{
if
(
!
pwd
)
{
ERROR
(
"no such user: %s
\n
"
,
ERROR
(
"no such user %s at line %i
\n
"
,
conf_params
[
CONF_USER
]);
userParam
->
value
,
userParam
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
}
}
else
{
else
{
uid_t
uid
=
geteuid
();
uid_t
uid
=
geteuid
();
if
((
pwd
=
getpwuid
(
uid
))
==
NULL
)
{
if
((
pwd
=
getpwuid
(
uid
))
==
NULL
)
{
ERROR
(
"problems getting passwd "
ERROR
(
"problems getting passwd entry "
"entry "
"for current user
\n
"
);
"for current user
\n
"
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
...
@@ -269,36 +395,24 @@ char ** readConf(char * file) {
...
@@ -269,36 +395,24 @@ char ** readConf(char * file) {
}
}
else
{
else
{
int
foundSlash
=
0
;
int
foundSlash
=
0
;
char
*
ch
=
&
(
char
*
ch
=
path
+
1
;
conf_params
[
conf_absolutePaths
[
i
]][
1
]);
for
(;
*
ch
!=
'\0'
&&
*
ch
!=
'/'
;
ch
++
);
for
(;
*
ch
!=
'\0'
&&
*
ch
!=
'/'
;
ch
++
);
if
(
*
ch
==
'/'
)
foundSlash
=
1
;
if
(
*
ch
==
'/'
)
foundSlash
=
1
;
*
ch
=
'\0'
;
*
ch
=
'\0'
;
pos
+=
ch
-
pos
+=
ch
-
path
+
1
;
&
(
conf_params
[
if
((
pwd
=
getpwnam
(
path
+
1
))
==
NULL
)
{
conf_absolutePaths
[
i
]][
1
]);
ERROR
(
"user
\"
%s
\"
not found at line %i
\n
"
,
if
((
pwd
=
getpwnam
(
&
(
conf_params
[
path
+
1
,
param
->
line
);
conf_absolutePaths
[
i
]][
1
])))
==
NULL
)
{
ERROR
(
"user
\"
%s
\"
not found
\n
"
,
&
(
conf_params
[
conf_absolutePaths
[
i
]][
1
]));
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
if
(
foundSlash
)
*
ch
=
'/'
;
if
(
foundSlash
)
*
ch
=
'/'
;
}
}
path
=
malloc
(
strlen
(
pwd
->
pw_dir
)
+
strlen
(
newPath
=
malloc
(
strlen
(
pwd
->
pw_dir
)
+
strlen
(
path
+
pos
)
+
1
);
&
(
conf_params
[
conf_absolutePaths
[
i
]][
pos
]))
+
1
);
strcpy
(
newPath
,
pwd
->
pw_dir
);
strcpy
(
path
,
pwd
->
pw_dir
);
strcat
(
newPath
,
path
+
pos
);
strcat
(
path
,
&
(
conf_params
[
conf_absolutePaths
[
i
]][
pos
]));
free
(
param
->
value
);
free
(
conf_params
[
conf_absolutePaths
[
i
]]);
param
->
value
=
newPath
;
conf_params
[
conf_absolutePaths
[
i
]]
=
path
;
}
}
}
return
conf_params
;
}
char
**
getConf
()
{
return
param
->
value
;
return
conf_params
;
}
}
src/conf.h
View file @
58dbe4bb
...
@@ -21,59 +21,72 @@
...
@@ -21,59 +21,72 @@
#include "../config.h"
#include "../config.h"
#define CONF_PORT 0
#define CONF_PORT "port"
#define CONF_MUSIC_DIRECTORY 1
#define CONF_MUSIC_DIR "music_directory"
#define CONF_PLAYLIST_DIRECTORY 2
#define CONF_PLAYLIST_DIR "playlist_directory"
#define CONF_LOG_FILE 3
#define CONF_LOG_FILE "log_file"
#define CONF_ERROR_FILE 4
#define CONF_ERROR_FILE "error_file"
#define CONF_CONNECTION_TIMEOUT 5
#define CONF_CONN_TIMEOUT "connection_timeout"
#define CONF_MIXER_DEVICE 6
#define CONF_MIXER_DEVICE "mixer_device"
#define CONF_MAX_CONNECTIONS 7
#define CONF_MAX_CONN "max_connections"
#define CONF_MAX_PLAYLIST_LENGTH 8
#define CONF_MAX_PLAYLIST_LENGTH "max_playlist_length"
#define CONF_BUFFER_BEFORE_PLAY 9
#define CONF_BUFFER_BEFORE_PLAY "buffer_before_play"
#define CONF_MAX_COMMAND_LIST_SIZE 10
#define CONF_MAX_COMMAND_LIST_SIZE "max_command_list_size"
#define CONF_MAX_OUTPUT_BUFFER_SIZE 11
#define CONF_MAX_OUTPUT_BUFFER_SIZE "max_output_buffer_size"
#define CONF_AO_DRIVER 12
#define CONF_AUDIO_OUTPUT "audio_output"
#define CONF_AO_DRIVER_OPTIONS 13
#define CONF_SAVE_ABSOLUTE_PATHS "save_absolute_paths_in_playlists"
#define CONF_SAVE_ABSOLUTE_PATHS_IN_PLAYLISTS 14
#define CONF_BIND_TO_ADDRESS "bind_to_address"
#define CONF_BIND_TO_ADDRESS 15
#define CONF_MIXER_TYPE "mixer_type"
#define CONF_MIXER_TYPE 16
#define CONF_STATE_FILE "state_file"
#define CONF_STATE_FILE 17
#define CONF_USER "user"
#define CONF_USER 18
#define CONF_DB_FILE "db_file"
#define CONF_DB_FILE 19
#define CONF_LOG_LEVEL "log_level"
#define CONF_LOG_LEVEL 20
#define CONF_MIXER_CONTROL "mixer_control"
#define CONF_MIXER_CONTROL 21
#define CONF_AUDIO_WRITE_SIZE "audio_write_size"
#define CONF_AUDIO_WRITE_SIZE 22
#define CONF_FS_CHARSET "filesystem_charset"
#define CONF_FS_CHARSET 23
#define CONF_PASSWORD "password"
#define CONF_PASSWORD 24
#define CONF_DEFAULT_PERMS "default_permissions"
#define CONF_DEFAULT_PERMISSIONS 25
#define CONF_AUDIO_BUFFER_SIZE "audio_buffer_size"
#define CONF_BUFFER_SIZE 26
#define CONF_REPLAYGAIN "replaygain"
#define CONF_REPLAYGAIN 27
#define CONF_AUDIO_OUTPUT_FORMAT "audio_output_format"
#define CONF_AUDIO_OUTPUT_FORMAT 28
#define CONF_HTTP_PROXY_HOST "http_proxy_host"
#define CONF_HTTP_PROXY_HOST 29
#define CONF_HTTP_PROXY_PORT "http_proxy_port"
#define CONF_HTTP_PROXY_PORT 30
#define CONF_HTTP_PROXY_USER "http_proxy_user"
#define CONF_HTTP_PROXY_USER 31
#define CONF_HTTP_PROXY_PASSWORD "http_proxy_password"
#define CONF_HTTP_PROXY_PASSWORD 32
#define CONF_REPLAYGAIN_PREAMP "replaygain_preamp"
#define CONF_REPLAYGAIN_PREAMP 33
#define CONF_ID3V1_ENCODING "id3v1_encoding"
#define CONF_SHOUT_HOST 34
#define CONF_SHOUT_PORT 35
#define CONF_SHOUT_PASSWD 36
#define CONF_SHOUT_MOUNT 37
#define CONF_SHOUT_NAME 38
#define CONF_SHOUT_USER 39
#define CONF_SHOUT_QUALITY 40
#define CONF_ID3V1_ENCODING 41
#define CONF_SHOUT_FORMAT 42
#define CONF_CAT_CHAR "\n"
typedef
struct
_BlockParam
{
char
*
name
;
char
*
value
;
int
line
;
}
BlockParam
;
/* do not free the return value, it is a static variable */
typedef
struct
_ConfigParam
{
char
**
readConf
(
char
*
file
);
char
*
value
;
unsigned
int
line
;
char
**
getConf
();
BlockParam
*
blockParams
;
int
numberOfBlockParams
;
}
ConfigParam
;
void
initConf
();
void
initConf
();
void
writeConf
(
char
*
file
);
void
readConf
(
char
*
file
);
/* don't free the returned value
set _last_ to NULL to get first entry */
ConfigParam
*
getNextConfigParam
(
char
*
name
,
ConfigParam
*
last
);
#define getConfigParam(name) getNextConfigParam(name, NULL)
char
*
getConfigParamValue
(
char
*
name
);
char
*
forceAndGetConfigParamValue
(
char
*
name
);
void
registerConfigParam
(
char
*
name
,
int
repeats
,
int
block
);
BlockParam
*
getBlockParam
(
ConfigParam
*
param
,
char
*
name
);
char
*
parseConfigFilePath
(
char
*
name
,
int
force
);
#endif
#endif
src/directory.c
View file @
58dbe4bb
...
@@ -1053,7 +1053,8 @@ int readDirectoryDB() {
...
@@ -1053,7 +1053,8 @@ int readDirectoryDB() {
fsCharset
=
&
(
buffer
[
strlen
(
fsCharset
=
&
(
buffer
[
strlen
(
DIRECTORY_FS_CHARSET
)]);
DIRECTORY_FS_CHARSET
)]);
if
((
tempCharset
=
if
((
tempCharset
=
getConf
()[
CONF_FS_CHARSET
])
&&
getConfigParamValue
(
CONF_FS_CHARSET
))
&&
strcmp
(
fsCharset
,
tempCharset
))
strcmp
(
fsCharset
,
tempCharset
))
{
{
WARNING
(
"Using
\"
%s
\"
for the "
WARNING
(
"Using
\"
%s
\"
for the "
...
...
src/inputStream_http.c
View file @
58dbe4bb
...
@@ -47,6 +47,11 @@
...
@@ -47,6 +47,11 @@
#define HTTP_REDIRECT_MAX 10
#define HTTP_REDIRECT_MAX 10
static
char
*
proxyHost
=
NULL
;
static
int
proxyPort
=
0
;
static
char
*
proxyUser
=
NULL
;
static
char
*
proxyPassword
=
NULL
;
typedef
struct
_InputStreemHTTPData
{
typedef
struct
_InputStreemHTTPData
{
char
*
host
;
char
*
host
;
char
*
path
;
char
*
path
;
...
@@ -59,57 +64,73 @@ typedef struct _InputStreemHTTPData {
...
@@ -59,57 +64,73 @@ typedef struct _InputStreemHTTPData {
int
icyMetaint
;
int
icyMetaint
;
int
prebuffer
;
int
prebuffer
;
int
icyOffset
;
int
icyOffset
;
char
*
proxyHost
;
int
proxyPort
;
char
*
proxyAuth
;
char
*
proxyAuth
;
char
*
httpAuth
;
char
*
httpAuth
;
}
InputStreamHTTPData
;
}
InputStreamHTTPData
;
void
inputStream_initHttp
()
{
void
inputStream_initHttp
()
{
if
(
getConf
()[
CONF_HTTP_PROXY_HOST
])
{
ConfigParam
*
param
=
getConfigParam
(
CONF_HTTP_PROXY_HOST
);
char
*
portStr
=
getConf
()[
CONF_HTTP_PROXY_PORT
];
int
port
=
0
;
char
*
test
;
char
*
test
;
if
(
!
portStr
)
{
if
(
param
)
{
ERROR
(
"http_proxy_host specified but not the http_"
proxyHost
=
param
->
value
;
"proxy_port
\n
"
);
param
=
getConfigParam
(
CONF_HTTP_PROXY_PORT
);
if
(
!
param
)
{
ERROR
(
"%s specified but not %s"
,
CONF_HTTP_PROXY_HOST
,
CONF_HTTP_PROXY_PORT
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
port
=
strtol
(
portStr
,
&
test
,
10
);
proxyPort
=
strtol
(
param
->
value
,
&
test
,
10
);
if
(
port
<=
0
||
*
test
!=
'\0'
)
{
if
(
proxyPort
<=
0
||
*
test
!=
'\0'
)
{
ERROR
(
"http_proxy_port
\"
%s
\"
is not a positive integer"
ERROR
(
"%s
\"
%s
\"
is not a positive integer, line %i
\n
"
"
\n
"
,
portStr
);
CONF_HTTP_PROXY_PORT
,
param
->
value
,
param
->
line
);
}
}
if
(
getConf
()[
CONF_HTTP_PROXY_USER
]
&&
param
=
getConfigParam
(
CONF_HTTP_PROXY_USER
);
!
getConf
()[
CONF_HTTP_PROXY_PASSWORD
])
{
if
(
param
)
{
ERROR
(
"http_proxy_user specified, but not http_proxy_"
proxyUser
=
param
->
value
;
"password
\n
"
);
param
=
getConfigParam
(
CONF_HTTP_PROXY_PASSWORD
);
if
(
!
param
)
{
ERROR
(
"%s specifid but not %s
\n
"
,
CONF_HTTP_PROXY_USER
,
CONF_HTTP_PROXY_PASSWORD
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
if
(
getConf
()[
CONF_HTTP_PROXY_PASSWORD
]
&&
proxyPassword
=
param
->
value
;
!
getConf
()[
CONF_HTTP_PROXY_USER
])
}
{
ERROR
(
"http proxy password specified, but not http "
param
=
getConfigParam
(
CONF_HTTP_PROXY_PASSWORD
);
"proxy user
\n
"
);
if
(
param
)
{
ERROR
(
"%s specifid but not %s
\n
"
,
CONF_HTTP_PROXY_PASSWORD
,
CONF_HTTP_PROXY_USER
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
}
}
else
if
(
getConf
()[
CONF_HTTP_PROXY_PORT
])
{
else
if
((
param
=
getConfigParam
(
CONF_HTTP_PROXY_PORT
)))
{
ERROR
(
"http_proxy_port specified but not http_proxy_host
\n
"
);
ERROR
(
"%s specified but not %s, line %i
\n
"
,
CONF_HTTP_PROXY_PORT
,
CONF_HTTP_PROXY_HOST
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
else
if
(
getConf
()[
CONF_HTTP_PROXY_USER
])
{
else
if
((
param
=
getConfigParam
(
CONF_HTTP_PROXY_USER
)))
{
ERROR
(
"http_proxy_user specified but not http_proxy_host
\n
"
);
ERROR
(
"%s specified but not %s, line %i
\n
"
,
CONF_HTTP_PROXY_USER
,
CONF_HTTP_PROXY_HOST
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
else
if
(
getConf
()[
CONF_HTTP_PROXY_PASSWORD
])
{
else
if
((
param
=
getConfigParam
(
CONF_HTTP_PROXY_PASSWORD
)))
{
ERROR
(
"http_proxy_password specified but not http_proxy_host"
ERROR
(
"%s specified but not %s, line %i
\n
"
,
"
\n
"
);
CONF_HTTP_PROXY_PASSWORD
,
CONF_HTTP_PROXY_HOST
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
}
}
...
@@ -188,19 +209,10 @@ static char * authString(char * header, char * user, char * password) {
...
@@ -188,19 +209,10 @@ static char * authString(char * header, char * user, char * password) {
static
InputStreamHTTPData
*
newInputStreamHTTPData
()
{
static
InputStreamHTTPData
*
newInputStreamHTTPData
()
{
InputStreamHTTPData
*
ret
=
malloc
(
sizeof
(
InputStreamHTTPData
));
InputStreamHTTPData
*
ret
=
malloc
(
sizeof
(
InputStreamHTTPData
));
if
(
getConf
()[
CONF_HTTP_PROXY_HOST
])
{
if
(
proxyHost
)
{
ret
->
proxyHost
=
getConf
()[
CONF_HTTP_PROXY_HOST
];
ret
->
proxyAuth
=
proxyAuthString
(
proxyUser
,
proxyPassword
);
DEBUG
(
__FILE__
": Proxy host %s
\n
"
,
ret
->
proxyHost
);
ret
->
proxyPort
=
atoi
(
getConf
()[
CONF_HTTP_PROXY_PORT
]);
DEBUG
(
__FILE__
": Proxy port %i
\n
"
,
ret
->
proxyPort
);
ret
->
proxyAuth
=
proxyAuthString
(
getConf
()[
CONF_HTTP_PROXY_USER
],
getConf
()[
CONF_HTTP_PROXY_PASSWORD
]);
}
else
{
ret
->
proxyHost
=
NULL
;
ret
->
proxyAuth
=
NULL
;
}
}
else
ret
->
proxyAuth
=
NULL
;
ret
->
httpAuth
=
NULL
;
ret
->
httpAuth
=
NULL
;
ret
->
host
=
NULL
;
ret
->
host
=
NULL
;
...
@@ -299,7 +311,7 @@ static int parseUrl(InputStreamHTTPData * data, char * url) {
...
@@ -299,7 +311,7 @@ static int parseUrl(InputStreamHTTPData * data, char * url) {
}
}
/* fetch the path */
/* fetch the path */
if
(
data
->
proxyHost
)
data
->
path
=
strdup
(
url
);
if
(
proxyHost
)
data
->
path
=
strdup
(
url
);
else
data
->
path
=
strdup
(
slash
?
slash
:
"/"
);
else
data
->
path
=
strdup
(
slash
?
slash
:
"/"
);
return
0
;
return
0
;
...
@@ -319,9 +331,9 @@ static int initHTTPConnection(InputStream * inStream) {
...
@@ -319,9 +331,9 @@ static int initHTTPConnection(InputStream * inStream) {
struct
sockaddr_in6
sin6
;
struct
sockaddr_in6
sin6
;
#endif
#endif
if
(
data
->
proxyHost
)
{
if
(
proxyHost
)
{
connHost
=
data
->
proxyHost
;
connHost
=
proxyHost
;
connPort
=
data
->
proxyPort
;
connPort
=
proxyPort
;
}
}
else
{
else
{
connHost
=
data
->
host
;
connHost
=
data
->
host
;
...
...
src/interface.c
View file @
58dbe4bb
...
@@ -48,11 +48,17 @@
...
@@ -48,11 +48,17 @@
#define INTERFACE_LIST_OK_MODE_BEGIN "command_list_ok_begin"
#define INTERFACE_LIST_OK_MODE_BEGIN "command_list_ok_begin"
#define INTERFACE_LIST_MODE_END "command_list_end"
#define INTERFACE_LIST_MODE_END "command_list_end"
#define INTERFACE_DEFAULT_OUT_BUFFER_SIZE 4096
#define INTERFACE_DEFAULT_OUT_BUFFER_SIZE 4096
#define INTERFACE_TIMEOUT_DEFAULT 60
int
interface_max_connections
=
0
;
#define INTERFACE_MAX_CONNECTIONS_DEFAULT 10
int
interface_timeout
;
#define INTERFACE_MAX_COMMAND_LIST_DEFAULT (2048*1024)
unsigned
long
long
interface_max_command_list_size
;
#define INTERFACE_MAX_OUTPUT_BUFFER_SIZE_DEFAULT (2048*1024)
unsigned
long
long
interface_max_output_buffer_size
;
static
int
interface_max_connections
=
INTERFACE_MAX_CONNECTIONS_DEFAULT
;
static
int
interface_timeout
=
INTERFACE_TIMEOUT_DEFAULT
;
static
size_t
interface_max_command_list_size
=
INTERFACE_MAX_COMMAND_LIST_DEFAULT
;
static
size_t
interface_max_output_buffer_size
=
INTERFACE_MAX_OUTPUT_BUFFER_SIZE_DEFAULT
;
typedef
struct
_Interface
{
typedef
struct
_Interface
{
char
buffer
[
INTERFACE_MAX_BUFFER_LENGTH
+
2
];
char
buffer
[
INTERFACE_MAX_BUFFER_LENGTH
+
2
];
...
@@ -420,33 +426,58 @@ int doIOForInterfaces() {
...
@@ -420,33 +426,58 @@ int doIOForInterfaces() {
void
initInterfaces
()
{
void
initInterfaces
()
{
int
i
;
int
i
;
char
*
test
;
char
*
test
;
ConfigParam
*
param
;
param
=
getConfigParam
(
CONF_CONN_TIMEOUT
);
interface_timeout
=
strtol
((
getConf
())[
CONF_CONNECTION_TIMEOUT
],
&
test
,
10
);
if
(
param
)
{
interface_timeout
=
strtol
(
param
->
value
,
&
test
,
10
);
if
(
*
test
!=
'\0'
||
interface_timeout
<=
0
)
{
if
(
*
test
!=
'\0'
||
interface_timeout
<=
0
)
{
ERROR
(
"connection timeout
\"
%s
\"
is not a positive integer
\n
"
,(
getConf
())[
CONF_CONNECTION_TIMEOUT
]);
ERROR
(
"connection timeout
\"
%s
\"
is not a positive "
"integer, line %i
\n
"
,
CONF_CONN_TIMEOUT
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
}
interface_max_connections
=
strtol
((
getConf
())[
CONF_MAX_CONNECTIONS
],
&
test
,
10
);
param
=
getConfigParam
(
CONF_MAX_CONN
);
if
(
param
)
{
interface_max_connections
=
strtol
(
param
->
value
,
&
test
,
10
);
if
(
*
test
!=
'\0'
||
interface_max_connections
<=
0
)
{
if
(
*
test
!=
'\0'
||
interface_max_connections
<=
0
)
{
ERROR
(
"max connections
\"
%s
\"
is not a positive integer
\n
"
,(
getConf
())[
CONF_MAX_CONNECTIONS
]);
ERROR
(
"max connections
\"
%s
\"
is not a positive integer"
", line %i
\n
"
,
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
}
param
=
getConfigParam
(
CONF_MAX_COMMAND_LIST_SIZE
);
interface_max_command_list_size
=
strtoll
((
getConf
())[
CONF_MAX_COMMAND_LIST_SIZE
],
&
test
,
10
);
if
(
param
)
{
interface_max_command_list_size
=
strtoll
(
param
->
value
,
&
test
,
10
);
if
(
*
test
!=
'\0'
||
interface_max_command_list_size
<=
0
)
{
if
(
*
test
!=
'\0'
||
interface_max_command_list_size
<=
0
)
{
ERROR
(
"max command list size
\"
%s
\"
is not a positive integer
\n
"
,(
getConf
())[
CONF_MAX_COMMAND_LIST_SIZE
]);
ERROR
(
"max command list size
\"
%s
\"
is not a positive "
"integer, line %i
\n
"
,
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
interface_max_command_list_size
*=
1024
;
}
param
=
getConfigParam
(
CONF_MAX_OUTPUT_BUFFER_SIZE
);
interface_max_output_buffer_size
=
strtoll
((
getConf
())[
CONF_MAX_OUTPUT_BUFFER_SIZE
],
&
test
,
10
);
if
(
param
)
{
interface_max_output_buffer_size
=
strtoll
(
param
->
value
,
&
test
,
10
);
if
(
*
test
!=
'\0'
||
interface_max_output_buffer_size
<=
0
)
{
if
(
*
test
!=
'\0'
||
interface_max_output_buffer_size
<=
0
)
{
ERROR
(
"max output buffer size
\"
%s
\"
is not a positive integer
\n
"
,(
getConf
())[
CONF_MAX_OUTPUT_BUFFER_SIZE
]);
ERROR
(
"max output buffer size
\"
%s
\"
is not a positive "
"integer, line %i
\n
"
,
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
interface_max_command_list_size
*=
1024
;
interface_max_output_buffer_size
*=
1024
;
interface_max_output_buffer_size
*=
1024
;
}
interfaces
=
malloc
(
sizeof
(
Interface
)
*
interface_max_connections
);
interfaces
=
malloc
(
sizeof
(
Interface
)
*
interface_max_connections
);
...
...
src/list.c
View file @
58dbe4bb
...
@@ -192,7 +192,7 @@ int findInList(List * list,char * key,void ** data) {
...
@@ -192,7 +192,7 @@ int findInList(List * list,char * key,void ** data) {
tmpNode
=
list
->
nodesArray
[
cur
];
tmpNode
=
list
->
nodesArray
[
cur
];
cmp
=
strcmp
(
tmpNode
->
key
,
key
);
cmp
=
strcmp
(
tmpNode
->
key
,
key
);
if
(
cmp
==
0
)
{
if
(
cmp
==
0
)
{
(
*
data
)
=
tmpNode
->
data
;
if
(
data
)
*
data
=
tmpNode
->
data
;
return
1
;
return
1
;
}
}
else
if
(
cmp
>
0
)
high
=
cur
;
else
if
(
cmp
>
0
)
high
=
cur
;
...
...
src/list.h
View file @
58dbe4bb
...
@@ -88,6 +88,7 @@ void deleteNodeFromList(List * list,ListNode * node);
...
@@ -88,6 +88,7 @@ void deleteNodeFromList(List * list,ListNode * node);
* _key_ -> which node is being searched for
* _key_ -> which node is being searched for
* _data_ -> a pointer to where data will be placed,
* _data_ -> a pointer to where data will be placed,
* _data_ memory should not by allocated or freed
* _data_ memory should not by allocated or freed
* _data_ can be NULL
* returns 1 if successful, 0 otherwise
* returns 1 if successful, 0 otherwise
*/
*/
int
findInList
(
List
*
list
,
char
*
key
,
void
**
data
);
int
findInList
(
List
*
list
,
char
*
key
,
void
**
data
);
...
...
src/listen.c
View file @
58dbe4bb
...
@@ -44,6 +44,7 @@
...
@@ -44,6 +44,7 @@
int
listenSocket
;
int
listenSocket
;
int
establish
(
unsigned
short
port
)
{
int
establish
(
unsigned
short
port
)
{
ConfigParam
*
param
;
int
allowReuse
=
ALLOW_REUSE
;
int
allowReuse
=
ALLOW_REUSE
;
int
sock
;
int
sock
;
struct
sockaddr
*
addrp
;
struct
sockaddr
*
addrp
;
...
@@ -61,7 +62,9 @@ int establish(unsigned short port) {
...
@@ -61,7 +62,9 @@ int establish(unsigned short port) {
sin
.
sin_port
=
htons
(
port
);
sin
.
sin_port
=
htons
(
port
);
sin
.
sin_family
=
AF_INET
;
sin
.
sin_family
=
AF_INET
;
if
(
strcmp
((
getConf
())[
CONF_BIND_TO_ADDRESS
],
"any"
)
==
0
)
{
param
=
getConfigParam
(
CONF_BIND_TO_ADDRESS
);
if
(
!
param
||
0
==
strcmp
(
param
->
value
,
"any"
)
==
0
)
{
#ifdef HAVE_IPV6
#ifdef HAVE_IPV6
if
(
ipv6Supported
())
{
if
(
ipv6Supported
())
{
sin6
.
sin6_addr
=
in6addr_any
;
sin6
.
sin6_addr
=
in6addr_any
;
...
@@ -78,9 +81,9 @@ int establish(unsigned short port) {
...
@@ -78,9 +81,9 @@ int establish(unsigned short port) {
}
}
else
{
else
{
struct
hostent
*
he
;
struct
hostent
*
he
;
if
(
!
(
he
=
gethostbyname
(
(
getConf
())[
CONF_BIND_TO_ADDRESS
]
)))
{
if
(
!
(
he
=
gethostbyname
(
param
->
value
)))
{
ERROR
(
"can't lookup host
\"
%s
\"\n
"
,
ERROR
(
"can't lookup host
\"
%s
\"
at line %i
\n
"
,
(
getConf
())[
CONF_BIND_TO_ADDRESS
]
);
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
switch
(
he
->
h_addrtype
)
{
switch
(
he
->
h_addrtype
)
{
...
@@ -88,8 +91,8 @@ int establish(unsigned short port) {
...
@@ -88,8 +91,8 @@ int establish(unsigned short port) {
case
AF_INET6
:
case
AF_INET6
:
if
(
!
ipv6Supported
())
{
if
(
!
ipv6Supported
())
{
ERROR
(
"no IPv6 support, but a IPv6 address "
ERROR
(
"no IPv6 support, but a IPv6 address "
"found for
\"
%s
\"\n
"
,
"found for
\"
%s
\"
at line %i
\n
"
,
(
getConf
())[
CONF_BIND_TO_ADDRESS
]
);
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
bcopy
((
char
*
)
he
->
h_addr
,(
char
*
)
bcopy
((
char
*
)
he
->
h_addr
,(
char
*
)
...
@@ -105,8 +108,9 @@ int establish(unsigned short port) {
...
@@ -105,8 +108,9 @@ int establish(unsigned short port) {
addrlen
=
sizeof
(
struct
sockaddr_in
);
addrlen
=
sizeof
(
struct
sockaddr_in
);
break
;
break
;
default:
default:
ERROR
(
"address type for
\"
%s
\"
is not IPv4 or IPv6
\n
"
,
ERROR
(
"address type for
\"
%s
\"
is not IPv4 or IPv6 "
(
getConf
())[
CONF_BIND_TO_ADDRESS
]);
"at line %i
\n
"
,
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
}
}
...
...
src/log.c
View file @
58dbe4bb
...
@@ -32,16 +32,24 @@ short warningFlushed = 0;
...
@@ -32,16 +32,24 @@ short warningFlushed = 0;
static
char
*
warningBuffer
=
NULL
;
static
char
*
warningBuffer
=
NULL
;
void
initLog
()
{
void
initLog
()
{
if
(
strcmp
(
getConf
()[
CONF_LOG_LEVEL
],
"default"
)
==
0
)
{
ConfigParam
*
param
=
getConfigParam
(
CONF_LOG_LEVEL
);
if
(
!
param
)
return
;
if
(
0
==
strcmp
(
param
->
value
,
"default"
))
{
if
(
logLevel
<
LOG_LEVEL_LOW
)
logLevel
=
LOG_LEVEL_LOW
;
if
(
logLevel
<
LOG_LEVEL_LOW
)
logLevel
=
LOG_LEVEL_LOW
;
}
}
else
if
(
strcmp
(
getConf
()[
CONF_LOG_LEVEL
],
"secure"
)
==
0
)
{
else
if
(
0
==
strcmp
(
param
->
value
,
"secure"
)
)
{
if
(
logLevel
<
LOG_LEVEL_SECURE
)
logLevel
=
LOG_LEVEL_SECURE
;
if
(
logLevel
<
LOG_LEVEL_SECURE
)
logLevel
=
LOG_LEVEL_SECURE
;
}
}
else
if
(
strcmp
(
getConf
()[
CONF_LOG_LEVEL
],
"verbose"
)
==
0
)
{
else
if
(
0
==
strcmp
(
param
->
value
,
"verbose"
)
)
{
if
(
logLevel
<
LOG_LEVEL_DEBUG
)
logLevel
=
LOG_LEVEL_DEBUG
;
if
(
logLevel
<
LOG_LEVEL_DEBUG
)
logLevel
=
LOG_LEVEL_DEBUG
;
}
}
else
ERROR
(
"unknown log level
\"
%s
\"\n
"
,
getConf
()[
CONF_LOG_LEVEL
]);
else
{
ERROR
(
"unknown log level
\"
%s
\"
at line %i
\n
"
,
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
}
}
}
#define BUFFER_LENGTH 4096
#define BUFFER_LENGTH 4096
...
...
src/main.c
View file @
58dbe4bb
...
@@ -165,9 +165,12 @@ void parseOptions(int argc, char ** argv, Options * options) {
...
@@ -165,9 +165,12 @@ void parseOptions(int argc, char ** argv, Options * options) {
return
;
return
;
}
}
else
if
(
argcLeft
<=
2
)
{
else
if
(
argcLeft
<=
2
)
{
char
**
conf
=
NULL
;
int
conf
=
0
;
if
(
argcLeft
==
2
)
conf
=
readConf
(
argv
[
argc
-
1
]);
if
(
argcLeft
==
2
)
{
if
(
argcLeft
==
1
)
{
readConf
(
argv
[
argc
-
1
]);
conf
=
1
;
}
else
if
(
argcLeft
==
1
)
{
FILE
*
fp
;
FILE
*
fp
;
char
*
homedir
=
getenv
(
"HOME"
);
char
*
homedir
=
getenv
(
"HOME"
);
char
userfile
[
MAXPATHLEN
+
1
]
=
""
;
char
userfile
[
MAXPATHLEN
+
1
]
=
""
;
...
@@ -179,23 +182,27 @@ void parseOptions(int argc, char ** argv, Options * options) {
...
@@ -179,23 +182,27 @@ void parseOptions(int argc, char ** argv, Options * options) {
}
}
if
(
strlen
(
userfile
)
&&
(
fp
=
fopen
(
userfile
,
"r"
)))
{
if
(
strlen
(
userfile
)
&&
(
fp
=
fopen
(
userfile
,
"r"
)))
{
fclose
(
fp
);
fclose
(
fp
);
conf
=
readConf
(
userfile
);
readConf
(
userfile
);
conf
=
1
;
}
}
else
if
((
fp
=
fopen
(
SYSTEM_CONFIG_FILE_LOCATION
,
"r"
)))
{
else
if
((
fp
=
fopen
(
SYSTEM_CONFIG_FILE_LOCATION
,
"r"
)))
{
fclose
(
fp
);
fclose
(
fp
);
conf
=
readConf
(
SYSTEM_CONFIG_FILE_LOCATION
);
readConf
(
SYSTEM_CONFIG_FILE_LOCATION
);
conf
=
1
;
}
}
}
}
if
(
conf
)
{
if
(
conf
)
{
options
->
portStr
=
conf
[
CONF_PORT
];
options
->
portStr
=
forceAndGetConfigParamValue
(
options
->
musicDirArg
=
conf
[
CONF_MUSIC_DIRECTORY
];
CONF_PORT
);
options
->
playlistDirArg
=
conf
[
CONF_PLAYLIST_DIRECTORY
];
options
->
musicDirArg
=
options
->
logFile
=
conf
[
CONF_LOG_FILE
];
parseConfigFilePath
(
CONF_MUSIC_DIR
,
1
);
options
->
errorFile
=
conf
[
CONF_ERROR_FILE
];
options
->
playlistDirArg
=
options
->
usr
=
conf
[
CONF_USER
];
parseConfigFilePath
(
CONF_PLAYLIST_DIR
,
1
);
if
(
conf
[
CONF_DB_FILE
])
{
options
->
logFile
=
parseConfigFilePath
(
CONF_LOG_FILE
,
1
);
options
->
dbFile
=
conf
[
CONF_DB_FILE
];
options
->
errorFile
=
}
parseConfigFilePath
(
CONF_ERROR_FILE
,
1
);
options
->
usr
=
parseConfigFilePath
(
CONF_USER
,
0
);
options
->
dbFile
=
parseConfigFilePath
(
CONF_DB_FILE
,
0
);
return
;
return
;
}
}
}
}
...
...
src/path.c
View file @
58dbe4bb
...
@@ -114,6 +114,7 @@ void initPaths(char * playlistDirArg, char * musicDirArg) {
...
@@ -114,6 +114,7 @@ void initPaths(char * playlistDirArg, char * musicDirArg) {
char
*
charset
=
NULL
;
char
*
charset
=
NULL
;
char
*
originalLocale
;
char
*
originalLocale
;
struct
stat
st
;
struct
stat
st
;
ConfigParam
*
param
;
playlistDir
=
prependCwdToPathDup
(
playlistDirArg
);
playlistDir
=
prependCwdToPathDup
(
playlistDirArg
);
if
((
stat
(
playlistDir
,
&
st
))
<
0
)
{
if
((
stat
(
playlistDir
,
&
st
))
<
0
)
{
...
@@ -135,8 +136,10 @@ void initPaths(char * playlistDirArg, char * musicDirArg) {
...
@@ -135,8 +136,10 @@ void initPaths(char * playlistDirArg, char * musicDirArg) {
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
if
(
getConf
()[
CONF_FS_CHARSET
])
{
param
=
getConfigParam
(
CONF_FS_CHARSET
);
charset
=
strdup
(
getConf
()[
CONF_FS_CHARSET
]);
if
(
param
)
{
charset
=
strdup
(
param
->
value
);
}
}
#ifdef HAVE_LOCALE
#ifdef HAVE_LOCALE
#ifdef HAVE_LANGINFO_CODESET
#ifdef HAVE_LANGINFO_CODESET
...
@@ -296,5 +299,3 @@ char * prependCwdToPathDup(char * path) {
...
@@ -296,5 +299,3 @@ char * prependCwdToPathDup(char * path) {
return
realloc
(
ret
,
len
+
1
);
return
realloc
(
ret
,
len
+
1
);
}
}
/* vim:set shiftwidth=4 tabstop=8 expandtab: */
src/permission.c
View file @
58dbe4bb
...
@@ -69,56 +69,53 @@ unsigned int parsePermissions(char * string) {
...
@@ -69,56 +69,53 @@ unsigned int parsePermissions(char * string) {
}
}
void
initPermissions
()
{
void
initPermissions
()
{
char
*
passwordSets
;
char
*
nextSet
;
char
*
temp
;
char
*
temp
;
char
*
cp1
;
char
*
cp2
;
char
*
cp2
;
char
*
password
;
char
*
password
;
unsigned
int
*
permission
;
unsigned
int
*
permission
;
ConfigParam
*
param
;
permission_passwords
=
makeList
(
free
);
permission_passwords
=
makeList
(
free
);
permission_default
=
PERMISSION_READ
|
PERMISSION_ADD
|
permission_default
=
PERMISSION_READ
|
PERMISSION_ADD
|
PERMISSION_CONTROL
|
PERMISSION_ADMIN
;
PERMISSION_CONTROL
|
PERMISSION_ADMIN
;
if
(
getConf
()[
CONF_DEFAULT_PERMISSIONS
])
{
param
=
getNextConfigParam
(
CONF_PASSWORD
,
NULL
);
permission_default
=
parsePermissions
(
getConf
()[
CONF_DEFAULT_PERMISSIONS
]);
}
if
(
!
getConf
()[
CONF_PASSWORD
])
return
;
if
(
!
getConf
()[
CONF_DEFAULT_PERMISSIONS
])
permission_default
=
0
;
passwordSets
=
strdup
(
getConf
()[
CONF_PASSWORD
]);
if
(
param
)
{
permission_default
=
0
;
nextSet
=
strtok_r
(
passwordSets
,
CONF_CAT_CHAR
,
&
cp1
);
do
{
while
(
nextSet
&&
strlen
(
nextSet
))
{
if
(
!
strstr
(
param
->
value
,
PERMISSION_PASSWORD_CHAR
))
{
if
(
!
strstr
(
nextSet
,
PERMISSION_PASSWORD_CHAR
))
{
ERROR
(
"
\"
%s
\"
not found in password string "
ERROR
(
"
\"
%s
\"
not found in password string
\"
%s
\"
\n
"
,
"
\"
%s
\"
, line %i
\n
"
,
PERMISSION_PASSWORD_CHAR
,
PERMISSION_PASSWORD_CHAR
,
nextSet
);
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
if
(
!
(
temp
=
strtok_r
(
nextSet
,
PERMISSION_PASSWORD_CHAR
,
&
cp2
)))
{
if
(
!
(
temp
=
strtok_r
(
param
->
value
,
PERMISSION_PASSWORD_CHAR
,
&
cp2
)))
{
ERROR
(
"something weird just happend in permission.c
\n
"
);
ERROR
(
"something weird just happend in permission.c
\n
"
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
password
=
temp
;
password
=
temp
;
permission
=
malloc
(
sizeof
(
unsigned
int
));
permission
=
malloc
(
sizeof
(
unsigned
int
));
*
permission
=
parsePermissions
(
strtok_r
(
NULL
,
""
,
&
cp2
));
*
permission
=
parsePermissions
(
strtok_r
(
NULL
,
""
,
&
cp2
));
insertInList
(
permission_passwords
,
password
,
permission
);
insertInList
(
permission_passwords
,
password
,
permission
);
}
while
((
param
=
getNextConfigParam
(
CONF_PASSWORD
,
param
)));
nextSet
=
strtok_r
(
NULL
,
CONF_CAT_CHAR
,
&
cp1
);
}
}
sortList
(
permission_passwords
);
param
=
getConfigParam
(
CONF_DEFAULT_PERMS
);
free
(
passwordSets
);
if
(
param
)
permission_default
=
parsePermissions
(
param
->
value
);
sortList
(
permission_passwords
);
}
}
int
getPermissionFromPassword
(
char
*
password
,
unsigned
int
*
permission
)
{
int
getPermissionFromPassword
(
char
*
password
,
unsigned
int
*
permission
)
{
...
...
src/playerData.c
View file @
58dbe4bb
...
@@ -30,23 +30,32 @@
...
@@ -30,23 +30,32 @@
int
buffered_before_play
;
int
buffered_before_play
;
int
buffered_chunks
;
int
buffered_chunks
;
#define DEFAULT_BUFFER_SIZE 2048
#define DEFAULT_BUFFER_BEFORE_PLAY 25
PlayerData
*
playerData_pd
;
PlayerData
*
playerData_pd
;
void
initPlayerData
()
{
void
initPlayerData
()
{
float
perc
;
float
perc
=
DEFAULT_BUFFER_BEFORE_PLAY
;
char
*
test
;
char
*
test
;
int
shmid
;
int
shmid
;
int
crossfade
=
0
;
int
crossfade
=
0
;
size_t
bufferSize
;
size_t
bufferSize
=
DEFAULT_BUFFER_SIZE
;
size_t
allocationSize
;
size_t
allocationSize
;
OutputBuffer
*
buffer
;
OutputBuffer
*
buffer
;
ConfigParam
*
param
;
param
=
getConfigParam
(
CONF_AUDIO_BUFFER_SIZE
);
bufferSize
=
strtol
(
getConf
()[
CONF_BUFFER_SIZE
],
&
test
,
10
);
if
(
param
)
{
bufferSize
=
strtol
(
param
->
value
,
&
test
,
10
);
if
(
*
test
!=
'\0'
||
bufferSize
<=
0
)
{
if
(
*
test
!=
'\0'
||
bufferSize
<=
0
)
{
ERROR
(
"buffer size
\"
%s
\"
is not a positive integer
\n
"
,
ERROR
(
"buffer size
\"
%s
\"
is not a positive integer, "
getConf
()[
CONF_BUFFER_SIZE
]
);
"line %i
\n
"
,
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
}
bufferSize
*=
1024
;
bufferSize
*=
1024
;
buffered_chunks
=
bufferSize
/
CHUNK_SIZE
;
buffered_chunks
=
bufferSize
/
CHUNK_SIZE
;
...
@@ -56,13 +65,18 @@ void initPlayerData() {
...
@@ -56,13 +65,18 @@ void initPlayerData() {
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
perc
=
strtod
((
getConf
())[
CONF_BUFFER_BEFORE_PLAY
],
&
test
);
param
=
getConfigParam
(
CONF_BUFFER_BEFORE_PLAY
);
if
(
param
)
{
perc
=
strtod
(
param
->
value
,
&
test
);
if
(
*
test
!=
'%'
||
perc
<
0
||
perc
>
100
)
{
if
(
*
test
!=
'%'
||
perc
<
0
||
perc
>
100
)
{
ERROR
(
"buffered before play
\"
%s
\"
is not a positive "
ERROR
(
"buffered before play
\"
%s
\"
is not a positive "
"percentage and less than 100 percent
\n
"
,
"percentage and less than 100 percent
, line %i"
(
getConf
())[
CONF_BUFFER_BEFORE_PLAY
]
);
"
\n
"
,
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
}
buffered_before_play
=
(
perc
/
100
)
*
buffered_chunks
;
buffered_before_play
=
(
perc
/
100
)
*
buffered_chunks
;
if
(
buffered_before_play
>
buffered_chunks
)
{
if
(
buffered_before_play
>
buffered_chunks
)
{
buffered_before_play
=
buffered_chunks
;
buffered_before_play
=
buffered_chunks
;
...
...
src/playlist.c
View file @
58dbe4bb
...
@@ -60,6 +60,9 @@
...
@@ -60,6 +60,9 @@
#define PLAYLIST_HASH_MULT 4
#define PLAYLIST_HASH_MULT 4
#define DEFAULT_PLAYLIST_MAX_LENGTH (1024*16)
#define DEFAULT_PLAYLIST_SAVE_ABSOLUTE_PATHS 0
typedef
struct
_Playlist
{
typedef
struct
_Playlist
{
Song
**
songs
;
Song
**
songs
;
/* holds version a song was modified on */
/* holds version a song was modified on */
...
@@ -77,13 +80,13 @@ typedef struct _Playlist {
...
@@ -77,13 +80,13 @@ typedef struct _Playlist {
static
Playlist
playlist
;
static
Playlist
playlist
;
static
int
playlist_state
=
PLAYLIST_STATE_STOP
;
static
int
playlist_state
=
PLAYLIST_STATE_STOP
;
static
int
playlist_max_length
;
static
int
playlist_max_length
=
DEFAULT_PLAYLIST_MAX_LENGTH
;
static
int
playlist_stopOnError
;
static
int
playlist_stopOnError
;
static
int
playlist_errorCount
=
0
;
static
int
playlist_errorCount
=
0
;
static
int
playlist_queueError
;
static
int
playlist_queueError
;
static
int
playlist_noGoToNext
=
0
;
static
int
playlist_noGoToNext
=
0
;
static
int
playlist_saveAbsolutePaths
;
static
int
playlist_saveAbsolutePaths
=
DEFAULT_PLAYLIST_SAVE_ABSOLUTE_PATHS
;
static
char
*
playlist_stateFile
=
NULL
;
static
char
*
playlist_stateFile
=
NULL
;
...
@@ -128,6 +131,7 @@ static void incrPlaylistCurrent() {
...
@@ -128,6 +131,7 @@ static void incrPlaylistCurrent() {
void
initPlaylist
()
{
void
initPlaylist
()
{
char
*
test
;
char
*
test
;
int
i
;
int
i
;
ConfigParam
*
param
;
playlist
.
length
=
0
;
playlist
.
length
=
0
;
playlist
.
repeat
=
0
;
playlist
.
repeat
=
0
;
...
@@ -136,27 +140,33 @@ void initPlaylist() {
...
@@ -136,27 +140,33 @@ void initPlaylist() {
playlist
.
queued
=
-
1
;
playlist
.
queued
=
-
1
;
playlist
.
current
=
-
1
;
playlist
.
current
=
-
1
;
playlist_max_length
=
strtol
((
getConf
())[
CONF_MAX_PLAYLIST_LENGTH
],
&
test
,
10
);
param
=
getConfigParam
(
CONF_MAX_PLAYLIST_LENGTH
);
if
(
param
)
{
playlist_max_length
=
strtol
(
param
->
value
,
&
test
,
10
);
if
(
*
test
!=
'\0'
)
{
if
(
*
test
!=
'\0'
)
{
ERROR
(
"max playlist length
\"
%s
\"
is not an integer
\n
"
,
ERROR
(
"max playlist length
\"
%s
\"
is not an integer, "
(
getConf
())[
CONF_MAX_PLAYLIST_LENGTH
]
);
"line %i
\n
"
,
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
}
if
(
strcmp
(
"yes"
,(
getConf
())[
CONF_SAVE_ABSOLUTE_PATHS_IN_PLAYLISTS
])
param
=
getConfigParam
(
CONF_SAVE_ABSOLUTE_PATHS
);
==
0
)
{
if
(
param
)
{
if
(
0
==
strcmp
(
"yes"
,
param
->
value
)
)
{
playlist_saveAbsolutePaths
=
1
;
playlist_saveAbsolutePaths
=
1
;
}
}
else
if
(
strcmp
(
"no"
,(
getConf
())[
CONF_SAVE_ABSOLUTE_PATHS_IN_PLAYLISTS
])
else
if
(
0
==
strcmp
(
"no"
,
param
->
value
)
)
{
==
0
)
{
playlist_saveAbsolutePaths
=
0
;
playlist_saveAbsolutePaths
=
0
;
}
}
else
{
else
{
ERROR
(
"save_absolute_paths_in_playlist
\"
%s
\"
is not yes or
"
ERROR
(
"%s
\"
%s
\"
is not yes or no, line %i
"
"no
\n
"
,
CONF_SAVE_ABSOLUTE_PATHS
,
(
getConf
())[
CONF_SAVE_ABSOLUTE_PATHS_IN_PLAYLISTS
]
);
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
}
playlist
.
songs
=
malloc
(
sizeof
(
Song
*
)
*
playlist_max_length
);
playlist
.
songs
=
malloc
(
sizeof
(
Song
*
)
*
playlist_max_length
);
playlist
.
songMod
=
malloc
(
sizeof
(
mpd_uint32
)
*
playlist_max_length
);
playlist
.
songMod
=
malloc
(
sizeof
(
mpd_uint32
)
*
playlist_max_length
);
...
@@ -169,9 +179,7 @@ void initPlaylist() {
...
@@ -169,9 +179,7 @@ void initPlaylist() {
srand
(
time
(
NULL
));
srand
(
time
(
NULL
));
if
(
getConf
()[
CONF_STATE_FILE
])
{
playlist_stateFile
=
getConfigParamValue
(
CONF_STATE_FILE
);
playlist_stateFile
=
getConf
()[
CONF_STATE_FILE
];
}
for
(
i
=
0
;
i
<
playlist_max_length
*
PLAYLIST_HASH_MULT
;
i
++
)
{
for
(
i
=
0
;
i
<
playlist_max_length
*
PLAYLIST_HASH_MULT
;
i
++
)
{
playlist
.
idToPosition
[
i
]
=
-
1
;
playlist
.
idToPosition
[
i
]
=
-
1
;
...
...
src/replayGain.c
View file @
58dbe4bb
...
@@ -32,34 +32,38 @@ static int replayGainState = REPLAYGAIN_OFF;
...
@@ -32,34 +32,38 @@ static int replayGainState = REPLAYGAIN_OFF;
static
float
replayGainPreamp
=
1
.
0
;
static
float
replayGainPreamp
=
1
.
0
;
void
initReplayGainState
()
{
void
initReplayGainState
()
{
if
(
!
getConf
()[
CONF_REPLAYGAIN
])
return
;
ConfigParam
*
param
=
getConfigParam
(
CONF_REPLAYGAIN
)
;
if
(
strcmp
(
getConf
()[
CONF_REPLAYGAIN
],
"track"
)
==
0
)
{
if
(
!
param
)
return
;
if
(
strcmp
(
param
->
value
,
"track"
)
==
0
)
{
replayGainState
=
REPLAYGAIN_TRACK
;
replayGainState
=
REPLAYGAIN_TRACK
;
}
}
else
if
(
strcmp
(
getConf
()[
CONF_REPLAYGAIN
],
"album"
)
==
0
)
{
else
if
(
strcmp
(
param
->
value
,
"album"
)
==
0
)
{
replayGainState
=
REPLAYGAIN_ALBUM
;
replayGainState
=
REPLAYGAIN_ALBUM
;
}
}
else
{
else
{
ERROR
(
"replaygain value
\"
%s
\"
is invalid
\n
"
,
ERROR
(
"replaygain value
\"
%s
\"
at line %i
is invalid
\n
"
,
getConf
()[
CONF_REPLAYGAIN
]
);
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
if
(
getConf
()[
CONF_REPLAYGAIN_PREAMP
])
{
param
=
getConfigParam
(
CONF_REPLAYGAIN_PREAMP
);
if
(
param
)
{
char
*
test
;
char
*
test
;
float
f
=
strtod
(
getConf
()[
CONF_REPLAYGAIN_PREAMP
]
,
&
test
);
float
f
=
strtod
(
param
->
value
,
&
test
);
if
(
*
test
!=
'\0'
)
{
if
(
*
test
!=
'\0'
)
{
ERROR
(
"Replaygain preamp
\"
%s
\"
is not a number
\n
"
,
ERROR
(
"Replaygain preamp
\"
%s
\"
is not a number
at "
getConf
()[
CONF_REPLAYGAIN_PREAMP
]
);
"line %i
\n
"
,
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
if
(
f
<
-
15
||
f
>
15
)
{
if
(
f
<
-
15
||
f
>
15
)
{
ERROR
(
"Replaygain preamp
\"
%s
\"
is not between -15 and"
ERROR
(
"Replaygain preamp
\"
%s
\"
is not between -15 and"
"15
\n
"
,
"15
at line %i
\n
"
,
getConf
()[
CONF_REPLAYGAIN_PREAMP
]
);
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
...
...
src/tag.c
View file @
58dbe4bb
...
@@ -93,18 +93,6 @@ char * getID3Info(struct id3_tag * tag, char * id) {
...
@@ -93,18 +93,6 @@ char * getID3Info(struct id3_tag * tag, char * id) {
utf8
=
id3_ucs4_utf8duplicate
(
ucs4
);
utf8
=
id3_ucs4_utf8duplicate
(
ucs4
);
if
(
!
utf8
)
return
NULL
;
if
(
!
utf8
)
return
NULL
;
if
(
getConf
()[
CONF_ID3V1_ENCODING
]
&&
(
id3_tag_options
(
tag
,
0
,
0
)
&
ID3_TAG_OPTION_ID3V1
))
{
char
*
isostr
;
setCharSetConversion
(
"ISO-8859-1"
,
"UTF-8"
);
isostr
=
convStrDup
(
utf8
);
free
(
utf8
);
setCharSetConversion
(
"UTF-8"
,
getConf
()[
CONF_ID3V1_ENCODING
]);
utf8
=
convStrDup
(
isostr
);
free
(
isostr
);
}
return
utf8
;
return
utf8
;
}
}
#endif
#endif
...
...
src/volume.c
View file @
58dbe4bb
...
@@ -45,8 +45,21 @@
...
@@ -45,8 +45,21 @@
#define VOLUME_MIXER_ALSA_DEFAULT "default"
#define VOLUME_MIXER_ALSA_DEFAULT "default"
#define VOLUME_MIXER_ALSA_CONTROL_DEFAULT "Master"
#define VOLUME_MIXER_ALSA_CONTROL_DEFAULT "Master"
int
volume_mixerType
=
VOLUME_MIXER_TYPE_SOFTWARE
;
#ifndef NO_OSS_MIXER
char
*
volume_mixerDevice
;
#define VOLUME_MIXER_TYPE_DEFAULT VOLUME_MIXER_TYPE_OSS
#define VOLUME_MIXER_DEVICE_DEFAULT VOLUME_MIXER_OSS_DEFAULT
#else
#ifdef HAVE_ALSA
#define VOLUME_MIXER_TYPE_DEFAULT VOLUME_MIXER_TYPE_ALSA
#define VOLUME_MIXER_DEVICE_DEFAULT VOLUME_MIXER_ALSA_DEFAULT
#else
#define VOLUME_MIXER_TYPE_DEFAULT VOLUME_MIXER_TYPE_SOFTWARE
#define VOLUME_MIXER_DEVICE_DEFAULT VOLUME_MIXER_SOFTWARE_DEFAULT
#endif
#endif
int
volume_mixerType
=
VOLUME_MIXER_TYPE_DEFAULT
;
char
*
volume_mixerDevice
=
VOLUME_MIXER_DEVICE_DEFAULT
;
int
volume_softwareSet
=
100
;
int
volume_softwareSet
=
100
;
...
@@ -66,13 +79,16 @@ int volume_alsaSet = -1;
...
@@ -66,13 +79,16 @@ int volume_alsaSet = -1;
#ifndef NO_OSS_MIXER
#ifndef NO_OSS_MIXER
int
prepOssMixer
(
char
*
device
)
{
int
prepOssMixer
(
char
*
device
)
{
int
devmask
=
0
;
int
devmask
=
0
;
ConfigParam
*
param
;
if
((
volume_ossFd
=
open
(
device
,
O_RDONLY
))
<
0
)
{
if
((
volume_ossFd
=
open
(
device
,
O_RDONLY
))
<
0
)
{
WARNING
(
"unable to open oss mixer
\"
%s
\"\n
"
,
device
);
WARNING
(
"unable to open oss mixer
\"
%s
\"\n
"
,
device
);
return
-
1
;
return
-
1
;
}
}
if
(
getConf
()[
CONF_MIXER_CONTROL
])
{
param
=
getConfigParam
(
CONF_MIXER_CONTROL
);
if
(
param
)
{
char
*
labels
[
SOUND_MIXER_NRDEVICES
]
=
SOUND_DEVICE_LABELS
;
char
*
labels
[
SOUND_MIXER_NRDEVICES
]
=
SOUND_DEVICE_LABELS
;
char
*
dup
;
char
*
dup
;
int
i
,
j
;
int
i
,
j
;
...
@@ -88,7 +104,7 @@ int prepOssMixer(char * device) {
...
@@ -88,7 +104,7 @@ int prepOssMixer(char * device) {
/* eliminate spaces at the end */
/* eliminate spaces at the end */
j
=
strlen
(
dup
)
-
1
;
j
=
strlen
(
dup
)
-
1
;
while
(
j
>=
0
&&
dup
[
j
]
==
' '
)
dup
[
j
--
]
=
'\0'
;
while
(
j
>=
0
&&
dup
[
j
]
==
' '
)
dup
[
j
--
]
=
'\0'
;
if
(
strcasecmp
(
dup
,
getConf
()[
CONF_MIXER_CONTROL
]
)
==
0
)
{
if
(
strcasecmp
(
dup
,
param
->
value
)
==
0
)
{
free
(
dup
);
free
(
dup
);
break
;
break
;
}
}
...
@@ -96,14 +112,14 @@ int prepOssMixer(char * device) {
...
@@ -96,14 +112,14 @@ int prepOssMixer(char * device) {
}
}
if
(
i
>=
SOUND_MIXER_NRDEVICES
)
{
if
(
i
>=
SOUND_MIXER_NRDEVICES
)
{
WARNING
(
"mixer control
\"
%s
\"
not found
\n
"
,
WARNING
(
"mixer control
\"
%s
\"
not found
at line %i
\n
"
,
getConf
()[
CONF_MIXER_CONTROL
]
);
param
->
value
,
param
->
line
);
close
(
volume_ossFd
);
close
(
volume_ossFd
);
return
-
1
;
return
-
1
;
}
}
else
if
(
!
(
(
1
<<
i
)
&
devmask
))
{
else
if
(
!
(
(
1
<<
i
)
&
devmask
))
{
WARNING
(
"mixer control
\"
%s
\"
not usable
\n
"
,
WARNING
(
"mixer control
\"
%s
\"
not usable
at line %i
\n
"
,
getConf
()[
CONF_MIXER_CONTROL
]
);
param
->
value
,
param
->
line
);
close
(
volume_ossFd
);
close
(
volume_ossFd
);
return
-
1
;
return
-
1
;
}
}
...
@@ -173,6 +189,7 @@ int prepAlsaMixer(char * card) {
...
@@ -173,6 +189,7 @@ int prepAlsaMixer(char * card) {
int
err
;
int
err
;
snd_mixer_elem_t
*
elem
;
snd_mixer_elem_t
*
elem
;
char
*
controlName
=
VOLUME_MIXER_ALSA_CONTROL_DEFAULT
;
char
*
controlName
=
VOLUME_MIXER_ALSA_CONTROL_DEFAULT
;
ConfigParam
*
param
;
if
((
err
=
snd_mixer_open
(
&
volume_alsaMixerHandle
,
0
))
<
0
)
{
if
((
err
=
snd_mixer_open
(
&
volume_alsaMixerHandle
,
0
))
<
0
)
{
WARNING
(
"problems opening alsa mixer: %s
\n
"
,
snd_strerror
(
err
));
WARNING
(
"problems opening alsa mixer: %s
\n
"
,
snd_strerror
(
err
));
...
@@ -201,8 +218,11 @@ int prepAlsaMixer(char * card) {
...
@@ -201,8 +218,11 @@ int prepAlsaMixer(char * card) {
}
}
elem
=
snd_mixer_first_elem
(
volume_alsaMixerHandle
);
elem
=
snd_mixer_first_elem
(
volume_alsaMixerHandle
);
if
(
getConf
()[
CONF_MIXER_CONTROL
])
{
controlName
=
getConf
()[
CONF_MIXER_CONTROL
];
param
=
getConfigParam
(
CONF_MIXER_CONTROL
);
if
(
param
)
{
controlName
=
param
->
value
;
}
}
while
(
elem
)
{
while
(
elem
)
{
...
@@ -340,29 +360,37 @@ void finishVolume() {
...
@@ -340,29 +360,37 @@ void finishVolume() {
}
}
void
initVolume
()
{
void
initVolume
()
{
ConfigParam
*
param
=
getConfigParam
(
CONF_MIXER_TYPE
);
if
(
param
)
{
if
(
0
);
if
(
0
);
#ifdef HAVE_ALSA
#ifdef HAVE_ALSA
else
if
(
strcmp
((
getConf
())[
CONF_MIXER_TYPE
],
VOLUME_MIXER_ALSA
)
==
0
)
{
else
if
(
strcmp
(
param
->
value
,
VOLUME_MIXER_ALSA
)
==
0
)
{
volume_mixerType
=
VOLUME_MIXER_TYPE_ALSA
;
volume_mixerType
=
VOLUME_MIXER_TYPE_ALSA
;
volume_mixerDevice
=
VOLUME_MIXER_ALSA_DEFAULT
;
volume_mixerDevice
=
VOLUME_MIXER_ALSA_DEFAULT
;
}
}
#endif
#endif
#ifndef NO_OSS_MIXER
#ifndef NO_OSS_MIXER
else
if
(
strcmp
((
getConf
())[
CONF_MIXER_TYPE
],
VOLUME_MIXER_OSS
)
==
0
)
{
else
if
(
strcmp
(
param
->
value
,
VOLUME_MIXER_OSS
)
==
0
)
{
volume_mixerType
=
VOLUME_MIXER_TYPE_OSS
;
volume_mixerType
=
VOLUME_MIXER_TYPE_OSS
;
volume_mixerDevice
=
VOLUME_MIXER_OSS_DEFAULT
;
volume_mixerDevice
=
VOLUME_MIXER_OSS_DEFAULT
;
}
}
#endif
#endif
else
if
(
strcmp
((
getConf
())[
CONF_MIXER_TYPE
]
,
VOLUME_MIXER_SOFTWARE
)
==
0
)
{
else
if
(
strcmp
(
param
->
value
,
VOLUME_MIXER_SOFTWARE
)
==
0
)
{
volume_mixerType
=
VOLUME_MIXER_TYPE_SOFTWARE
;
volume_mixerType
=
VOLUME_MIXER_TYPE_SOFTWARE
;
volume_mixerDevice
=
VOLUME_MIXER_SOFTWARE_DEFAULT
;
volume_mixerDevice
=
VOLUME_MIXER_SOFTWARE_DEFAULT
;
}
}
else
{
else
{
ERROR
(
"unknown mixer type: %s
\n
"
,(
getConf
())[
CONF_MIXER_TYPE
]);
ERROR
(
"unknown mixer type %s at line %i
\n
"
,
param
->
value
,
param
->
line
);
exit
(
EXIT_FAILURE
);
exit
(
EXIT_FAILURE
);
}
}
if
(
strlen
((
getConf
())[
CONF_MIXER_DEVICE
]))
{
}
volume_mixerDevice
=
(
getConf
())[
CONF_MIXER_DEVICE
];
param
=
getConfigParam
(
CONF_MIXER_DEVICE
);
if
(
param
)
{
volume_mixerDevice
=
param
->
value
;
}
}
}
}
...
@@ -431,4 +459,3 @@ int changeVolumeLevel(FILE * fp, int change, int rel) {
...
@@ -431,4 +459,3 @@ int changeVolumeLevel(FILE * fp, int change, int rel) {
break
;
break
;
}
}
}
}
/* vim:set shiftwidth=4 tabstop=8 expandtab: */
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment