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
1b5c1f75
Commit
1b5c1f75
authored
Apr 26, 2019
by
Max Kellermann
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
input/InputStreams: pass std::unique_lock<> to various methods
parent
040573c6
Hide whitespace changes
Inline
Side-by-side
Showing
33 changed files
with
212 additions
and
156 deletions
+212
-156
Bzip2ArchivePlugin.cxx
src/archive/plugins/Bzip2ArchivePlugin.cxx
+3
-2
Iso9660ArchivePlugin.cxx
src/archive/plugins/Iso9660ArchivePlugin.cxx
+4
-2
ZzipArchivePlugin.cxx
src/archive/plugins/ZzipArchivePlugin.cxx
+5
-4
FileCommands.cxx
src/command/FileCommands.cxx
+3
-3
FingerprintCommands.cxx
src/command/FingerprintCommands.cxx
+1
-1
Bridge.cxx
src/decoder/Bridge.cxx
+1
-1
Thread.cxx
src/decoder/Thread.cxx
+17
-11
AsyncInputStream.cxx
src/input/AsyncInputStream.cxx
+6
-4
AsyncInputStream.hxx
src/input/AsyncInputStream.hxx
+4
-2
BufferedInputStream.cxx
src/input/BufferedInputStream.cxx
+10
-7
BufferedInputStream.hxx
src/input/BufferedInputStream.hxx
+3
-2
FailingInputStream.hxx
src/input/FailingInputStream.hxx
+2
-2
IcyInputStream.cxx
src/input/IcyInputStream.cxx
+4
-3
IcyInputStream.hxx
src/input/IcyInputStream.hxx
+2
-1
InputStream.cxx
src/input/InputStream.cxx
+11
-11
InputStream.hxx
src/input/InputStream.hxx
+13
-7
ProxyInputStream.cxx
src/input/ProxyInputStream.cxx
+8
-6
ProxyInputStream.hxx
src/input/ProxyInputStream.hxx
+4
-2
RewindInputStream.cxx
src/input/RewindInputStream.cxx
+8
-6
ThreadInputStream.cxx
src/input/ThreadInputStream.cxx
+3
-2
ThreadInputStream.hxx
src/input/ThreadInputStream.hxx
+2
-1
CdioParanoiaInputPlugin.cxx
src/input/plugins/CdioParanoiaInputPlugin.cxx
+7
-4
FfmpegInputPlugin.cxx
src/input/plugins/FfmpegInputPlugin.cxx
+7
-4
FileInputPlugin.cxx
src/input/plugins/FileInputPlugin.cxx
+8
-4
SmbclientInputPlugin.cxx
src/input/plugins/SmbclientInputPlugin.cxx
+7
-4
Aiff.cxx
src/tag/Aiff.cxx
+5
-5
Aiff.hxx
src/tag/Aiff.hxx
+4
-1
ApeLoader.cxx
src/tag/ApeLoader.cxx
+5
-5
Id3Load.cxx
src/tag/Id3Load.cxx
+31
-29
Riff.cxx
src/tag/Riff.cxx
+5
-5
Riff.hxx
src/tag/Riff.hxx
+4
-1
TestRewindInputStream.cxx
test/TestRewindInputStream.cxx
+13
-12
run_input.cxx
test/run_input.cxx
+2
-2
No files found.
src/archive/plugins/Bzip2ArchivePlugin.cxx
View file @
1b5c1f75
...
@@ -72,7 +72,8 @@ public:
...
@@ -72,7 +72,8 @@ public:
/* virtual methods from InputStream */
/* virtual methods from InputStream */
bool
IsEOF
()
noexcept
override
;
bool
IsEOF
()
noexcept
override
;
size_t
Read
(
void
*
ptr
,
size_t
size
)
override
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
size
)
override
;
private
:
private
:
void
Open
();
void
Open
();
...
@@ -147,7 +148,7 @@ Bzip2InputStream::FillBuffer()
...
@@ -147,7 +148,7 @@ Bzip2InputStream::FillBuffer()
}
}
size_t
size_t
Bzip2InputStream
::
Read
(
void
*
ptr
,
size_t
length
)
Bzip2InputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
,
void
*
ptr
,
size_t
length
)
{
{
const
ScopeUnlock
unlock
(
mutex
);
const
ScopeUnlock
unlock
(
mutex
);
...
...
src/archive/plugins/Iso9660ArchivePlugin.cxx
View file @
1b5c1f75
...
@@ -157,7 +157,8 @@ public:
...
@@ -157,7 +157,8 @@ public:
/* virtual methods from InputStream */
/* virtual methods from InputStream */
bool
IsEOF
()
noexcept
override
;
bool
IsEOF
()
noexcept
override
;
size_t
Read
(
void
*
ptr
,
size_t
size
)
override
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
size
)
override
;
};
};
InputStreamPtr
InputStreamPtr
...
@@ -174,7 +175,8 @@ Iso9660ArchiveFile::OpenStream(const char *pathname,
...
@@ -174,7 +175,8 @@ Iso9660ArchiveFile::OpenStream(const char *pathname,
}
}
size_t
size_t
Iso9660InputStream
::
Read
(
void
*
ptr
,
size_t
read_size
)
Iso9660InputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
,
void
*
ptr
,
size_t
read_size
)
{
{
const
ScopeUnlock
unlock
(
mutex
);
const
ScopeUnlock
unlock
(
mutex
);
...
...
src/archive/plugins/ZzipArchivePlugin.cxx
View file @
1b5c1f75
...
@@ -111,8 +111,9 @@ public:
...
@@ -111,8 +111,9 @@ public:
/* virtual methods from InputStream */
/* virtual methods from InputStream */
bool
IsEOF
()
noexcept
override
;
bool
IsEOF
()
noexcept
override
;
size_t
Read
(
void
*
ptr
,
size_t
size
)
override
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
Seek
(
offset_type
offset
)
override
;
void
*
ptr
,
size_t
size
)
override
;
void
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
offset
)
override
;
};
};
InputStreamPtr
InputStreamPtr
...
@@ -130,7 +131,7 @@ ZzipArchiveFile::OpenStream(const char *pathname,
...
@@ -130,7 +131,7 @@ ZzipArchiveFile::OpenStream(const char *pathname,
}
}
size_t
size_t
ZzipInputStream
::
Read
(
void
*
ptr
,
size_t
read_size
)
ZzipInputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
,
void
*
ptr
,
size_t
read_size
)
{
{
const
ScopeUnlock
unlock
(
mutex
);
const
ScopeUnlock
unlock
(
mutex
);
...
@@ -149,7 +150,7 @@ ZzipInputStream::IsEOF() noexcept
...
@@ -149,7 +150,7 @@ ZzipInputStream::IsEOF() noexcept
}
}
void
void
ZzipInputStream
::
Seek
(
offset_type
new_offset
)
ZzipInputStream
::
Seek
(
std
::
unique_lock
<
Mutex
>
&
,
offset_type
new_offset
)
{
{
const
ScopeUnlock
unlock
(
mutex
);
const
ScopeUnlock
unlock
(
mutex
);
...
...
src/command/FileCommands.cxx
View file @
1b5c1f75
...
@@ -292,9 +292,9 @@ read_stream_art(Response &r, const char *uri, size_t offset)
...
@@ -292,9 +292,9 @@ read_stream_art(Response &r, const char *uri, size_t offset)
size_t
read_size
;
size_t
read_size
;
{
{
const
std
::
lock_guard
<
Mutex
>
protect
(
mutex
);
std
::
unique_lock
<
Mutex
>
lock
(
mutex
);
is
->
Seek
(
offset
);
is
->
Seek
(
lock
,
offset
);
read_size
=
is
->
Read
(
&
buffer
,
CHUNK_SIZE
);
read_size
=
is
->
Read
(
lock
,
&
buffer
,
CHUNK_SIZE
);
}
}
r
.
Format
(
"size: %"
PRIoffset
"
\n
"
r
.
Format
(
"size: %"
PRIoffset
"
\n
"
...
...
src/command/FingerprintCommands.cxx
View file @
1b5c1f75
...
@@ -305,7 +305,7 @@ GetChromaprintCommand::Read(InputStream &is, void *buffer, size_t length)
...
@@ -305,7 +305,7 @@ GetChromaprintCommand::Read(InputStream &is, void *buffer, size_t length)
cond
.
wait
(
lock
);
cond
.
wait
(
lock
);
}
}
return
is
.
Read
(
buffer
,
length
);
return
is
.
Read
(
lock
,
buffer
,
length
);
}
}
CommandResult
CommandResult
...
...
src/decoder/Bridge.cxx
View file @
1b5c1f75
...
@@ -403,7 +403,7 @@ try {
...
@@ -403,7 +403,7 @@ try {
dc
.
cond
.
wait
(
lock
);
dc
.
cond
.
wait
(
lock
);
}
}
size_t
nbytes
=
is
.
Read
(
buffer
,
length
);
size_t
nbytes
=
is
.
Read
(
lock
,
buffer
,
length
);
assert
(
nbytes
>
0
||
is
.
IsEOF
());
assert
(
nbytes
>
0
||
is
.
IsEOF
());
return
nbytes
;
return
nbytes
;
...
...
src/decoder/Thread.cxx
View file @
1b5c1f75
...
@@ -55,7 +55,8 @@ static constexpr Domain decoder_thread_domain("decoder_thread");
...
@@ -55,7 +55,8 @@ static constexpr Domain decoder_thread_domain("decoder_thread");
static
bool
static
bool
decoder_stream_decode
(
const
DecoderPlugin
&
plugin
,
decoder_stream_decode
(
const
DecoderPlugin
&
plugin
,
DecoderBridge
&
bridge
,
DecoderBridge
&
bridge
,
InputStream
&
input_stream
)
InputStream
&
input_stream
,
std
::
unique_lock
<
Mutex
>
&
lock
)
{
{
assert
(
plugin
.
stream_decode
!=
nullptr
);
assert
(
plugin
.
stream_decode
!=
nullptr
);
assert
(
bridge
.
stream_tag
==
nullptr
);
assert
(
bridge
.
stream_tag
==
nullptr
);
...
@@ -70,7 +71,7 @@ decoder_stream_decode(const DecoderPlugin &plugin,
...
@@ -70,7 +71,7 @@ decoder_stream_decode(const DecoderPlugin &plugin,
/* rewind the stream, so each plugin gets a fresh start */
/* rewind the stream, so each plugin gets a fresh start */
try
{
try
{
input_stream
.
Rewind
();
input_stream
.
Rewind
(
lock
);
}
catch
(...)
{
}
catch
(...)
{
}
}
...
@@ -161,6 +162,7 @@ decoder_check_plugin(const DecoderPlugin &plugin, const InputStream &is,
...
@@ -161,6 +162,7 @@ decoder_check_plugin(const DecoderPlugin &plugin, const InputStream &is,
static
bool
static
bool
decoder_run_stream_plugin
(
DecoderBridge
&
bridge
,
InputStream
&
is
,
decoder_run_stream_plugin
(
DecoderBridge
&
bridge
,
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
,
const
char
*
suffix
,
const
char
*
suffix
,
const
DecoderPlugin
&
plugin
,
const
DecoderPlugin
&
plugin
,
bool
&
tried_r
)
bool
&
tried_r
)
...
@@ -171,11 +173,12 @@ decoder_run_stream_plugin(DecoderBridge &bridge, InputStream &is,
...
@@ -171,11 +173,12 @@ decoder_run_stream_plugin(DecoderBridge &bridge, InputStream &is,
bridge
.
Reset
();
bridge
.
Reset
();
tried_r
=
true
;
tried_r
=
true
;
return
decoder_stream_decode
(
plugin
,
bridge
,
is
);
return
decoder_stream_decode
(
plugin
,
bridge
,
is
,
lock
);
}
}
static
bool
static
bool
decoder_run_stream_locked
(
DecoderBridge
&
bridge
,
InputStream
&
is
,
decoder_run_stream_locked
(
DecoderBridge
&
bridge
,
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
,
const
char
*
uri
,
bool
&
tried_r
)
const
char
*
uri
,
bool
&
tried_r
)
{
{
UriSuffixBuffer
suffix_buffer
;
UriSuffixBuffer
suffix_buffer
;
...
@@ -183,7 +186,8 @@ decoder_run_stream_locked(DecoderBridge &bridge, InputStream &is,
...
@@ -183,7 +186,8 @@ decoder_run_stream_locked(DecoderBridge &bridge, InputStream &is,
using
namespace
std
::
placeholders
;
using
namespace
std
::
placeholders
;
const
auto
f
=
std
::
bind
(
decoder_run_stream_plugin
,
const
auto
f
=
std
::
bind
(
decoder_run_stream_plugin
,
std
::
ref
(
bridge
),
std
::
ref
(
is
),
suffix
,
std
::
ref
(
bridge
),
std
::
ref
(
is
),
std
::
ref
(
lock
),
suffix
,
_1
,
std
::
ref
(
tried_r
));
_1
,
std
::
ref
(
tried_r
));
return
decoder_plugins_try
(
f
);
return
decoder_plugins_try
(
f
);
}
}
...
@@ -192,7 +196,8 @@ decoder_run_stream_locked(DecoderBridge &bridge, InputStream &is,
...
@@ -192,7 +196,8 @@ decoder_run_stream_locked(DecoderBridge &bridge, InputStream &is,
* Try decoding a stream, using the fallback plugin.
* Try decoding a stream, using the fallback plugin.
*/
*/
static
bool
static
bool
decoder_run_stream_fallback
(
DecoderBridge
&
bridge
,
InputStream
&
is
)
decoder_run_stream_fallback
(
DecoderBridge
&
bridge
,
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
)
{
{
const
struct
DecoderPlugin
*
plugin
;
const
struct
DecoderPlugin
*
plugin
;
...
@@ -202,7 +207,7 @@ decoder_run_stream_fallback(DecoderBridge &bridge, InputStream &is)
...
@@ -202,7 +207,7 @@ decoder_run_stream_fallback(DecoderBridge &bridge, InputStream &is)
plugin
=
decoder_plugin_from_name
(
"mad"
);
plugin
=
decoder_plugin_from_name
(
"mad"
);
#endif
#endif
return
plugin
!=
nullptr
&&
plugin
->
stream_decode
!=
nullptr
&&
return
plugin
!=
nullptr
&&
plugin
->
stream_decode
!=
nullptr
&&
decoder_stream_decode
(
*
plugin
,
bridge
,
is
);
decoder_stream_decode
(
*
plugin
,
bridge
,
is
,
lock
);
}
}
/**
/**
...
@@ -249,16 +254,16 @@ decoder_run_stream(DecoderBridge &bridge, const char *uri)
...
@@ -249,16 +254,16 @@ decoder_run_stream(DecoderBridge &bridge, const char *uri)
MaybeLoadReplayGain
(
bridge
,
*
input_stream
);
MaybeLoadReplayGain
(
bridge
,
*
input_stream
);
const
std
::
lock_guard
<
Mutex
>
protect
(
dc
.
mutex
);
std
::
unique_lock
<
Mutex
>
lock
(
dc
.
mutex
);
bool
tried
=
false
;
bool
tried
=
false
;
return
dc
.
command
==
DecoderCommand
::
STOP
||
return
dc
.
command
==
DecoderCommand
::
STOP
||
decoder_run_stream_locked
(
bridge
,
*
input_stream
,
uri
,
decoder_run_stream_locked
(
bridge
,
*
input_stream
,
lock
,
uri
,
tried
)
||
tried
)
||
/* fallback to mp3: this is needed for bastard streams
/* fallback to mp3: this is needed for bastard streams
that don't have a suffix or set the mimeType */
that don't have a suffix or set the mimeType */
(
!
tried
&&
(
!
tried
&&
decoder_run_stream_fallback
(
bridge
,
*
input_stream
));
decoder_run_stream_fallback
(
bridge
,
*
input_stream
,
lock
));
}
}
/**
/**
...
@@ -282,8 +287,9 @@ TryDecoderFile(DecoderBridge &bridge, Path path_fs, const char *suffix,
...
@@ -282,8 +287,9 @@ TryDecoderFile(DecoderBridge &bridge, Path path_fs, const char *suffix,
const
std
::
lock_guard
<
Mutex
>
protect
(
dc
.
mutex
);
const
std
::
lock_guard
<
Mutex
>
protect
(
dc
.
mutex
);
return
decoder_file_decode
(
plugin
,
bridge
,
path_fs
);
return
decoder_file_decode
(
plugin
,
bridge
,
path_fs
);
}
else
if
(
plugin
.
stream_decode
!=
nullptr
)
{
}
else
if
(
plugin
.
stream_decode
!=
nullptr
)
{
const
std
::
lock_guard
<
Mutex
>
protect
(
dc
.
mutex
);
std
::
unique_lock
<
Mutex
>
lock
(
dc
.
mutex
);
return
decoder_stream_decode
(
plugin
,
bridge
,
input_stream
);
return
decoder_stream_decode
(
plugin
,
bridge
,
input_stream
,
lock
);
}
else
}
else
return
false
;
return
false
;
}
}
...
...
src/input/AsyncInputStream.cxx
View file @
1b5c1f75
...
@@ -95,7 +95,8 @@ AsyncInputStream::IsEOF() noexcept
...
@@ -95,7 +95,8 @@ AsyncInputStream::IsEOF() noexcept
}
}
void
void
AsyncInputStream
::
Seek
(
offset_type
new_offset
)
AsyncInputStream
::
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
new_offset
)
{
{
assert
(
IsReady
());
assert
(
IsReady
());
assert
(
seek_state
==
SeekState
::
NONE
);
assert
(
seek_state
==
SeekState
::
NONE
);
...
@@ -136,7 +137,7 @@ AsyncInputStream::Seek(offset_type new_offset)
...
@@ -136,7 +137,7 @@ AsyncInputStream::Seek(offset_type new_offset)
CondInputStreamHandler
cond_handler
;
CondInputStreamHandler
cond_handler
;
const
ScopeExchangeInputStreamHandler
h
(
*
this
,
&
cond_handler
);
const
ScopeExchangeInputStreamHandler
h
(
*
this
,
&
cond_handler
);
while
(
seek_state
!=
SeekState
::
NONE
)
while
(
seek_state
!=
SeekState
::
NONE
)
cond_handler
.
cond
.
wait
(
mutex
);
cond_handler
.
cond
.
wait
(
lock
);
Check
();
Check
();
}
}
...
@@ -171,7 +172,8 @@ AsyncInputStream::IsAvailable() noexcept
...
@@ -171,7 +172,8 @@ AsyncInputStream::IsAvailable() noexcept
}
}
size_t
size_t
AsyncInputStream
::
Read
(
void
*
ptr
,
size_t
read_size
)
AsyncInputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
read_size
)
{
{
assert
(
!
GetEventLoop
().
IsInside
());
assert
(
!
GetEventLoop
().
IsInside
());
...
@@ -187,7 +189,7 @@ AsyncInputStream::Read(void *ptr, size_t read_size)
...
@@ -187,7 +189,7 @@ AsyncInputStream::Read(void *ptr, size_t read_size)
break
;
break
;
const
ScopeExchangeInputStreamHandler
h
(
*
this
,
&
cond_handler
);
const
ScopeExchangeInputStreamHandler
h
(
*
this
,
&
cond_handler
);
cond_handler
.
cond
.
wait
(
mutex
);
cond_handler
.
cond
.
wait
(
lock
);
}
}
const
size_t
nbytes
=
std
::
min
(
read_size
,
r
.
size
);
const
size_t
nbytes
=
std
::
min
(
read_size
,
r
.
size
);
...
...
src/input/AsyncInputStream.hxx
View file @
1b5c1f75
...
@@ -83,10 +83,12 @@ public:
...
@@ -83,10 +83,12 @@ public:
/* virtual methods from InputStream */
/* virtual methods from InputStream */
void
Check
()
final
;
void
Check
()
final
;
bool
IsEOF
()
noexcept
final
;
bool
IsEOF
()
noexcept
final
;
void
Seek
(
offset_type
new_offset
)
final
;
void
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
new_offset
)
final
;
std
::
unique_ptr
<
Tag
>
ReadTag
()
noexcept
final
;
std
::
unique_ptr
<
Tag
>
ReadTag
()
noexcept
final
;
bool
IsAvailable
()
noexcept
final
;
bool
IsAvailable
()
noexcept
final
;
size_t
Read
(
void
*
ptr
,
size_t
read_size
)
final
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
read_size
)
final
;
protected
:
protected
:
/**
/**
...
...
src/input/BufferedInputStream.cxx
View file @
1b5c1f75
...
@@ -64,7 +64,8 @@ BufferedInputStream::Check()
...
@@ -64,7 +64,8 @@ BufferedInputStream::Check()
}
}
void
void
BufferedInputStream
::
Seek
(
offset_type
new_offset
)
BufferedInputStream
::
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
new_offset
)
{
{
if
(
new_offset
>=
size
)
{
if
(
new_offset
>=
size
)
{
offset
=
size
;
offset
=
size
;
...
@@ -84,7 +85,7 @@ BufferedInputStream::Seek(offset_type new_offset)
...
@@ -84,7 +85,7 @@ BufferedInputStream::Seek(offset_type new_offset)
wake_cond
.
notify_one
();
wake_cond
.
notify_one
();
while
(
seek
)
while
(
seek
)
client_cond
.
wait
(
mutex
);
client_cond
.
wait
(
lock
);
if
(
seek_error
)
if
(
seek_error
)
std
::
rethrow_exception
(
std
::
exchange
(
seek_error
,
{}));
std
::
rethrow_exception
(
std
::
exchange
(
seek_error
,
{}));
...
@@ -105,7 +106,8 @@ BufferedInputStream::IsAvailable() noexcept
...
@@ -105,7 +106,8 @@ BufferedInputStream::IsAvailable() noexcept
}
}
size_t
size_t
BufferedInputStream
::
Read
(
void
*
ptr
,
size_t
s
)
BufferedInputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
s
)
{
{
if
(
offset
>=
size
)
if
(
offset
>=
size
)
return
0
;
return
0
;
...
@@ -140,7 +142,7 @@ BufferedInputStream::Read(void *ptr, size_t s)
...
@@ -140,7 +142,7 @@ BufferedInputStream::Read(void *ptr, size_t s)
wake_cond
.
notify_one
();
wake_cond
.
notify_one
();
}
}
client_cond
.
wait
(
mutex
);
client_cond
.
wait
(
lock
);
}
}
}
}
...
@@ -156,7 +158,7 @@ BufferedInputStream::RunThread() noexcept
...
@@ -156,7 +158,7 @@ BufferedInputStream::RunThread() noexcept
if
(
seek
)
{
if
(
seek
)
{
try
{
try
{
input
->
Seek
(
seek_offset
);
input
->
Seek
(
lock
,
seek_offset
);
}
catch
(...)
{
}
catch
(...)
{
seek_error
=
std
::
current_exception
();
seek_error
=
std
::
current_exception
();
}
}
...
@@ -183,7 +185,7 @@ BufferedInputStream::RunThread() noexcept
...
@@ -183,7 +185,7 @@ BufferedInputStream::RunThread() noexcept
offset to prepare filling
offset to prepare filling
the buffer from there */
the buffer from there */
try
{
try
{
input
->
Seek
(
offset
);
input
->
Seek
(
lock
,
offset
);
}
catch
(...)
{
}
catch
(...)
{
read_error
=
std
::
current_exception
();
read_error
=
std
::
current_exception
();
client_cond
.
notify_one
();
client_cond
.
notify_one
();
...
@@ -195,7 +197,8 @@ BufferedInputStream::RunThread() noexcept
...
@@ -195,7 +197,8 @@ BufferedInputStream::RunThread() noexcept
}
}
try
{
try
{
size_t
nbytes
=
input
->
Read
(
w
.
data
,
w
.
size
);
size_t
nbytes
=
input
->
Read
(
lock
,
w
.
data
,
w
.
size
);
buffer
.
Commit
(
read_offset
,
buffer
.
Commit
(
read_offset
,
read_offset
+
nbytes
);
read_offset
+
nbytes
);
}
catch
(...)
{
}
catch
(...)
{
...
...
src/input/BufferedInputStream.hxx
View file @
1b5c1f75
...
@@ -85,12 +85,13 @@ public:
...
@@ -85,12 +85,13 @@ public:
/* we don't need to implement Update() because all attributes
/* we don't need to implement Update() because all attributes
have been copied already in our constructor */
have been copied already in our constructor */
//void Update() noexcept;
//void Update() noexcept;
void
Seek
(
offset_type
offset
)
override
;
void
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
offset
)
override
;
bool
IsEOF
()
noexcept
override
;
bool
IsEOF
()
noexcept
override
;
/* we don't support tags */
/* we don't support tags */
// std::unique_ptr<Tag> ReadTag() override;
// std::unique_ptr<Tag> ReadTag() override;
bool
IsAvailable
()
noexcept
override
;
bool
IsAvailable
()
noexcept
override
;
size_t
Read
(
void
*
ptr
,
size_t
size
)
override
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
size
)
override
;
/* virtual methods from class InputStreamHandler */
/* virtual methods from class InputStreamHandler */
void
OnInputStreamReady
()
noexcept
override
{
void
OnInputStreamReady
()
noexcept
override
{
...
...
src/input/FailingInputStream.hxx
View file @
1b5c1f75
...
@@ -45,7 +45,7 @@ public:
...
@@ -45,7 +45,7 @@ public:
std
::
rethrow_exception
(
error
);
std
::
rethrow_exception
(
error
);
}
}
void
Seek
(
offset_type
)
override
{
void
Seek
(
std
::
unique_lock
<
Mutex
>
&
,
offset_type
)
override
{
std
::
rethrow_exception
(
error
);
std
::
rethrow_exception
(
error
);
}
}
...
@@ -53,7 +53,7 @@ public:
...
@@ -53,7 +53,7 @@ public:
return
false
;
return
false
;
}
}
size_t
Read
(
void
*
,
size_t
)
override
{
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
,
void
*
,
size_t
)
override
{
std
::
rethrow_exception
(
error
);
std
::
rethrow_exception
(
error
);
}
}
};
};
...
...
src/input/IcyInputStream.cxx
View file @
1b5c1f75
...
@@ -80,13 +80,14 @@ IcyInputStream::ReadTag() noexcept
...
@@ -80,13 +80,14 @@ IcyInputStream::ReadTag() noexcept
}
}
size_t
size_t
IcyInputStream
::
Read
(
void
*
ptr
,
size_t
read_size
)
IcyInputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
read_size
)
{
{
if
(
!
IsEnabled
())
if
(
!
IsEnabled
())
return
ProxyInputStream
::
Read
(
ptr
,
read_size
);
return
ProxyInputStream
::
Read
(
lock
,
ptr
,
read_size
);
while
(
true
)
{
while
(
true
)
{
size_t
nbytes
=
ProxyInputStream
::
Read
(
ptr
,
read_size
);
size_t
nbytes
=
ProxyInputStream
::
Read
(
lock
,
ptr
,
read_size
);
if
(
nbytes
==
0
)
if
(
nbytes
==
0
)
return
0
;
return
0
;
...
...
src/input/IcyInputStream.hxx
View file @
1b5c1f75
...
@@ -66,7 +66,8 @@ public:
...
@@ -66,7 +66,8 @@ public:
/* virtual methods from InputStream */
/* virtual methods from InputStream */
void
Update
()
noexcept
override
;
void
Update
()
noexcept
override
;
std
::
unique_ptr
<
Tag
>
ReadTag
()
noexcept
override
;
std
::
unique_ptr
<
Tag
>
ReadTag
()
noexcept
override
;
size_t
Read
(
void
*
ptr
,
size_t
size
)
override
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
size
)
override
;
};
};
#endif
#endif
src/input/InputStream.cxx
View file @
1b5c1f75
...
@@ -72,7 +72,7 @@ InputStream::CheapSeeking() const noexcept
...
@@ -72,7 +72,7 @@ InputStream::CheapSeeking() const noexcept
}
}
void
void
InputStream
::
Seek
(
gcc_unused
offset_type
new_offset
)
InputStream
::
Seek
(
std
::
unique_lock
<
Mutex
>
&
,
gcc_unused
offset_type
new_offset
)
{
{
throw
std
::
runtime_error
(
"Seeking is not implemented"
);
throw
std
::
runtime_error
(
"Seeking is not implemented"
);
}
}
...
@@ -80,15 +80,15 @@ InputStream::Seek(gcc_unused offset_type new_offset)
...
@@ -80,15 +80,15 @@ InputStream::Seek(gcc_unused offset_type new_offset)
void
void
InputStream
::
LockSeek
(
offset_type
_offset
)
InputStream
::
LockSeek
(
offset_type
_offset
)
{
{
const
std
::
lock_guard
<
Mutex
>
protect
(
mutex
);
std
::
unique_lock
<
Mutex
>
lock
(
mutex
);
Seek
(
_offset
);
Seek
(
lock
,
_offset
);
}
}
void
void
InputStream
::
LockSkip
(
offset_type
_offset
)
InputStream
::
LockSkip
(
offset_type
_offset
)
{
{
const
std
::
lock_guard
<
Mutex
>
protect
(
mutex
);
std
::
unique_lock
<
Mutex
>
lock
(
mutex
);
Skip
(
_offset
);
Skip
(
lock
,
_offset
);
}
}
std
::
unique_ptr
<
Tag
>
std
::
unique_ptr
<
Tag
>
...
@@ -119,18 +119,18 @@ InputStream::LockRead(void *ptr, size_t _size)
...
@@ -119,18 +119,18 @@ InputStream::LockRead(void *ptr, size_t _size)
#endif
#endif
assert
(
_size
>
0
);
assert
(
_size
>
0
);
const
std
::
lock_guard
<
Mutex
>
protect
(
mutex
);
std
::
unique_lock
<
Mutex
>
lock
(
mutex
);
return
Read
(
ptr
,
_size
);
return
Read
(
lock
,
ptr
,
_size
);
}
}
void
void
InputStream
::
ReadFull
(
void
*
_ptr
,
size_t
_size
)
InputStream
::
ReadFull
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
_ptr
,
size_t
_size
)
{
{
uint8_t
*
ptr
=
(
uint8_t
*
)
_ptr
;
uint8_t
*
ptr
=
(
uint8_t
*
)
_ptr
;
size_t
nbytes_total
=
0
;
size_t
nbytes_total
=
0
;
while
(
_size
>
0
)
{
while
(
_size
>
0
)
{
size_t
nbytes
=
Read
(
ptr
+
nbytes_total
,
_size
);
size_t
nbytes
=
Read
(
lock
,
ptr
+
nbytes_total
,
_size
);
if
(
nbytes
==
0
)
if
(
nbytes
==
0
)
throw
std
::
runtime_error
(
"Unexpected end of file"
);
throw
std
::
runtime_error
(
"Unexpected end of file"
);
...
@@ -148,8 +148,8 @@ InputStream::LockReadFull(void *ptr, size_t _size)
...
@@ -148,8 +148,8 @@ InputStream::LockReadFull(void *ptr, size_t _size)
#endif
#endif
assert
(
_size
>
0
);
assert
(
_size
>
0
);
const
std
::
lock_guard
<
Mutex
>
protect
(
mutex
);
std
::
unique_lock
<
Mutex
>
lock
(
mutex
);
ReadFull
(
ptr
,
_size
);
ReadFull
(
lock
,
ptr
,
_size
);
}
}
bool
bool
...
...
src/input/InputStream.hxx
View file @
1b5c1f75
...
@@ -271,9 +271,11 @@ public:
...
@@ -271,9 +271,11 @@ public:
*
*
* Throws std::runtime_error on error.
* Throws std::runtime_error on error.
*
*
* @param lock the locked mutex; may be used to wait on
* condition variables
* @param offset the relative offset
* @param offset the relative offset
*/
*/
virtual
void
Seek
(
offset_type
offset
);
virtual
void
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
offset
);
/**
/**
* Wrapper for Seek() which locks and unlocks the mutex; the
* Wrapper for Seek() which locks and unlocks the mutex; the
...
@@ -285,8 +287,8 @@ public:
...
@@ -285,8 +287,8 @@ public:
* Rewind to the beginning of the stream. This is a wrapper
* Rewind to the beginning of the stream. This is a wrapper
* for Seek(0, error).
* for Seek(0, error).
*/
*/
void
Rewind
()
{
void
Rewind
(
std
::
unique_lock
<
Mutex
>
&
lock
)
{
Seek
(
0
);
Seek
(
lock
,
0
);
}
}
void
LockRewind
()
{
void
LockRewind
()
{
...
@@ -296,8 +298,9 @@ public:
...
@@ -296,8 +298,9 @@ public:
/**
/**
* Skip input bytes.
* Skip input bytes.
*/
*/
void
Skip
(
offset_type
_offset
)
{
void
Skip
(
std
::
unique_lock
<
Mutex
>
&
lock
,
Seek
(
GetOffset
()
+
_offset
);
offset_type
_offset
)
{
Seek
(
lock
,
GetOffset
()
+
_offset
);
}
}
void
LockSkip
(
offset_type
_offset
);
void
LockSkip
(
offset_type
_offset
);
...
@@ -351,12 +354,15 @@ public:
...
@@ -351,12 +354,15 @@ public:
*
*
* Throws std::runtime_error on error.
* Throws std::runtime_error on error.
*
*
* @param lock the locked mutex; may be used to wait on
* condition variables
* @param ptr the buffer to read into
* @param ptr the buffer to read into
* @param size the maximum number of bytes to read
* @param size the maximum number of bytes to read
* @return the number of bytes read
* @return the number of bytes read
*/
*/
gcc_nonnull_all
gcc_nonnull_all
virtual
size_t
Read
(
void
*
ptr
,
size_t
size
)
=
0
;
virtual
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
size
)
=
0
;
/**
/**
* Wrapper for Read() which locks and unlocks the mutex;
* Wrapper for Read() which locks and unlocks the mutex;
...
@@ -379,7 +385,7 @@ public:
...
@@ -379,7 +385,7 @@ public:
* @return true if the whole data was read, false otherwise.
* @return true if the whole data was read, false otherwise.
*/
*/
gcc_nonnull_all
gcc_nonnull_all
void
ReadFull
(
void
*
ptr
,
size_t
size
);
void
ReadFull
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
size
);
/**
/**
* Wrapper for ReadFull() which locks and unlocks the mutex;
* Wrapper for ReadFull() which locks and unlocks the mutex;
...
...
src/input/ProxyInputStream.cxx
View file @
1b5c1f75
...
@@ -89,12 +89,13 @@ ProxyInputStream::Update() noexcept
...
@@ -89,12 +89,13 @@ ProxyInputStream::Update() noexcept
}
}
void
void
ProxyInputStream
::
Seek
(
offset_type
new_offset
)
ProxyInputStream
::
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
new_offset
)
{
{
while
(
!
input
)
while
(
!
input
)
set_input_cond
.
wait
(
mutex
);
set_input_cond
.
wait
(
lock
);
input
->
Seek
(
new_offset
);
input
->
Seek
(
lock
,
new_offset
);
CopyAttributes
();
CopyAttributes
();
}
}
...
@@ -120,12 +121,13 @@ ProxyInputStream::IsAvailable() noexcept
...
@@ -120,12 +121,13 @@ ProxyInputStream::IsAvailable() noexcept
}
}
size_t
size_t
ProxyInputStream
::
Read
(
void
*
ptr
,
size_t
read_size
)
ProxyInputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
read_size
)
{
{
while
(
!
input
)
while
(
!
input
)
set_input_cond
.
wait
(
mutex
);
set_input_cond
.
wait
(
lock
);
size_t
nbytes
=
input
->
Read
(
ptr
,
read_size
);
size_t
nbytes
=
input
->
Read
(
lock
,
ptr
,
read_size
);
CopyAttributes
();
CopyAttributes
();
return
nbytes
;
return
nbytes
;
}
}
src/input/ProxyInputStream.hxx
View file @
1b5c1f75
...
@@ -60,11 +60,13 @@ public:
...
@@ -60,11 +60,13 @@ public:
/* virtual methods from InputStream */
/* virtual methods from InputStream */
void
Check
()
override
;
void
Check
()
override
;
void
Update
()
noexcept
override
;
void
Update
()
noexcept
override
;
void
Seek
(
offset_type
new_offset
)
override
;
void
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
new_offset
)
override
;
bool
IsEOF
()
noexcept
override
;
bool
IsEOF
()
noexcept
override
;
std
::
unique_ptr
<
Tag
>
ReadTag
()
noexcept
override
;
std
::
unique_ptr
<
Tag
>
ReadTag
()
noexcept
override
;
bool
IsAvailable
()
noexcept
override
;
bool
IsAvailable
()
noexcept
override
;
size_t
Read
(
void
*
ptr
,
size_t
read_size
)
override
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
read_size
)
override
;
protected
:
protected
:
/**
/**
...
...
src/input/RewindInputStream.cxx
View file @
1b5c1f75
...
@@ -60,8 +60,9 @@ public:
...
@@ -60,8 +60,9 @@ public:
return
!
ReadingFromBuffer
()
&&
ProxyInputStream
::
IsEOF
();
return
!
ReadingFromBuffer
()
&&
ProxyInputStream
::
IsEOF
();
}
}
size_t
Read
(
void
*
ptr
,
size_t
size
)
override
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
Seek
(
offset_type
offset
)
override
;
void
*
ptr
,
size_t
size
)
override
;
void
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
offset
)
override
;
private
:
private
:
/**
/**
...
@@ -74,7 +75,8 @@ private:
...
@@ -74,7 +75,8 @@ private:
};
};
size_t
size_t
RewindInputStream
::
Read
(
void
*
ptr
,
size_t
read_size
)
RewindInputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
read_size
)
{
{
if
(
ReadingFromBuffer
())
{
if
(
ReadingFromBuffer
())
{
/* buffered read */
/* buffered read */
...
@@ -93,7 +95,7 @@ RewindInputStream::Read(void *ptr, size_t read_size)
...
@@ -93,7 +95,7 @@ RewindInputStream::Read(void *ptr, size_t read_size)
}
else
{
}
else
{
/* pass method call to underlying stream */
/* pass method call to underlying stream */
size_t
nbytes
=
input
->
Read
(
ptr
,
read_size
);
size_t
nbytes
=
input
->
Read
(
lock
,
ptr
,
read_size
);
if
(
input
->
GetOffset
()
>
(
offset_type
)
sizeof
(
buffer
))
if
(
input
->
GetOffset
()
>
(
offset_type
)
sizeof
(
buffer
))
/* disable buffering */
/* disable buffering */
...
@@ -114,7 +116,7 @@ RewindInputStream::Read(void *ptr, size_t read_size)
...
@@ -114,7 +116,7 @@ RewindInputStream::Read(void *ptr, size_t read_size)
}
}
void
void
RewindInputStream
::
Seek
(
offset_type
new_offset
)
RewindInputStream
::
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
new_offset
)
{
{
assert
(
IsReady
());
assert
(
IsReady
());
...
@@ -132,7 +134,7 @@ RewindInputStream::Seek(offset_type new_offset)
...
@@ -132,7 +134,7 @@ RewindInputStream::Seek(offset_type new_offset)
buffered range now */
buffered range now */
tail
=
0
;
tail
=
0
;
ProxyInputStream
::
Seek
(
new_offset
);
ProxyInputStream
::
Seek
(
lock
,
new_offset
);
}
}
}
}
...
...
src/input/ThreadInputStream.cxx
View file @
1b5c1f75
...
@@ -130,7 +130,8 @@ ThreadInputStream::IsAvailable() noexcept
...
@@ -130,7 +130,8 @@ ThreadInputStream::IsAvailable() noexcept
}
}
inline
size_t
inline
size_t
ThreadInputStream
::
Read
(
void
*
ptr
,
size_t
read_size
)
ThreadInputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
read_size
)
{
{
assert
(
!
thread
.
IsInside
());
assert
(
!
thread
.
IsInside
());
...
@@ -154,7 +155,7 @@ ThreadInputStream::Read(void *ptr, size_t read_size)
...
@@ -154,7 +155,7 @@ ThreadInputStream::Read(void *ptr, size_t read_size)
return
0
;
return
0
;
const
ScopeExchangeInputStreamHandler
h
(
*
this
,
&
cond_handler
);
const
ScopeExchangeInputStreamHandler
h
(
*
this
,
&
cond_handler
);
cond_handler
.
cond
.
wait
(
mutex
);
cond_handler
.
cond
.
wait
(
lock
);
}
}
}
}
...
...
src/input/ThreadInputStream.hxx
View file @
1b5c1f75
...
@@ -94,7 +94,8 @@ public:
...
@@ -94,7 +94,8 @@ public:
void
Check
()
override
final
;
void
Check
()
override
final
;
bool
IsEOF
()
noexcept
final
;
bool
IsEOF
()
noexcept
final
;
bool
IsAvailable
()
noexcept
final
;
bool
IsAvailable
()
noexcept
final
;
size_t
Read
(
void
*
ptr
,
size_t
size
)
override
final
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
*
ptr
,
size_t
size
)
override
final
;
protected
:
protected
:
/**
/**
...
...
src/input/plugins/CdioParanoiaInputPlugin.cxx
View file @
1b5c1f75
...
@@ -91,8 +91,9 @@ class CdioParanoiaInputStream final : public InputStream {
...
@@ -91,8 +91,9 @@ class CdioParanoiaInputStream final : public InputStream {
/* virtual methods from InputStream */
/* virtual methods from InputStream */
bool
IsEOF
()
noexcept
override
;
bool
IsEOF
()
noexcept
override
;
size_t
Read
(
void
*
ptr
,
size_t
size
)
override
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
Seek
(
offset_type
offset
)
override
;
void
*
ptr
,
size_t
size
)
override
;
void
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
offset
)
override
;
};
};
static
constexpr
Domain
cdio_domain
(
"cdio"
);
static
constexpr
Domain
cdio_domain
(
"cdio"
);
...
@@ -255,7 +256,8 @@ input_cdio_open(const char *uri,
...
@@ -255,7 +256,8 @@ input_cdio_open(const char *uri,
}
}
void
void
CdioParanoiaInputStream
::
Seek
(
offset_type
new_offset
)
CdioParanoiaInputStream
::
Seek
(
std
::
unique_lock
<
Mutex
>
&
,
offset_type
new_offset
)
{
{
if
(
new_offset
>
size
)
if
(
new_offset
>
size
)
throw
FormatRuntimeError
(
"Invalid offset to seek %ld (%ld)"
,
throw
FormatRuntimeError
(
"Invalid offset to seek %ld (%ld)"
,
...
@@ -276,7 +278,8 @@ CdioParanoiaInputStream::Seek(offset_type new_offset)
...
@@ -276,7 +278,8 @@ CdioParanoiaInputStream::Seek(offset_type new_offset)
}
}
size_t
size_t
CdioParanoiaInputStream
::
Read
(
void
*
ptr
,
size_t
length
)
CdioParanoiaInputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
,
void
*
ptr
,
size_t
length
)
{
{
size_t
nbytes
=
0
;
size_t
nbytes
=
0
;
char
*
wptr
=
(
char
*
)
ptr
;
char
*
wptr
=
(
char
*
)
ptr
;
...
...
src/input/plugins/FfmpegInputPlugin.cxx
View file @
1b5c1f75
...
@@ -49,8 +49,10 @@ public:
...
@@ -49,8 +49,10 @@ public:
/* virtual methods from InputStream */
/* virtual methods from InputStream */
bool
IsEOF
()
noexcept
override
;
bool
IsEOF
()
noexcept
override
;
size_t
Read
(
void
*
ptr
,
size_t
size
)
override
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
Seek
(
offset_type
offset
)
override
;
void
*
ptr
,
size_t
size
)
override
;
void
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
offset
)
override
;
};
};
gcc_const
gcc_const
...
@@ -79,7 +81,8 @@ input_ffmpeg_open(const char *uri,
...
@@ -79,7 +81,8 @@ input_ffmpeg_open(const char *uri,
}
}
size_t
size_t
FfmpegInputStream
::
Read
(
void
*
ptr
,
size_t
read_size
)
FfmpegInputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
,
void
*
ptr
,
size_t
read_size
)
{
{
size_t
result
;
size_t
result
;
...
@@ -99,7 +102,7 @@ FfmpegInputStream::IsEOF() noexcept
...
@@ -99,7 +102,7 @@ FfmpegInputStream::IsEOF() noexcept
}
}
void
void
FfmpegInputStream
::
Seek
(
offset_type
new_offset
)
FfmpegInputStream
::
Seek
(
std
::
unique_lock
<
Mutex
>
&
,
offset_type
new_offset
)
{
{
uint64_t
result
;
uint64_t
result
;
...
...
src/input/plugins/FileInputPlugin.cxx
View file @
1b5c1f75
...
@@ -48,8 +48,10 @@ public:
...
@@ -48,8 +48,10 @@ public:
return
GetOffset
()
>=
GetSize
();
return
GetOffset
()
>=
GetSize
();
}
}
size_t
Read
(
void
*
ptr
,
size_t
size
)
override
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
Seek
(
offset_type
offset
)
override
;
void
*
ptr
,
size_t
size
)
override
;
void
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
offset
)
override
;
};
};
InputStreamPtr
InputStreamPtr
...
@@ -74,7 +76,8 @@ OpenFileInputStream(Path path, Mutex &mutex)
...
@@ -74,7 +76,8 @@ OpenFileInputStream(Path path, Mutex &mutex)
}
}
void
void
FileInputStream
::
Seek
(
offset_type
new_offset
)
FileInputStream
::
Seek
(
std
::
unique_lock
<
Mutex
>
&
,
offset_type
new_offset
)
{
{
{
{
const
ScopeUnlock
unlock
(
mutex
);
const
ScopeUnlock
unlock
(
mutex
);
...
@@ -85,7 +88,8 @@ FileInputStream::Seek(offset_type new_offset)
...
@@ -85,7 +88,8 @@ FileInputStream::Seek(offset_type new_offset)
}
}
size_t
size_t
FileInputStream
::
Read
(
void
*
ptr
,
size_t
read_size
)
FileInputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
,
void
*
ptr
,
size_t
read_size
)
{
{
size_t
nbytes
;
size_t
nbytes
;
...
...
src/input/plugins/SmbclientInputPlugin.cxx
View file @
1b5c1f75
...
@@ -56,8 +56,9 @@ public:
...
@@ -56,8 +56,9 @@ public:
return
offset
>=
size
;
return
offset
>=
size
;
}
}
size_t
Read
(
void
*
ptr
,
size_t
size
)
override
;
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
lock
,
void
Seek
(
offset_type
offset
)
override
;
void
*
ptr
,
size_t
size
)
override
;
void
Seek
(
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
offset
)
override
;
};
};
/*
/*
...
@@ -118,7 +119,8 @@ input_smbclient_open(const char *uri,
...
@@ -118,7 +119,8 @@ input_smbclient_open(const char *uri,
}
}
size_t
size_t
SmbclientInputStream
::
Read
(
void
*
ptr
,
size_t
read_size
)
SmbclientInputStream
::
Read
(
std
::
unique_lock
<
Mutex
>
&
,
void
*
ptr
,
size_t
read_size
)
{
{
ssize_t
nbytes
;
ssize_t
nbytes
;
...
@@ -136,7 +138,8 @@ SmbclientInputStream::Read(void *ptr, size_t read_size)
...
@@ -136,7 +138,8 @@ SmbclientInputStream::Read(void *ptr, size_t read_size)
}
}
void
void
SmbclientInputStream
::
Seek
(
offset_type
new_offset
)
SmbclientInputStream
::
Seek
(
std
::
unique_lock
<
Mutex
>
&
,
offset_type
new_offset
)
{
{
off_t
result
;
off_t
result
;
...
...
src/tag/Aiff.cxx
View file @
1b5c1f75
...
@@ -39,14 +39,14 @@ struct aiff_chunk_header {
...
@@ -39,14 +39,14 @@ struct aiff_chunk_header {
};
};
size_t
size_t
aiff_seek_id3
(
InputStream
&
is
)
aiff_seek_id3
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
)
{
{
/* seek to the beginning and read the AIFF header */
/* seek to the beginning and read the AIFF header */
is
.
Rewind
();
is
.
Rewind
(
lock
);
aiff_header
header
;
aiff_header
header
;
is
.
ReadFull
(
&
header
,
sizeof
(
header
));
is
.
ReadFull
(
lock
,
&
header
,
sizeof
(
header
));
if
(
memcmp
(
header
.
id
,
"FORM"
,
4
)
!=
0
||
if
(
memcmp
(
header
.
id
,
"FORM"
,
4
)
!=
0
||
(
is
.
KnownSize
()
&&
FromBE32
(
header
.
size
)
>
is
.
GetSize
())
||
(
is
.
KnownSize
()
&&
FromBE32
(
header
.
size
)
>
is
.
GetSize
())
||
(
memcmp
(
header
.
format
,
"AIFF"
,
4
)
!=
0
&&
(
memcmp
(
header
.
format
,
"AIFF"
,
4
)
!=
0
&&
...
@@ -57,7 +57,7 @@ aiff_seek_id3(InputStream &is)
...
@@ -57,7 +57,7 @@ aiff_seek_id3(InputStream &is)
/* read the chunk header */
/* read the chunk header */
aiff_chunk_header
chunk
;
aiff_chunk_header
chunk
;
is
.
ReadFull
(
&
chunk
,
sizeof
(
chunk
));
is
.
ReadFull
(
lock
,
&
chunk
,
sizeof
(
chunk
));
size_t
size
=
FromBE32
(
chunk
.
size
);
size_t
size
=
FromBE32
(
chunk
.
size
);
if
(
size
>
size_t
(
std
::
numeric_limits
<
int
>::
max
()))
if
(
size
>
size_t
(
std
::
numeric_limits
<
int
>::
max
()))
...
@@ -73,6 +73,6 @@ aiff_seek_id3(InputStream &is)
...
@@ -73,6 +73,6 @@ aiff_seek_id3(InputStream &is)
/* pad byte */
/* pad byte */
++
size
;
++
size
;
is
.
Skip
(
size
);
is
.
Skip
(
lock
,
size
);
}
}
}
}
src/tag/Aiff.hxx
View file @
1b5c1f75
...
@@ -25,9 +25,12 @@
...
@@ -25,9 +25,12 @@
#ifndef MPD_AIFF_HXX
#ifndef MPD_AIFF_HXX
#define MPD_AIFF_HXX
#define MPD_AIFF_HXX
#include <mutex>
#include <stddef.h>
#include <stddef.h>
class
InputStream
;
class
InputStream
;
class
Mutex
;
/**
/**
* Seeks the AIFF file to the ID3 chunk.
* Seeks the AIFF file to the ID3 chunk.
...
@@ -38,6 +41,6 @@ class InputStream;
...
@@ -38,6 +41,6 @@ class InputStream;
* @return the size of the ID3 chunk
* @return the size of the ID3 chunk
*/
*/
size_t
size_t
aiff_seek_id3
(
InputStream
&
is
);
aiff_seek_id3
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
);
#endif
#endif
src/tag/ApeLoader.cxx
View file @
1b5c1f75
...
@@ -40,15 +40,15 @@ struct ApeFooter {
...
@@ -40,15 +40,15 @@ struct ApeFooter {
bool
bool
tag_ape_scan
(
InputStream
&
is
,
ApeTagCallback
callback
)
tag_ape_scan
(
InputStream
&
is
,
ApeTagCallback
callback
)
try
{
try
{
const
std
::
lock_guard
<
Mutex
>
protect
(
is
.
mutex
);
std
::
unique_lock
<
Mutex
>
lock
(
is
.
mutex
);
if
(
!
is
.
KnownSize
()
||
!
is
.
CheapSeeking
())
if
(
!
is
.
KnownSize
()
||
!
is
.
CheapSeeking
())
return
false
;
return
false
;
/* determine if file has an apeV2 tag */
/* determine if file has an apeV2 tag */
ApeFooter
footer
;
ApeFooter
footer
;
is
.
Seek
(
is
.
GetSize
()
-
sizeof
(
footer
));
is
.
Seek
(
lock
,
is
.
GetSize
()
-
sizeof
(
footer
));
is
.
ReadFull
(
&
footer
,
sizeof
(
footer
));
is
.
ReadFull
(
lock
,
&
footer
,
sizeof
(
footer
));
if
(
memcmp
(
footer
.
id
,
"APETAGEX"
,
sizeof
(
footer
.
id
))
!=
0
||
if
(
memcmp
(
footer
.
id
,
"APETAGEX"
,
sizeof
(
footer
.
id
))
!=
0
||
FromLE32
(
footer
.
version
)
!=
2000
)
FromLE32
(
footer
.
version
)
!=
2000
)
...
@@ -61,14 +61,14 @@ try {
...
@@ -61,14 +61,14 @@ try {
remaining
>
1024
*
1024
)
remaining
>
1024
*
1024
)
return
false
;
return
false
;
is
.
Seek
(
is
.
GetSize
()
-
remaining
);
is
.
Seek
(
lock
,
is
.
GetSize
()
-
remaining
);
/* read tag into buffer */
/* read tag into buffer */
remaining
-=
sizeof
(
footer
);
remaining
-=
sizeof
(
footer
);
assert
(
remaining
>
10
);
assert
(
remaining
>
10
);
std
::
unique_ptr
<
char
[]
>
buffer
(
new
char
[
remaining
]);
std
::
unique_ptr
<
char
[]
>
buffer
(
new
char
[
remaining
]);
is
.
ReadFull
(
buffer
.
get
(),
remaining
);
is
.
ReadFull
(
lock
,
buffer
.
get
(),
remaining
);
/* read tags */
/* read tags */
unsigned
n
=
FromLE32
(
footer
.
count
);
unsigned
n
=
FromLE32
(
footer
.
count
);
...
...
src/tag/Id3Load.cxx
View file @
1b5c1f75
...
@@ -37,11 +37,12 @@ tag_is_id3v1(struct id3_tag *tag) noexcept
...
@@ -37,11 +37,12 @@ tag_is_id3v1(struct id3_tag *tag) noexcept
}
}
static
long
static
long
get_id3v2_footer_size
(
InputStream
&
is
,
offset_type
offset
)
get_id3v2_footer_size
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
offset
)
try
{
try
{
id3_byte_t
buf
[
ID3_TAG_QUERYSIZE
];
id3_byte_t
buf
[
ID3_TAG_QUERYSIZE
];
is
.
Seek
(
offset
);
is
.
Seek
(
lock
,
offset
);
is
.
ReadFull
(
buf
,
sizeof
(
buf
));
is
.
ReadFull
(
lock
,
buf
,
sizeof
(
buf
));
return
id3_tag_query
(
buf
,
sizeof
(
buf
));
return
id3_tag_query
(
buf
,
sizeof
(
buf
));
}
catch
(...)
{
}
catch
(...)
{
...
@@ -49,10 +50,10 @@ try {
...
@@ -49,10 +50,10 @@ try {
}
}
static
UniqueId3Tag
static
UniqueId3Tag
ReadId3Tag
(
InputStream
&
is
)
ReadId3Tag
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
)
try
{
try
{
id3_byte_t
query_buffer
[
ID3_TAG_QUERYSIZE
];
id3_byte_t
query_buffer
[
ID3_TAG_QUERYSIZE
];
is
.
ReadFull
(
query_buffer
,
sizeof
(
query_buffer
));
is
.
ReadFull
(
lock
,
query_buffer
,
sizeof
(
query_buffer
));
/* Look for a tag header */
/* Look for a tag header */
long
tag_size
=
id3_tag_query
(
query_buffer
,
sizeof
(
query_buffer
));
long
tag_size
=
id3_tag_query
(
query_buffer
,
sizeof
(
query_buffer
));
...
@@ -72,7 +73,7 @@ try {
...
@@ -72,7 +73,7 @@ try {
/* now read the remaining bytes */
/* now read the remaining bytes */
const
size_t
remaining
=
tag_size
-
sizeof
(
query_buffer
);
const
size_t
remaining
=
tag_size
-
sizeof
(
query_buffer
);
is
.
ReadFull
(
end
,
remaining
);
is
.
ReadFull
(
lock
,
end
,
remaining
);
return
UniqueId3Tag
(
id3_tag_parse
(
tag_buffer
.
get
(),
tag_size
));
return
UniqueId3Tag
(
id3_tag_parse
(
tag_buffer
.
get
(),
tag_size
));
}
catch
(...)
{
}
catch
(...)
{
...
@@ -80,20 +81,20 @@ try {
...
@@ -80,20 +81,20 @@ try {
}
}
static
UniqueId3Tag
static
UniqueId3Tag
ReadId3Tag
(
InputStream
&
is
,
offset_type
offset
)
ReadId3Tag
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
offset
)
try
{
try
{
is
.
Seek
(
offset
);
is
.
Seek
(
lock
,
offset
);
return
ReadId3Tag
(
is
);
return
ReadId3Tag
(
is
,
lock
);
}
catch
(...)
{
}
catch
(...)
{
return
nullptr
;
return
nullptr
;
}
}
static
UniqueId3Tag
static
UniqueId3Tag
ReadId3v1Tag
(
InputStream
&
is
)
ReadId3v1Tag
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
)
try
{
try
{
id3_byte_t
buffer
[
ID3V1_SIZE
];
id3_byte_t
buffer
[
ID3V1_SIZE
];
is
.
ReadFull
(
buffer
,
ID3V1_SIZE
);
is
.
ReadFull
(
lock
,
buffer
,
ID3V1_SIZE
);
return
UniqueId3Tag
(
id3_tag_parse
(
buffer
,
ID3V1_SIZE
));
return
UniqueId3Tag
(
id3_tag_parse
(
buffer
,
ID3V1_SIZE
));
}
catch
(...)
{
}
catch
(...)
{
...
@@ -101,18 +102,19 @@ try {
...
@@ -101,18 +102,19 @@ try {
}
}
static
UniqueId3Tag
static
UniqueId3Tag
ReadId3v1Tag
(
InputStream
&
is
,
offset_type
offset
)
ReadId3v1Tag
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
,
offset_type
offset
)
try
{
try
{
is
.
Seek
(
offset
);
is
.
Seek
(
lock
,
offset
);
return
ReadId3v1Tag
(
is
);
return
ReadId3v1Tag
(
is
,
lock
);
}
catch
(...)
{
}
catch
(...)
{
return
nullptr
;
return
nullptr
;
}
}
static
UniqueId3Tag
static
UniqueId3Tag
tag_id3_find_from_beginning
(
InputStream
&
is
)
tag_id3_find_from_beginning
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
)
try
{
try
{
auto
tag
=
ReadId3Tag
(
is
);
auto
tag
=
ReadId3Tag
(
is
,
lock
);
if
(
!
tag
)
{
if
(
!
tag
)
{
return
nullptr
;
return
nullptr
;
}
else
if
(
tag_is_id3v1
(
tag
.
get
()))
{
}
else
if
(
tag_is_id3v1
(
tag
.
get
()))
{
...
@@ -129,7 +131,7 @@ try {
...
@@ -129,7 +131,7 @@ try {
break
;
break
;
/* Get the tag specified by the SEEK frame */
/* Get the tag specified by the SEEK frame */
auto
seektag
=
ReadId3Tag
(
is
,
is
.
GetOffset
()
+
seek
);
auto
seektag
=
ReadId3Tag
(
is
,
lock
,
is
.
GetOffset
()
+
seek
);
if
(
!
seektag
||
tag_is_id3v1
(
seektag
.
get
()))
if
(
!
seektag
||
tag_is_id3v1
(
seektag
.
get
()))
break
;
break
;
...
@@ -143,7 +145,7 @@ try {
...
@@ -143,7 +145,7 @@ try {
}
}
static
UniqueId3Tag
static
UniqueId3Tag
tag_id3_find_from_end
(
InputStream
&
is
)
tag_id3_find_from_end
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
)
try
{
try
{
if
(
!
is
.
KnownSize
()
||
!
is
.
CheapSeeking
())
if
(
!
is
.
KnownSize
()
||
!
is
.
CheapSeeking
())
return
nullptr
;
return
nullptr
;
...
@@ -155,7 +157,7 @@ try {
...
@@ -155,7 +157,7 @@ try {
offset_type
offset
=
size
-
ID3V1_SIZE
;
offset_type
offset
=
size
-
ID3V1_SIZE
;
/* Get an id3v1 tag from the end of file for later use */
/* Get an id3v1 tag from the end of file for later use */
auto
v1tag
=
ReadId3v1Tag
(
is
,
offset
);
auto
v1tag
=
ReadId3v1Tag
(
is
,
lock
,
offset
);
if
(
!
v1tag
)
if
(
!
v1tag
)
offset
=
size
;
offset
=
size
;
...
@@ -164,7 +166,7 @@ try {
...
@@ -164,7 +166,7 @@ try {
return
v1tag
;
return
v1tag
;
long
tag_offset
=
long
tag_offset
=
get_id3v2_footer_size
(
is
,
offset
-
ID3_TAG_QUERYSIZE
);
get_id3v2_footer_size
(
is
,
lock
,
offset
-
ID3_TAG_QUERYSIZE
);
if
(
tag_offset
>=
0
)
if
(
tag_offset
>=
0
)
return
v1tag
;
return
v1tag
;
...
@@ -173,7 +175,7 @@ try {
...
@@ -173,7 +175,7 @@ try {
return
v1tag
;
return
v1tag
;
/* Get the tag which the footer belongs to */
/* Get the tag which the footer belongs to */
auto
tag
=
ReadId3Tag
(
is
,
offset
-
tag_size
);
auto
tag
=
ReadId3Tag
(
is
,
lock
,
offset
-
tag_size
);
if
(
!
tag
)
if
(
!
tag
)
return
v1tag
;
return
v1tag
;
...
@@ -184,13 +186,13 @@ try {
...
@@ -184,13 +186,13 @@ try {
}
}
static
UniqueId3Tag
static
UniqueId3Tag
tag_id3_riff_aiff_load
(
InputStream
&
is
)
tag_id3_riff_aiff_load
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
)
try
{
try
{
size_t
size
;
size_t
size
;
try
{
try
{
size
=
riff_seek_id3
(
is
);
size
=
riff_seek_id3
(
is
,
lock
);
}
catch
(...)
{
}
catch
(...)
{
size
=
aiff_seek_id3
(
is
);
size
=
aiff_seek_id3
(
is
,
lock
);
}
}
if
(
size
>
4
*
1024
*
1024
)
if
(
size
>
4
*
1024
*
1024
)
...
@@ -198,7 +200,7 @@ try {
...
@@ -198,7 +200,7 @@ try {
return
nullptr
;
return
nullptr
;
std
::
unique_ptr
<
id3_byte_t
[]
>
buffer
(
new
id3_byte_t
[
size
]);
std
::
unique_ptr
<
id3_byte_t
[]
>
buffer
(
new
id3_byte_t
[
size
]);
is
.
ReadFull
(
buffer
.
get
(),
size
);
is
.
ReadFull
(
lock
,
buffer
.
get
(),
size
);
return
UniqueId3Tag
(
id3_tag_parse
(
buffer
.
get
(),
size
));
return
UniqueId3Tag
(
id3_tag_parse
(
buffer
.
get
(),
size
));
}
catch
(...)
{
}
catch
(...)
{
...
@@ -208,13 +210,13 @@ try {
...
@@ -208,13 +210,13 @@ try {
UniqueId3Tag
UniqueId3Tag
tag_id3_load
(
InputStream
&
is
)
tag_id3_load
(
InputStream
&
is
)
try
{
try
{
const
std
::
lock_guard
<
Mutex
>
protect
(
is
.
mutex
);
std
::
unique_lock
<
Mutex
>
lock
(
is
.
mutex
);
auto
tag
=
tag_id3_find_from_beginning
(
is
);
auto
tag
=
tag_id3_find_from_beginning
(
is
,
lock
);
if
(
tag
==
nullptr
&&
is
.
CheapSeeking
())
{
if
(
tag
==
nullptr
&&
is
.
CheapSeeking
())
{
tag
=
tag_id3_riff_aiff_load
(
is
);
tag
=
tag_id3_riff_aiff_load
(
is
,
lock
);
if
(
tag
==
nullptr
)
if
(
tag
==
nullptr
)
tag
=
tag_id3_find_from_end
(
is
);
tag
=
tag_id3_find_from_end
(
is
,
lock
);
}
}
return
tag
;
return
tag
;
...
...
src/tag/Riff.cxx
View file @
1b5c1f75
...
@@ -39,14 +39,14 @@ struct riff_chunk_header {
...
@@ -39,14 +39,14 @@ struct riff_chunk_header {
};
};
size_t
size_t
riff_seek_id3
(
InputStream
&
is
)
riff_seek_id3
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
)
{
{
/* seek to the beginning and read the RIFF header */
/* seek to the beginning and read the RIFF header */
is
.
Rewind
();
is
.
Rewind
(
lock
);
riff_header
header
;
riff_header
header
;
is
.
ReadFull
(
&
header
,
sizeof
(
header
));
is
.
ReadFull
(
lock
,
&
header
,
sizeof
(
header
));
if
(
memcmp
(
header
.
id
,
"RIFF"
,
4
)
!=
0
||
if
(
memcmp
(
header
.
id
,
"RIFF"
,
4
)
!=
0
||
(
is
.
KnownSize
()
&&
FromLE32
(
header
.
size
)
>
is
.
GetSize
()))
(
is
.
KnownSize
()
&&
FromLE32
(
header
.
size
)
>
is
.
GetSize
()))
throw
std
::
runtime_error
(
"Not a RIFF file"
);
throw
std
::
runtime_error
(
"Not a RIFF file"
);
...
@@ -55,7 +55,7 @@ riff_seek_id3(InputStream &is)
...
@@ -55,7 +55,7 @@ riff_seek_id3(InputStream &is)
/* read the chunk header */
/* read the chunk header */
riff_chunk_header
chunk
;
riff_chunk_header
chunk
;
is
.
ReadFull
(
&
chunk
,
sizeof
(
chunk
));
is
.
ReadFull
(
lock
,
&
chunk
,
sizeof
(
chunk
));
size_t
size
=
FromLE32
(
chunk
.
size
);
size_t
size
=
FromLE32
(
chunk
.
size
);
if
(
size
>
size_t
(
std
::
numeric_limits
<
int
>::
max
()))
if
(
size
>
size_t
(
std
::
numeric_limits
<
int
>::
max
()))
...
@@ -72,6 +72,6 @@ riff_seek_id3(InputStream &is)
...
@@ -72,6 +72,6 @@ riff_seek_id3(InputStream &is)
/* pad byte */
/* pad byte */
++
size
;
++
size
;
is
.
Skip
(
size
);
is
.
Skip
(
lock
,
size
);
}
}
}
}
src/tag/Riff.hxx
View file @
1b5c1f75
...
@@ -25,8 +25,11 @@
...
@@ -25,8 +25,11 @@
#ifndef MPD_RIFF_HXX
#ifndef MPD_RIFF_HXX
#define MPD_RIFF_HXX
#define MPD_RIFF_HXX
#include <mutex>
#include <stddef.h>
#include <stddef.h>
class
Mutex
;
class
InputStream
;
class
InputStream
;
/**
/**
...
@@ -38,6 +41,6 @@ class InputStream;
...
@@ -38,6 +41,6 @@ class InputStream;
* @return the size of the ID3 chunk
* @return the size of the ID3 chunk
*/
*/
size_t
size_t
riff_seek_id3
(
InputStream
&
is
);
riff_seek_id3
(
InputStream
&
is
,
std
::
unique_lock
<
Mutex
>
&
lock
);
#endif
#endif
test/TestRewindInputStream.cxx
View file @
1b5c1f75
...
@@ -28,7 +28,8 @@ public:
...
@@ -28,7 +28,8 @@ public:
return
remaining
==
0
;
return
remaining
==
0
;
}
}
size_t
Read
(
void
*
ptr
,
size_t
read_size
)
override
{
size_t
Read
(
std
::
unique_lock
<
Mutex
>
&
,
void
*
ptr
,
size_t
read_size
)
override
{
size_t
nbytes
=
std
::
min
(
remaining
,
read_size
);
size_t
nbytes
=
std
::
min
(
remaining
,
read_size
);
memcpy
(
ptr
,
data
,
nbytes
);
memcpy
(
ptr
,
data
,
nbytes
);
data
+=
nbytes
;
data
+=
nbytes
;
...
@@ -51,7 +52,7 @@ TEST(RewindInputStream, Basic)
...
@@ -51,7 +52,7 @@ TEST(RewindInputStream, Basic)
EXPECT_TRUE
(
ris
.
get
()
!=
sis
);
EXPECT_TRUE
(
ris
.
get
()
!=
sis
);
EXPECT_TRUE
(
ris
!=
nullptr
);
EXPECT_TRUE
(
ris
!=
nullptr
);
const
std
::
lock_guard
<
Mutex
>
protect
(
mutex
);
std
::
unique_lock
<
Mutex
>
lock
(
mutex
);
ris
->
Update
();
ris
->
Update
();
EXPECT_TRUE
(
ris
->
IsReady
());
EXPECT_TRUE
(
ris
->
IsReady
());
...
@@ -59,50 +60,50 @@ TEST(RewindInputStream, Basic)
...
@@ -59,50 +60,50 @@ TEST(RewindInputStream, Basic)
EXPECT_EQ
(
offset_type
(
0
),
ris
->
GetOffset
());
EXPECT_EQ
(
offset_type
(
0
),
ris
->
GetOffset
());
char
buffer
[
16
];
char
buffer
[
16
];
size_t
nbytes
=
ris
->
Read
(
buffer
,
2
);
size_t
nbytes
=
ris
->
Read
(
lock
,
buffer
,
2
);
EXPECT_EQ
(
size_t
(
2
),
nbytes
);
EXPECT_EQ
(
size_t
(
2
),
nbytes
);
EXPECT_EQ
(
'f'
,
buffer
[
0
]);
EXPECT_EQ
(
'f'
,
buffer
[
0
]);
EXPECT_EQ
(
'o'
,
buffer
[
1
]);
EXPECT_EQ
(
'o'
,
buffer
[
1
]);
EXPECT_EQ
(
offset_type
(
2
),
ris
->
GetOffset
());
EXPECT_EQ
(
offset_type
(
2
),
ris
->
GetOffset
());
EXPECT_FALSE
(
ris
->
IsEOF
());
EXPECT_FALSE
(
ris
->
IsEOF
());
nbytes
=
ris
->
Read
(
buffer
,
2
);
nbytes
=
ris
->
Read
(
lock
,
buffer
,
2
);
EXPECT_EQ
(
size_t
(
2
),
nbytes
);
EXPECT_EQ
(
size_t
(
2
),
nbytes
);
EXPECT_EQ
(
'o'
,
buffer
[
0
]);
EXPECT_EQ
(
'o'
,
buffer
[
0
]);
EXPECT_EQ
(
' '
,
buffer
[
1
]);
EXPECT_EQ
(
' '
,
buffer
[
1
]);
EXPECT_EQ
(
offset_type
(
4
),
ris
->
GetOffset
());
EXPECT_EQ
(
offset_type
(
4
),
ris
->
GetOffset
());
EXPECT_FALSE
(
ris
->
IsEOF
());
EXPECT_FALSE
(
ris
->
IsEOF
());
ris
->
Seek
(
1
);
ris
->
Seek
(
lock
,
1
);
EXPECT_EQ
(
offset_type
(
1
),
ris
->
GetOffset
());
EXPECT_EQ
(
offset_type
(
1
),
ris
->
GetOffset
());
EXPECT_FALSE
(
ris
->
IsEOF
());
EXPECT_FALSE
(
ris
->
IsEOF
());
nbytes
=
ris
->
Read
(
buffer
,
2
);
nbytes
=
ris
->
Read
(
lock
,
buffer
,
2
);
EXPECT_EQ
(
size_t
(
2
),
nbytes
);
EXPECT_EQ
(
size_t
(
2
),
nbytes
);
EXPECT_EQ
(
'o'
,
buffer
[
0
]);
EXPECT_EQ
(
'o'
,
buffer
[
0
]);
EXPECT_EQ
(
'o'
,
buffer
[
1
]);
EXPECT_EQ
(
'o'
,
buffer
[
1
]);
EXPECT_EQ
(
offset_type
(
3
),
ris
->
GetOffset
());
EXPECT_EQ
(
offset_type
(
3
),
ris
->
GetOffset
());
EXPECT_FALSE
(
ris
->
IsEOF
());
EXPECT_FALSE
(
ris
->
IsEOF
());
ris
->
Seek
(
0
);
ris
->
Seek
(
lock
,
0
);
EXPECT_EQ
(
offset_type
(
0
),
ris
->
GetOffset
());
EXPECT_EQ
(
offset_type
(
0
),
ris
->
GetOffset
());
EXPECT_FALSE
(
ris
->
IsEOF
());
EXPECT_FALSE
(
ris
->
IsEOF
());
nbytes
=
ris
->
Read
(
buffer
,
2
);
nbytes
=
ris
->
Read
(
lock
,
buffer
,
2
);
EXPECT_EQ
(
size_t
(
2
),
nbytes
);
EXPECT_EQ
(
size_t
(
2
),
nbytes
);
EXPECT_EQ
(
'f'
,
buffer
[
0
]);
EXPECT_EQ
(
'f'
,
buffer
[
0
]);
EXPECT_EQ
(
'o'
,
buffer
[
1
]);
EXPECT_EQ
(
'o'
,
buffer
[
1
]);
EXPECT_EQ
(
offset_type
(
2
),
ris
->
GetOffset
());
EXPECT_EQ
(
offset_type
(
2
),
ris
->
GetOffset
());
EXPECT_FALSE
(
ris
->
IsEOF
());
EXPECT_FALSE
(
ris
->
IsEOF
());
nbytes
=
ris
->
Read
(
buffer
,
sizeof
(
buffer
));
nbytes
=
ris
->
Read
(
lock
,
buffer
,
sizeof
(
buffer
));
EXPECT_EQ
(
size_t
(
2
),
nbytes
);
EXPECT_EQ
(
size_t
(
2
),
nbytes
);
EXPECT_EQ
(
'o'
,
buffer
[
0
]);
EXPECT_EQ
(
'o'
,
buffer
[
0
]);
EXPECT_EQ
(
' '
,
buffer
[
1
]);
EXPECT_EQ
(
' '
,
buffer
[
1
]);
EXPECT_EQ
(
offset_type
(
4
),
ris
->
GetOffset
());
EXPECT_EQ
(
offset_type
(
4
),
ris
->
GetOffset
());
EXPECT_FALSE
(
ris
->
IsEOF
());
EXPECT_FALSE
(
ris
->
IsEOF
());
nbytes
=
ris
->
Read
(
buffer
,
sizeof
(
buffer
));
nbytes
=
ris
->
Read
(
lock
,
buffer
,
sizeof
(
buffer
));
EXPECT_EQ
(
size_t
(
3
),
nbytes
);
EXPECT_EQ
(
size_t
(
3
),
nbytes
);
EXPECT_EQ
(
'b'
,
buffer
[
0
]);
EXPECT_EQ
(
'b'
,
buffer
[
0
]);
EXPECT_EQ
(
'a'
,
buffer
[
1
]);
EXPECT_EQ
(
'a'
,
buffer
[
1
]);
...
@@ -110,11 +111,11 @@ TEST(RewindInputStream, Basic)
...
@@ -110,11 +111,11 @@ TEST(RewindInputStream, Basic)
EXPECT_EQ
(
offset_type
(
7
),
ris
->
GetOffset
());
EXPECT_EQ
(
offset_type
(
7
),
ris
->
GetOffset
());
EXPECT_TRUE
(
ris
->
IsEOF
());
EXPECT_TRUE
(
ris
->
IsEOF
());
ris
->
Seek
(
3
);
ris
->
Seek
(
lock
,
3
);
EXPECT_EQ
(
offset_type
(
3
),
ris
->
GetOffset
());
EXPECT_EQ
(
offset_type
(
3
),
ris
->
GetOffset
());
EXPECT_FALSE
(
ris
->
IsEOF
());
EXPECT_FALSE
(
ris
->
IsEOF
());
nbytes
=
ris
->
Read
(
buffer
,
sizeof
(
buffer
));
nbytes
=
ris
->
Read
(
lock
,
buffer
,
sizeof
(
buffer
));
EXPECT_EQ
(
size_t
(
4
),
nbytes
);
EXPECT_EQ
(
size_t
(
4
),
nbytes
);
EXPECT_EQ
(
' '
,
buffer
[
0
]);
EXPECT_EQ
(
' '
,
buffer
[
0
]);
EXPECT_EQ
(
'b'
,
buffer
[
1
]);
EXPECT_EQ
(
'b'
,
buffer
[
1
]);
...
...
test/run_input.cxx
View file @
1b5c1f75
...
@@ -131,7 +131,7 @@ tag_save(FILE *file, const Tag &tag)
...
@@ -131,7 +131,7 @@ tag_save(FILE *file, const Tag &tag)
static
int
static
int
dump_input_stream
(
InputStream
*
is
)
dump_input_stream
(
InputStream
*
is
)
{
{
const
std
::
lock_guard
<
Mutex
>
protect
(
is
->
mutex
);
std
::
unique_lock
<
Mutex
>
lock
(
is
->
mutex
);
/* print meta data */
/* print meta data */
...
@@ -150,7 +150,7 @@ dump_input_stream(InputStream *is)
...
@@ -150,7 +150,7 @@ dump_input_stream(InputStream *is)
}
}
char
buffer
[
4096
];
char
buffer
[
4096
];
size_t
num_read
=
is
->
Read
(
buffer
,
sizeof
(
buffer
));
size_t
num_read
=
is
->
Read
(
lock
,
buffer
,
sizeof
(
buffer
));
if
(
num_read
==
0
)
if
(
num_read
==
0
)
break
;
break
;
...
...
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