Andre Noll [Mon, 15 Aug 2011 18:20:02 +0000 (20:20 +0200)]
command: Remove two dead stores.
command.c:771:2: warning: Value stored to 'ret' is never read
ret = -E_BAD_USER;
^ ~~~~~~~~~~~
command.c:765:2: warning: Value stored to 'numbytes' is never read
numbytes = ret;
^ ~~~
Andre Noll [Mon, 15 Aug 2011 18:16:38 +0000 (20:16 +0200)]
aac_afh: Don't compute the number of milliseconds twice.
aac_afh.c:194:16: warning: Value stored to 'ms' during its initialization is never read
long unsigned ms = 1000.0 * afhi->chunks_total * tmp
^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Andre Noll [Mon, 15 Aug 2011 18:05:11 +0000 (20:05 +0200)]
crypt: Streamline get_asymmetric_key().
The clang analyzer says
crypt.c:202:9: warning: Function call argument is an uninitialized value
ret2 = para_munmap(map, map_size);
^ ~~~~~~~~
And right it is. This is not a bug though as map_size is only undefined
if map is NULL and in this case para_munmap does not look at its second
argument. However, this is rather subtle, so introduce a new label out_unmap
and jump there only if we really must unmap the file.
Andre Noll [Mon, 15 Aug 2011 17:42:15 +0000 (19:42 +0200)]
wmadec: Fix two dead stores.
wmadec_filter.c:772:3: warning: Value stored to 'mult1' is never read
mult1 = mult;
^ ~~~~
wmadec_filter.c:1015:3: warning: Value stored to 'n' is never read
n = pwd->block_len;
^ ~~~~~~~~~~~~~~
Also convert a statement of the form x = x * y to x *= y;
Andre Noll [Thu, 15 Sep 2011 12:33:14 +0000 (14:33 +0200)]
dccp_recv: Avoid NULL pointer dereference.
dccp_recv.c:48:16: warning: Access to field 'btrp' results in a dereference of a null pointer (loaded from variable 'pdd')
btr_pool_free(pdd->btrp);
^~~
In dccp_recv_close(), if pdd is NULL, we avoid closing pdd->fd but
dereference pdd nevertheless one line later. Fix this by returning
early if pdd is NULL.
Andre Noll [Tue, 20 Sep 2011 20:27:18 +0000 (22:27 +0200)]
recv: Improve documentation of generic_recv_pre_select().
Make it clear that this function returns the state of the given buffer
tree node, i.e. > 0 on success, == 0 if there is nothing to do and <
0 on errors.
Andre Noll [Wed, 31 Aug 2011 03:32:04 +0000 (05:32 +0200)]
mp3dec: Avoid possible endless loop.
If an error occurs during frame decode at the end of an 8K buffer,
the code in mp3dec.c might loop forever because we miss to consume
the data of all frames that have been decoded so far during this
iteration of the scheduler loop.
The two callers of used_mad_buffer_bytes() both call btr_consume()
next, and this fix requires to call the same two function once more
from another location. So it is natural to move the btr_consume()
call into used_mad_buffer_bytes() and rename the latter function
to mp3dec_consume().
Andre Noll [Wed, 17 Aug 2011 17:08:17 +0000 (19:08 +0200)]
mp3dec: Fix possible endless loop.
If the header of the last frame of a (corrupt) mp3 file can be decoded
but the rest of the frame can not, the mp3 decoder may end up in a
busy loop.
Fix this by performing the same check as for errors during header
decode. This adds some code duplication but as we are late in the
release cycle, let's go for the minimal fix for now.
Andre Noll [Mon, 15 Aug 2011 20:56:01 +0000 (22:56 +0200)]
sched: Zero-out fd sets on min delay.
If at least one pre_select method requests a minimal delay, we don't
call select() anymore as it would return immediately anyway. However,
the fds that have already been set by previous pre_select methods are
then treated as ready for IO in post_seelect which they most likely
are not. This causes unnecessary calls to readv() and friends which
returned EAGAIN.
Fix this by clearing all fd sets in case of minimal timeouts.
Andre Noll [Mon, 15 Aug 2011 18:09:54 +0000 (20:09 +0200)]
crypt: Really set result to NULL if get_asymmetric_key() fails.
The error path of this function sets the local variable "result"
is set to NULL, which is useless. We must store NULL in the pointer
variable whose address was passed to the function, so "*result =
NULL" is correct.
Andre Noll [Sun, 29 May 2011 10:27:43 +0000 (12:27 +0200)]
oggdec: Take internal state into account.
It is incorrect to look only at the node status of the oggdec buffer
tree node and do nothing if the status is zero. In case the previous
call to ogg_post_select() returned early because it hit the maximal
output buffer size limit, the node status is zero if there is no more
input available, but ov_read() will nevertheless return data which
should be fed to the children of the decoder node as soon as possible.
Andre Noll [Sat, 21 May 2011 19:06:01 +0000 (21:06 +0200)]
Simplify ogg_post_select().
Currently, in each invocation of post_select(), we allocate a
640K buffer and shrink it afterwards to the actual size of the
decoded data. This is ugly and unnecessary.
This patch changes ogg_post_select() to allocate and fill 32K
buffers until the maximal output size is reached or there is
nothing left to decode.
Andre Noll [Sat, 6 Aug 2011 20:32:49 +0000 (22:32 +0200)]
write_common: Make check_writer_arg() exit on syntax errors.
This function parses the argument of the --writer option to extract
the name of the writer, which is the first word of the argument. If
this word is not the name of a supported writer, the function
returns NULL to indicate that the given writer does not exist.
Otherwise check_writer_arg() calls the ->parse_config_or_die method
of this writer which parses the remaining part of the argument and
exits on errors.
It is more consistent and simpler to let this function exit also
in case the writer was not found. This simplifies the callers a bit
since they do not have to check the return value any more. It also
allows to kill E_WRITE_COMMON_SYNTAX.
Andre Noll [Sat, 6 Aug 2011 19:44:24 +0000 (21:44 +0200)]
audiod: Fix memory leak in writer setup.
If no writers are given, the default writer is used for each supported
audio format. In this case, we called the writer's command line parser
on each open, rather than once at startup as we fo for the non-default
case. This resulted in a memory leak which is fixed in this patch by
setting up the default writer only once, in the same way the default
receivers and filters are set up.
Andre Noll [Tue, 26 Jul 2011 18:51:24 +0000 (20:51 +0200)]
alsa: Select on the alsa poll fd.
This teaches the post_select method of the alsa writer to get a control
file descriptor from the alsa library via snd_pcm_poll_descriptors().
This file descriptor becomes readable when a buffer period has passed
and new samples can be written to the alsa handle. We add the fd to
the read fd set so that the select() call of the main scheduler loop
returns just in time.
This is more precise and simpler than the previous approach to compute
the time until a buffer underrun occurs.
Andre Noll [Sat, 30 Jul 2011 16:14:25 +0000 (18:14 +0200)]
mp3_afh: Take padding into account when computing frame duration.
Without this fix, the computed duration of a frame can be slightly
larger than its actual duration. If this happens for many frames of
an mp3 file, the chunk size will be slightly too large, which leads
to buffer underruns during streaming.
Andre Noll [Sun, 7 Aug 2011 10:33:03 +0000 (12:33 +0200)]
mp3dec: Handle decode errors gracefully.
Currently decoding damaged mp3 files leads to very audible artefacts
even if only a single frame is corrupt. This patch instructs the mp3
decoder to synchronize the stream on decode errors and to continue the
decode process. Only on fatal errors the input buffer is discarded.
Andre Noll [Thu, 14 Jul 2011 06:17:08 +0000 (08:17 +0200)]
vss: Clean up timeout computations.
By passing the sched struct to vss_compute_timeout() we can get
rid of the static the_timeout struct in vss_compute_timeout(). The
previous patch, which made the timeout helper functions of sched.c
return whether the given barrier is in the past, allows to simplify
the timeout code of vss.c a bit.
The patch also combines the general timeout computations and the
computation for FEC slices into a single function.
Andre Noll [Wed, 13 Jul 2011 19:13:32 +0000 (21:13 +0200)]
sched: Improve sched_request_barrier() and friends.
Make these functions tell its caller whether the given barrier
was in the past. This is useful for vss because for certain
barriers, no other actions should be performed before the barrier
has passed.
Andre Noll [Fri, 5 Aug 2011 10:53:46 +0000 (12:53 +0200)]
gcrypt: Return key size in bytes.
The crypto API requires get_asymmetric_key() to return the size of
the RSA key in bytes on success. The return value is evaluated in
populate_user_list() where keys which are too short to encrypt a
challenge buffer are rejected right away.
However, for ASN.1 keys, the gcrypt implementation returned the number
of *bits* instead. This caused para_server to accept keys which are
in fact not suitable for authentication.
Andre Noll [Sun, 31 Jul 2011 12:40:10 +0000 (14:40 +0200)]
afs: Fix long-standing bug in add command.
Before the add command handler adds a given audio file to the database
it asks the afs process to check whether the file already exists.
The afs process looks for rows in the audio file table with path
and/or hash identical to the given file. If a match is found a
pointer to the matching row is passed from afs to the command handler.
The get_row_pointer_from_result() helper is then called by the command
handler to extract the row pointer from the result returned by afs.
However, this helper incorrectly dereferenced the pointer which caused
the command handler to examine an address rather than the content of
the address to tell whether the file already exists and whether path
or content has changed. This could lead to changed/moved files being
ignored as well as existing files being added again.
This bug was introduced in commit 0a3b9b83, back in 2008.
Andre Noll [Thu, 21 Jul 2011 17:59:46 +0000 (19:59 +0200)]
sched: Optimize the case of zero timeouts.
If a pre_select method calls sched_min_delay() there is no
point in calling the pre_select hooks of the other tasks since
these can not decrease the timeout any further, and adding file
descriptors to the fd sets makes no sense either. So we may
break out early in sched_preselect() in this case.
If the timeout is zero we may even omit the entire select call as
well as the subsequent gettimeofday() since select() will return
immediately anyway. This patch teaches sched_postselect() to do so
which saves at least two system calls (plus locking in case of
para_server) in a rather hot path.
Andre Noll [Thu, 21 Jul 2011 17:39:03 +0000 (19:39 +0200)]
sched: Kill unnecessary check in sched_pre_select().
The only two callers of sched_shutdown() call this function
from post_select context, so we may safely remove the check
whether the pre_select list is empty.
Add a comment to sched_shutdown() which mentions that this
function must be called from post_select.
Andre Noll [Fri, 3 Jun 2011 04:58:45 +0000 (06:58 +0200)]
Don't ship generated *cmdline.[ch] files in tarball.
These files increase the size of the tarball considerably for no real
gain. Gengetopt is available as a package on all major distributions,
so simply require gengetopt.
Andre Noll [Sun, 24 Jul 2011 20:18:42 +0000 (22:18 +0200)]
alsa: Avoid busy loop.
It is possible that snd_pcm_writei() returns zero rather than -EAGAIN
in case nothing was written because the alsa buffer was already full.
Currently we try again, and eventually succeed. However, this is
ugly, burns CPU cycles and might even lead to an endless loop for
misconfigured alsa devices. So simply return from alsa_post_select()
if snd_pcm_writei() returned zero.
Andre Noll [Thu, 9 Jun 2011 22:01:09 +0000 (00:01 +0200)]
client: Do not leak buffer tree node on exit.
Currently we deallocate the buffer tree node of the client
task in case the connect fails and in audiod.c's close_stat_pipe()
but miss to free it for para_client in case of a regular connection
shutdown.
Fix this memory leak by freeing the buffer tree node in
client_close().
Andre Noll [Thu, 3 Feb 2011 16:15:39 +0000 (17:15 +0100)]
Rewrite of the osx writer.
This replaces most of the code taken from mosx-mpg123 and should
make osx_write.c much more readable, shorter and more reliable.
Since coreaudio creates a new thread which periodically calls our
callback function, some kind of coordination between the two threads
of execution is necessary.
This implementation employs a new buffer tree node and a mutex to
serialize access to the data buffers. The parent thread pushes
down all data to the child thread which consumes this data in the
callback function. Both threads grab the new mutex whenever they
access or modify the data buffers.
Andre Noll [Thu, 3 Feb 2011 16:12:53 +0000 (17:12 +0100)]
audiod get_play_time_slot_num(): Avoid possible NULL pointer dereference.
The pointer to the buffer tree node is dereferenced unconditionally
in btr_get_node_start(). This patch makes sure we never pass a NULL
pointer to this function.
Andre Noll [Thu, 9 Jun 2011 15:52:13 +0000 (17:52 +0200)]
Work around some clang warnings.
This fixes a bunch of warnings of the form
command.c:126:2: warning: expression result unused [-Wunused-value]
WRITE_STATUS_ITEM(&b, SI_MTIME, "%s\n", mtime);
when compiling with clang. This warning is bogus, because the underlying call
to para_printf() can only return failure if the max_size_handler fails, but
this handler is never called here because the size of this para_buffer is
unlimited.
Andre Noll [Mon, 4 Jul 2011 23:04:34 +0000 (01:04 +0200)]
gcrypt: Optionally use internal OAEP padding.
libgcrypt supports OAEP padding since version 1.5.0, which has just
been released. Since want the paraslash gcrypt code to work also
for older gcrypt libraries, we check the library version at runtime
and fall back to the internal OAEP padding code if an old library
was detected.
This patch moves much of the rather ugly OAEP padding code into new
new helper decode_rsa() which reduces to a mere memcpy for newer
gcrypt versions. Much of the old code can be removed once all major
distributions ship libgcrypt-1.5.0 or later.
Andre Noll [Sat, 4 Jun 2011 13:26:15 +0000 (15:26 +0200)]
Add alternative crypto implementation.
This fills gcrypt.c (which contained only dummy functions so far)
with contents.
The old openssl-based crypto API uses OAEP padding exclusively, as
this padding method is recommended for new applications which do not
have to care about backwards compatibility. Unfortunately, libcrypt
only supports the older pkcs1 padding method. Since we want older
para_client versions to be compatible with a newer para_server, even
if this para_server was compiled against libgcrypt, we must implement
our own OAEP padding functions. This turned out to be quite simple,
given the good documentation in rfc 3447.
This together with the fact that there is no ASN1 parser in libgcrypt
makes the patch quite large though.
On the other hand, SHA1, random numbers and RC4 were straight-forward
to implement using the primitives provided by libgcrypt.
Andre Noll [Mon, 7 Mar 2011 07:07:37 +0000 (08:07 +0100)]
stream cipher: Allow in-place encryption.
unlike openssl's RC4(), the RC4 implemenation of libgcrypt can encrypt
a buffer in-place. For this the "buf" argument of the various send
and receive functions must not be const.
Andre Noll [Mon, 7 Mar 2011 07:04:23 +0000 (08:04 +0100)]
crypt: Make base64_decode public.
gcrypt.c needs this to decode public rsa keys. Public functions
should always return proper error codes, so change the return
value for errors from -1 to -E_BASE64.
Andre Noll [Sat, 5 Mar 2011 20:53:54 +0000 (21:53 +0100)]
crypt: Move implementation-independent code to separate file.
This introduces crypt_common.c which contains helper functions from
crypt.c which are independent of openssl.
crypt.common.c contains two types of public functions: Frontend
functions are called by users of the crypto API, and these functions
are exported as usual through the crypt.h header file. Backend
functions, on the other hand, are expected to be called only from
the crypto implementation (i.e. from crypt.c or gcrypt.c). These
functions are exported through the new crypt_backend.h header file.
Andre Noll [Sun, 5 Jun 2011 17:14:37 +0000 (19:14 +0200)]
Clear score table on mood reload.
Whenever a blob is added, the mood event handler is called
which may reload the current mood in order to react to the
change being made. However, we missed to clear the score table
first. This is necessary to to re-insert all admissible files.
Currently this fails with
afs_event: table moods, event 8: key already exists in rbtree