Skip to content
GitLab
Projects
Groups
Snippets
/
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in
Toggle navigation
Menu
Open sidebar
Institute of Technical Acoustics (ITA)
ITADataSources
Commits
c283da2e
Commit
c283da2e
authored
Apr 11, 2017
by
Jonas Stienen
Browse files
Merging NetAudio to develop
parents
d7d9cda2
11ebc640
Changes
40
Expand all
Hide whitespace changes
Inline
Side-by-side
CMakeLists.txt
View file @
c283da2e
...
...
@@ -110,23 +110,22 @@ endif( )
if
(
ITA_DATA_SOURCES_WITH_NET_AUDIO
)
list
(
APPEND ITADataSourcesHeader
"include/ITANetAudioClient.h"
"include/ITANetAudioMessage.h"
"include/ITANetAudioProtocol.h"
"include/ITANetAudioServer.h"
"include/ITANetAudioStream.h"
"include/ITANetAudioS
treamingClient
.h"
"include/ITANetAudioS
ampleServer
.h"
"include/ITANetAudioStreamingServer.h"
"include/ITANetAudioStreamingClient.h"
)
list
(
APPEND ITADataSourcesSources
"src/ITANetAudioClient.cpp"
"src/ITANetAudioClient.h"
"src/ITANetAudioMessage.cpp"
"src/ITANetAudioProtocol.cpp"
"src/ITANetAudioMessage.h"
"src/ITANetAudioProtocol.h"
"src/ITANetAudioServer.cpp"
"src/ITANetAudioServer.h"
"src/ITANetAudioStream.cpp"
"src/ITANetAudioStreamingClient.cpp"
"src/ITANetAudioStreamingClient.h"
"src/ITANetAudioStreamingServer.cpp"
"src/ITANetAudioServer.cpp"
)
endif
(
)
...
...
include/ITANetAudioSampleServer.h
0 → 100644
View file @
c283da2e
/*
* ----------------------------------------------------------------
*
* ITA core libs
* (c) Copyright Institute of Technical Acoustics (ITA)
* RWTH Aachen University, Germany, 2015-2017
*
* ----------------------------------------------------------------
* ____ __________ _______
* // / //__ ___/ // _ |
* // / // / // /_| |
* // / // / // ___ |
* //__/ //__/ //__/ |__|
*
* ----------------------------------------------------------------
*
*/
#ifndef INCLUDE_WATCHER_ITA_NET_AUDIO_SAMPLE_SERVER
#define INCLUDE_WATCHER_ITA_NET_AUDIO_SAMPLE_SERVER
#include
<ITADataSourcesDefinitions.h>
#include
<ITANetAudioStreamingServer.h>
#include
<ITADataSourceRealization.h>
//! Sample-generation class with abstract method for providing samples
/*
* This ready-to-use class helps to provide samples for a NetAudio streaming server with
* a single method for processing that has to be implemented ...
* ... just derive and implement Process() method. Have a look at Zero() method
* for exemplary usage of sample buffer.
*/
class
CITASampleProcessor
:
public
ITADatasourceRealization
{
public:
//! Create a sample processor with streaming parameters
/*
* @param[in] iNumChannels Channels provided
* @param[in] dSampleRate Audio processing sampling rate
* @param[in] iBlockLength Audio processing block length / buffer size
*/
inline
CITASampleProcessor
(
const
int
iNumChannels
,
const
double
dSampleRate
,
const
int
iBlockLength
)
:
ITADatasourceRealization
(
(
unsigned
int
)
(
iNumChannels
),
dSampleRate
,
(
unsigned
int
)
(
iBlockLength
)
)
{
m_vvfSampleBuffer
.
resize
(
iNumChannels
);
for
(
size_t
c
=
0
;
c
<
iNumChannels
;
c
++
)
m_vvfSampleBuffer
[
c
].
resize
(
iBlockLength
);
Zero
();
};
inline
~
CITASampleProcessor
()
{
};
//! Sets all channels and samples to zero
inline
void
Zero
()
{
/*
* Use this as an example how to work with the buffer structure.
*/
// Iterate over channels
for
(
size_t
c
=
0
;
c
<
m_vvfSampleBuffer
.
size
();
c
++
)
{
std
::
vector
<
float
>&
vfSingleChannelSampleBuffer
(
m_vvfSampleBuffer
[
c
]
);
// One channel
// Iterate over samples of channel
for
(
size_t
n
=
0
;
n
<
vfSingleChannelSampleBuffer
.
size
();
n
++
)
{
float
&
fSample
(
vfSingleChannelSampleBuffer
[
n
]
);
// One sample
fSample
=
0.0
f
;
// -> Manipulation
}
}
};
//! Process samples (overwrite this virtual method)
/**
* Method that is called in audio streaming context and requests
* to produce or copy audio samples into the internal buffer m_vvfSampleBuffer
*
* @param[in] pStreamInfo Information over streaming status, i.e. sample count and time stamp
*
*/
virtual
void
Process
(
const
ITAStreamInfo
*
pStreamInfo
)
=
0
;
protected:
std
::
vector
<
std
::
vector
<
float
>
>
m_vvfSampleBuffer
;
//!< Multi-channel sample buffer to be filled
private:
//! Delegate internal buffer to audio stream (ITADatasource)
inline
void
ProcessStream
(
const
ITAStreamInfo
*
pInfo
)
{
Process
(
pInfo
);
for
(
size_t
c
=
0
;
c
<
m_vvfSampleBuffer
.
size
();
c
++
)
{
float
*
pfData
=
GetWritePointer
(
(
unsigned
int
)
(
c
)
);
for
(
size_t
n
=
0
;
n
<
m_vvfSampleBuffer
[
c
].
size
();
n
++
)
pfData
[
n
]
=
m_vvfSampleBuffer
[
c
][
n
];
}
IncrementWritePointer
();
};
};
//! Network audio sample server (for providing samples via derived generator class)
/**
* Audio sample transmitter for a networked sample callback function that can connect via TCP/IP.
*
* @sa CITANetAudioStream CITANetAudioStreamingServer CITASampleProcessor
* @note not thread-safe
*/
class
CITANetAudioSampleServer
:
public
CITANetAudioStreamingServer
{
public:
inline
CITANetAudioSampleServer
(
CITASampleProcessor
*
pProcessor
)
:
m_pSampleProcessor
(
pProcessor
)
{
SetInputStream
(
m_pSampleProcessor
);
};
inline
~
CITANetAudioSampleServer
()
{};
private:
//! Prohibit public access to streaming context and delegate
inline
void
SetInputStream
(
ITADatasource
*
pDataSource
)
{
CITANetAudioStreamingServer
::
SetInputStream
(
pDataSource
);
};
//! Prohibit public access to streaming context and delegate
inline
ITADatasource
*
GetInputStream
()
const
{
return
CITANetAudioStreamingServer
::
GetInputStream
();
};
CITASampleProcessor
*
m_pSampleProcessor
;
//!< Callback / sample processor
};
#endif // INCLUDE_WATCHER_ITA_NET_AUDIO_SAMPLE_SERVER
include/ITANetAudioStream.h
View file @
c283da2e
...
...
@@ -26,9 +26,6 @@
#include
<string>
#include
<vector>
#include
<iostream>
#include
<fstream>
using
namespace
std
;
class
CITANetAudioStreamingClient
;
...
...
@@ -38,7 +35,7 @@ class ITABufferedDataLoggerImplAudio;
//! Network audio stream
/**
* Audio streaming for a signal source that is connected via TCP/IP.
* Audio streaming for a signal source that is connected via TCP/IP
or UDP
.
* The network audio stream behaves like a client and receives samples
* from a network audio stream server, CITANetAudioStreamingSearver.
*
...
...
@@ -46,11 +43,13 @@ class ITABufferedDataLoggerImplAudio;
* block the streaming processing, because it is decoupled from the
* network connection and forwards samples from an internal ring buffer.
* If the buffer runs out of samples, zeros will be return. If the buffer
* overruns, the sample server will be suspende
b
by blocking the network
* overruns, the sample server will be suspende
d
by blocking the network
* data flow.
*
* Latency can be managed by either providing a small ring buffer or
* oversizing the ring buffer and requesting a target latency.
* Latency can be managed by either providing a small ring buffer and
* constantly filling it uo, or by oversizing the internal ring buffer
* only pushing samples to meet a target latency. This has to be
* implemented by the server.
*
* \note not thread-safe
*/
...
...
@@ -58,7 +57,21 @@ class ITA_DATA_SOURCES_API CITANetAudioStream : public ITADatasource
{
public:
//! Constructor of a network audio stream
CITANetAudioStream
(
int
iChannels
,
double
dSamplingRate
,
int
iBufferSize
,
int
iRingBufferCapacity
=
2048
);
/**
* @param[in] iChannels Number of channels
* @param[in] dSamplingRate Sampling rate
* @param[in] iBufferSize Size of audio streaming buffer
* @param[in] iRingBufferCapacity Internal ring buffer
*
* The ring buffer capacity should be roughly 6-10 buffer sizes long for short audio streaming buffers,
* and can go down to one block in case of higher audio buffer sizes.
*
* The streaming parameters have to match with the server settings (yes also buffer size, that of the audio streaming context)
*
* @note Accept for more memory usage, oversizing the buffer does not require more CPU.
*/
CITANetAudioStream
(
const
int
iChannels
,
const
double
dSamplingRate
,
const
int
iBufferSize
,
const
int
iRingBufferCapacity
=
2048
);
virtual
~
CITANetAudioStream
();
//! Network streaming status of client
...
...
@@ -68,16 +81,20 @@ public:
STOPPED
,
//!< Client not connected to a server and streaming stopped, i.e. not receiving samples by choice
CONNECTED
,
//!< Client is connected to a sample server (and potentially receives samples)
STREAMING
,
//!<
BUFFER_UNDERRUN
,
BUFFER_OVERRUN
,
BUFFER_UNDERRUN
,
//!< Client internal audio buffer ran out of samples
BUFFER_OVERRUN
,
//!< Client internal audio ring buffer is full
};
//! Connect a streaming server
/**
* @sAddress[in] Server address IP
, i.e.
127.0.0.1
* @sAddress[in] Server address IP
(
127.0.0.1
, localhost, etc.)
* @iPort[in] Server socket port, defaults to 12480
* @return True, if connection could be established and streaming parameters match
*/
bool
Connect
(
const
std
::
string
&
sAddress
,
int
iPort
=
12480
);
bool
Connect
(
const
std
::
string
&
sAddress
,
const
int
iPort
=
12480
,
const
bool
bUseUDP
=
false
);
//! Disconnct safely from server
void
Disconnect
();
//! Returns the connection status
/**
...
...
@@ -85,43 +102,47 @@ public:
*/
bool
GetIsConnected
()
const
;
//!
S
et
allowed latency (s
)
//!
R
et
urns the minimal latency possible (single block
)
/**
* Sets the latency that will be used for reading and writing from ring buffer.
* New samples will be requested and send if the latency / ring buffer samples
* is lower than the target latency.
*/
void
SetAllowedLatencySeconds
(
float
fLatencySeconds
);
void
SetAllowedLatencySamples
(
int
iLatencySamples
);
float
GetAllowedLatencySeconds
()
const
;
int
GetAllowedLatencySamples
()
const
;
//! Sets the minimal latency possible
/**
* Real-time network audio is considered to process at lowest latency possible.
* However, this implementation requires at least one block. Hence latency is
* depending on sampling rate and block length.
*
* @sa GetMinimumLatencySamples()
* @sa GetMinimumLatencySamples()
* @return Minimum latency in seconds
*/
float
GetMinimumLatencySeconds
()
const
;
//! Returns the maximum latency possible (entire ring buffer used)
/**
* @return Maximum latency in seconds
*/
float
GetMaximumLatencySeconds
()
const
;
//! Returns the minimum latency possible (single block)
/**
* @return Minimum latency in samples
*/
int
GetMinimumLatencySamples
()
const
;
//! Returns the maximum latency possible (entire ring buffer used)
/**
* @return Maximum latency in samples
*/
int
GetMaximumLatencySamples
()
const
;
//! Sets the latency for real-time processing
//! Returns the NetAudio streaming logger base name
std
::
string
GetNetAudioStreamLoggerBaseName
()
const
;
//! Sets the NetAudio streaming logger base name
/**
* Real-time network audio is considered to process at lowest latency possible.
* However, this implementation requires at least one block. Hence latency is
* depending on sampling rate and block length. This method basically
* sets the minimum allowed latency to this value.
*
* @sa GetMinimumLatencySeconds()
* @sa SetAllowedLatencySeconds()
* If debugging is enabled, all debugging files will be named
* with this suffix.
* @param[in] sBaseName Base name string
*
*/
void
SetLatencyForRealtime
();
void
SetNetAudioStreamingLoggerBaseName
(
const
std
::
string
&
sBaseName
);
//! Enabled/disables export of loggers
void
SetDebuggingEnabled
(
bool
bEnabled
);
//! Logging export flag getter
bool
GetIsDebuggingEnabled
()
const
;
//! Returns (static) size of ring buffer
/**
...
...
@@ -167,6 +188,7 @@ public:
*/
void
IncrementBlockPointer
();
protected:
//! This method is called by the networkg client and pushes samples into the ring buffer
/**
...
...
@@ -180,7 +202,7 @@ protected:
*
* @note This method is not called out of the audio streaming context but out of the network context.
*/
int
Transmit
(
const
ITASampleFrame
&
sfNewSamples
,
int
iNumSamples
);
int
Transmit
(
const
ITASampleFrame
&
sfNewSamples
,
const
int
iNumSamples
);
//! Returns samples that can be read from ring buffer
/**
...
...
@@ -194,6 +216,9 @@ protected:
*/
int
GetRingBufferFreeSamples
()
const
;
//! Returns a string for the streaming status identifier
static
std
::
string
GetStreamingStatusString
(
const
int
iStreamingStatus
);
private:
CITANetAudioStreamingClient
*
m_pNetAudioStreamingClient
;
//!< Audio streaming network client
...
...
@@ -204,16 +229,17 @@ private:
int
m_iWriteCursor
;
//!< Cursor where samples will be fed into ring buffer from net audio producer (always ahead)
bool
m_bRingBufferFull
;
//!< Indicator if ring buffer is full (and read cursor equals write cursor)
ITASampleFrame
m_sfRingBuffer
;
//!< Ring buffer
int
m_iTargetSampleLatency
;
//!< Maximum allowed samples / target sample latency
int
m_iStreamingStatus
;
//!< Current streaming status
double
m_dLastStreamingTimeCode
;
ITABufferedDataLoggerImplAudio
*
m_pAudioLogger
;
//!< Logging for the audio stream
ITABufferedDataLoggerImplStream
*
m_pStreamLogger
;
//!< Logging for the audio stream
ITABufferedDataLoggerImplNet
*
m_pNetLogger
;
//!< Logging for the network stream
int
iAudioStreamingBlockID
;
//!< Audio streaming block id
int
iNetStreamingBlockID
;
//!< Network streaming block id
ITABufferedDataLoggerImplStream
*
m_pAudioStreamLogger
;
//!< Logging for the audio stream
ITABufferedDataLoggerImplNet
*
m_pNetworkStreamLogger
;
//!< Logging for the network stream
std
::
string
m_sNetAudioStreamLoggerBaseName
;
bool
m_bDebuggingEnabled
;
int
m_iAudioStreamingBlockID
;
//!< Audio streaming block id
int
m_iNetStreamingBlockID
;
//!< Network streaming block id
friend
class
CITANetAudioStreamingClient
;
};
...
...
include/ITANetAudioStreamingServer.h
View file @
c283da2e
/*
* ----------------------------------------------------------------
*
* ITA core libs
* (c) Copyright Institute of Technical Acoustics (ITA)
* RWTH Aachen University, Germany, 2015-2017
*
* ----------------------------------------------------------------
* ____ __________ _______
* // / //__ ___/ // _ |
* // / // / // /_| |
* // / // / // ___ |
* //__/ //__/ //__/ |__|
*
* ----------------------------------------------------------------
*
*/
#ifndef INCLUDE_WATCHER_ITA_NET_AUDIO_STREAMING_SERVER
#define INCLUDE_WATCHER_ITA_NET_AUDIO_STREAMING_SERVER
#include
<ITADataSourcesDefinitions.h>
#include
<ITANetAudioProtocol.h>
#include
<string>
#include
<vector>
#include
<iostream>
#include
<fstream>
#include
<ITANetAudioProtocol.h>
#include
<VistaInterProcComm/Concurrency/VistaThreadLoop.h>
#include
<ITASampleFrame.h>
class
ITADatasource
;
class
CITANetAudioMessage
;
class
CITANetAudioProtocol
;
class
CITANetAudioServer
;
class
CITANetAudioMessage
;
class
VistaTCPSocket
;
class
ITABufferedDataLoggerImplServer
;
//! Network audio sample server (for connecting a net audio stream)
/**
* Audio sample transmitter for a networked signal source that can connect via TCP/IP.
*
* \sa CITANetAudioStream
* \note not thread-safe
*/
class
ITA_DATA_SOURCES_API
CITANetAudioStreamingServer
:
public
VistaThreadLoop
{
public:
enum
UpdateStrategy
{
AUTO
=
1
,
//!< Automatic update rate based on sample rate and block length of client (default)
ADAPTIVE
,
//!< Adaptive update rate, adjusts for drifting clocks
CONSTANT
,
//!< Set a user-defined update rate (may cause forced pausing of sample feeding or dropouts on client side)
};
CITANetAudioStreamingServer
();
virtual
~
CITANetAudioStreamingServer
()
{};
bool
Start
(
const
std
::
string
&
sAddress
,
int
iPort
);
bool
IsClientConnected
()
const
;
std
::
string
GetNetworkAddress
()
const
;
int
GetNetworkPort
()
const
;
bool
LoopBody
();
void
Stop
();
void
SetInputStream
(
ITADatasource
*
pInStream
);
int
GetNetStreamBlocklength
()
const
;
int
GetNetStreamNumberOfChannels
()
const
;
double
GetNetStreamSampleRate
()
const
;
void
SetAutomaticUpdateRate
();
protected:
ITADatasource
*
GetInputStream
()
const
;
private:
CITANetAudioServer
*
m_pNetAudioServer
;
ITASampleFrame
m_sfTempTransmitBuffer
;
ITADatasource
*
m_pInputStream
;
VistaConnectionIP
*
m_pConnection
;
CITANetAudioProtocol
::
StreamingParameters
m_oServerParams
;
CITANetAudioMessage
*
m_pMessage
;
int
iServerBlockId
;
ITABufferedDataLoggerImplServer
*
m_pServerLogger
;
int
m_iUpdateStrategy
;
int
m_iClientRingBufferFreeSamples
;
int
m_iMaxSendBlocks
;
friend
class
CITANetAudioServer
;
};
#endif // INCLUDE_WATCHER_ITA_NET_AUDIO_STREAMING_SERVER
/*
* ----------------------------------------------------------------
*
* ITA core libs
* (c) Copyright Institute of Technical Acoustics (ITA)
* RWTH Aachen University, Germany, 2015-2017
*
* ----------------------------------------------------------------
* ____ __________ _______
* // / //__ ___/ // _ |
* // / // / // /_| |
* // / // / // ___ |
* //__/ //__/ //__/ |__|
*
* ----------------------------------------------------------------
*
*/
#ifndef INCLUDE_WATCHER_ITA_NET_AUDIO_STREAMING_SERVER
#define INCLUDE_WATCHER_ITA_NET_AUDIO_STREAMING_SERVER
#include
<ITADataSourcesDefinitions.h>
#include
<ITASampleFrame.h>
#include
<ITAStopWatch.h>
#include
<VistaInterProcComm/Concurrency/VistaThreadLoop.h>
#include
<string>
#include
<vector>
#include
<iostream>
<<<<<<<<<
Temporary
merge
branch
1
#include
<fstream>
#include
<ITANetAudioProtocol.h>
#include
<VistaInterProcComm/Concurrency/VistaThreadLoop.h>
#include
<ITASampleFrame.h>
class
ITADatasource
;
class
CITANetAudioMessage
;
class
CITANetAudioProtocol
;
class
CITANetAudioServer
;
class
CITANetAudioMessage
;
class
VistaTCPSocket
;
//! Network audio sample server (for connecting a net audio stream)
/**
* Audio sample transmitter for a networked signal source that can connect via TCP/IP.
*
* \sa CITANetAudioStream
* \note not thread-safe
*/
class
ITA_DATA_SOURCES_API
CITANetAudioStreamingServer
:
public
VistaThreadLoop
{
public:
enum
UpdateStrategy
{
AUTO
=
1
,
//!< Automatic update rate based on sample rate and block length of client (default)
ADAPTIVE
,
//!< Adaptive update rate, adjusts for drifting clocks
CONSTANT
,
//!< Set a user-defined update rate (may cause forced pausing of sample feeding or dropouts on client side)
};
CITANetAudioStreamingServer
();
virtual
~
CITANetAudioStreamingServer
()
{};
bool
Start
(
const
std
::
string
&
sAddress
,
int
iPort
);
bool
IsClientConnected
()
const
;
std
::
string
GetNetworkAddress
()
const
;
int
GetNetworkPort
()
const
;
bool
LoopBody
();
void
Stop
();
void
SetInputStream
(
ITADatasource
*
pInStream
);
int
GetNetStreamBlocklength
()
const
;
int
GetNetStreamNumberOfChannels
()
const
;
double
GetNetStreamSampleRate
()
const
;
void
SetAutomaticUpdateRate
();
protected:
ITADatasource
*
GetInputStream
()
const
;
private:
CITANetAudioServer
*
m_pNetAudioServer
;
ITASampleFrame
m_sfTempTransmitBuffer
;
ITADatasource
*
m_pInputStream
;
VistaConnectionIP
*
m_pConnection
;
CITANetAudioProtocol
::
StreamingParameters
m_oServerParams
;
CITANetAudioMessage
*
m_pIncomingMessage
;
CITANetAudioMessage
*
m_pOutgoingMessage
;
int
m_iUpdateStrategy
;
int
m_iClientRingBufferFreeSamples
;
friend
class
CITANetAudioServer
;
};
#endif // INCLUDE_WATCHER_ITA_NET_AUDIO_STREAMING_SERVER
=========
#include
<fstream>
class
ITADatasource
;
class
CITANetAudioMessage
;
class
CITANetAudioProtocol
;
class
CITANetAudioServer
;
class
CITANetAudioMessage
;
class
CITABufferedDataLoggerImplServer
;
class
VistaConnectionIP
;
//! Network audio streaming server (for connecting a net audio stream) with an ITADataSource connection
/**
* Audio sample transmitter for a networked signal source that can connect via TCP/IP.
*
* @sa CITANetAudioStream
* @note not thread-safe
*/
class
ITA_DATA_SOURCES_API
CITANetAudioStreamingServer
:
public
VistaThreadLoop
{
public:
CITANetAudioStreamingServer
();
~
CITANetAudioStreamingServer
();
//! Start to listen on a socket (blocking)
bool
Start
(
const
std
::
string
&
sAddress
,
const
int
iPort
,
const
double
dTimeIntervalCientSendStatus
,
const
bool
bUseUDP
=
false
);
bool
IsClientConnected
()
const
;
std
::
string
GetNetworkAddress
()
const
;
int
GetNetworkPort
()
const
;
void
Stop
();
void
SetInputStream
(
ITADatasource
*
pInStream
);
int
GetNetStreamBlocklength
()
const
;
int
GetNetStreamNumberOfChannels
(
)
const
;
double
GetNetStreamSampleRate
(
)
const
;
double
GetEstimatedCorrFactor
(
)
const
;