foobar2000 SDK  2015-08-03
Data Structures | Public Member Functions | Private Types | Private Member Functions | Private Attributes
dsp_manager

#include <dsp_manager.h>

Data Structures

struct  t_dsp_chain_entry
 

Public Member Functions

 dsp_manager ()
 
void close ()
 
void flush ()
 
bool is_active () const
 
double run (dsp_chunk_list *p_list, const metadb_handle_ptr &p_cur_file, unsigned p_flags, abort_callback &p_abort)
 
void set_config (const dsp_chain_config &p_data)
 

Private Types

typedef pfc::chain_list_v2_t< t_dsp_chain_entryt_dsp_chain
 

Private Member Functions

 dsp_manager (const dsp_manager &)
 
void dsp_run (t_dsp_chain::const_iterator p_iter, dsp_chunk_list *list, const metadb_handle_ptr &cur_file, unsigned flags, double &latency, abort_callback &)
 
const dsp_manageroperator= (const dsp_manager &)
 

Private Attributes

t_dsp_chain m_chain
 
dsp_chain_config_impl m_config
 
bool m_config_changed
 

Detailed Description

Helper class for running audio data through a DSP chain.

Definition at line 2 of file dsp_manager.h.


Data Structure Documentation

struct dsp_manager::t_dsp_chain_entry

Definition at line 21 of file dsp_manager.h.

Data Fields
service_ptr_t< dsp > m_dsp
dsp_preset_impl m_preset
bool m_recycle_flag

Member Typedef Documentation

Definition at line 26 of file dsp_manager.h.

Constructor & Destructor Documentation

dsp_manager::dsp_manager ( )
inline

Definition at line 4 of file dsp_manager.h.

4 : m_config_changed(false) {}
bool m_config_changed
Definition: dsp_manager.h:30
dsp_manager::dsp_manager ( const dsp_manager )
inlineprivate

Definition at line 34 of file dsp_manager.h.

34 {throw pfc::exception_not_implemented();}

Member Function Documentation

void dsp_manager::close ( )

Equivalent to set_config() with empty configuration.

Definition at line 3 of file dsp_manager.cpp.

3  {
5  m_config_changed = true;
6 }
t_dsp_chain m_chain
Definition: dsp_manager.h:28
bool m_config_changed
Definition: dsp_manager.h:30
void dsp_manager::dsp_run ( t_dsp_chain::const_iterator  p_iter,
dsp_chunk_list list,
const metadb_handle_ptr cur_file,
unsigned  flags,
double &  latency,
abort_callback p_abort 
)
private

Definition at line 15 of file dsp_manager.cpp.

16 {
17  p_list->remove_bad_chunks();
18 
19  TRACK_CODE("dsp::run",p_iter->m_dsp->run_abortable(p_list,cur_file,flags,p_abort));
20  TRACK_CODE("dsp::get_latency",latency += p_iter->m_dsp->get_latency());
21 }
void dsp_manager::flush ( )

Flushes the DSP (e.g. when seeking).

Definition at line 130 of file dsp_manager.cpp.

131 {
132  for(t_dsp_chain::const_iterator iter = m_chain.first(); iter.is_valid(); ++iter) {
133  TRACK_CODE("dsp::flush",iter->m_dsp->flush());
134  }
135 }
::pfc::const_iterator< t_item > const_iterator
Definition: chain_list_v2.h:31
t_dsp_chain m_chain
Definition: dsp_manager.h:28
bool is_valid() const
Definition: iterators.h:24
bool dsp_manager::is_active ( ) const

Returns whether there's at least one active DSP in the configuration.

Definition at line 138 of file dsp_manager.cpp.

138 {return m_config.get_count()>0;}
t_size get_count() const
Definition: dsp.cpp:188
dsp_chain_config_impl m_config
Definition: dsp_manager.h:29
const dsp_manager& dsp_manager::operator= ( const dsp_manager )
inlineprivate

Definition at line 35 of file dsp_manager.h.

35 {throw pfc::exception_not_implemented();}
double dsp_manager::run ( dsp_chunk_list p_list,
const metadb_handle_ptr p_cur_file,
unsigned  p_flags,
abort_callback p_abort 
)

Runs DSP on the specified chunk list.

Returns
Current DSP latency in seconds.

Definition at line 23 of file dsp_manager.cpp.

23  {
24  TRACK_CALL_TEXT("dsp_manager::run");
25 
26  try {
27 #if defined(_MSC_VER) && defined(_M_IX86)
28  fpu_control_default l_fpu_control;
29 #endif
30  double latency=0;
31  bool done = false;
32 
33  t_dsp_chain::const_iterator flush_mark;
34  if ((p_flags & dsp::END_OF_TRACK) && ! (p_flags & dsp::FLUSH)) {
35  for(t_dsp_chain::const_iterator iter = m_chain.first(); iter.is_valid(); ++iter) {
36  if (iter->m_dsp->need_track_change_mark()) flush_mark = iter;
37  }
38  }
39 
40  if (m_config_changed)
41  {
42  t_dsp_chain newchain;
43  bool recycle_available = true;
44 
45  for(t_size n=0;n<m_config.get_count();n++) {
46  service_ptr_t<dsp> temp;
47 
48  const dsp_preset & preset = m_config.get_item(n);
49  if (dsp_entry::g_dsp_exists(preset.get_owner())) {
50  t_dsp_chain::iterator iter = newchain.insert_last();
51  iter->m_preset = m_config.get_item(n);
52  iter->m_recycle_flag = false;
53  }
54  }
55 
56 
57  //HACK: recycle existing DSPs in a special case when user has apparently only altered settings of one of DSPs.
58  if (newchain.get_count() == m_chain.get_count()) {
59  t_size data_mismatch_count = 0;
60  t_size owner_mismatch_count = 0;
61  t_dsp_chain::iterator iter_src, iter_dst;
62  iter_src = m_chain.first(); iter_dst = newchain.first();
63  while(iter_src.is_valid() && iter_dst.is_valid()) {
64  if (iter_src->m_preset.get_owner() != iter_dst->m_preset.get_owner()) {
65  owner_mismatch_count++;
66  } else if (iter_src->m_preset != iter_dst->m_preset) {
67  data_mismatch_count++;
68  }
69  ++iter_src; ++iter_dst;
70  }
71  recycle_available = (owner_mismatch_count == 0 && data_mismatch_count <= 1);
72  } else {
73  recycle_available = false;
74  }
75 
76  if (recycle_available) {
77  t_dsp_chain::iterator iter_src, iter_dst;
78  iter_src = m_chain.first(); iter_dst = newchain.first();
79  while(iter_src.is_valid() && iter_dst.is_valid()) {
80  if (iter_src->m_preset == iter_dst->m_preset) {
81  iter_src->m_recycle_flag = true;
82  iter_dst->m_dsp = iter_src->m_dsp;
83  }
84  ++iter_src; ++iter_dst;
85  }
86  }
87 
88  for(t_dsp_chain::iterator iter = newchain.first(); iter.is_valid(); ++iter) {
89  if (iter->m_dsp.is_empty()) {
90  if (!dsp_entry::g_instantiate(iter->m_dsp,iter->m_preset)) uBugCheck();
91  }
92  }
93 
94  if (m_chain.get_count()>0) {
95  bool flushflag = flush_mark.is_valid();
96  for(t_dsp_chain::const_iterator iter = m_chain.first(); iter.is_valid(); ++iter) {
97  unsigned flags2 = p_flags;
98  if (iter == flush_mark) flushflag = false;
99  if (flushflag || !iter->m_recycle_flag) flags2|=dsp::FLUSH;
100  dsp_run(iter,p_list,p_cur_file,flags2,latency,p_abort);
101  }
102  done = true;
103  }
104 
105  m_chain = newchain;
106  m_config_changed = false;
107  }
108 
109  if (!done)
110  {
111  bool flushflag = flush_mark.is_valid();
112  for(t_dsp_chain::const_iterator iter = m_chain.first(); iter.is_valid(); ++iter) {
113  unsigned flags2 = p_flags;
114  if (iter == flush_mark) flushflag = false;
115  if (flushflag) flags2|=dsp::FLUSH;
116  dsp_run(iter,p_list,p_cur_file,flags2,latency,p_abort);
117  }
118  done = true;
119  }
120 
121  p_list->remove_bad_chunks();
122 
123  return latency;
124  } catch(...) {
125  p_list->remove_all();
126  throw;
127  }
128 }
void remove_all()
Definition: dsp.h:12
::pfc::const_iterator< t_item > const_iterator
Definition: chain_list_v2.h:31
t_dsp_chain m_chain
Definition: dsp_manager.h:28
Flush everything.
Definition: dsp.h:52
::pfc::iterator< t_item > iterator
Definition: chain_list_v2.h:30
void remove_bad_chunks()
Definition: dsp.cpp:60
bool is_valid() const
Definition: iterators.h:24
t_size get_count() const
Definition: chain_list_v2.h:61
Flush whatever you need to when tracks change.
Definition: dsp.h:50
size_t t_size
Definition: int_types.h:48
static bool g_dsp_exists(const GUID &p_guid)
Definition: dsp.cpp:103
pfc::chain_list_v2_t< t_dsp_chain_entry > t_dsp_chain
Definition: dsp_manager.h:26
virtual GUID get_owner() const =0
static bool g_instantiate(service_ptr_t< dsp > &p_out, const dsp_preset &p_preset)
Definition: dsp.cpp:79
void dsp_run(t_dsp_chain::const_iterator p_iter, dsp_chunk_list *list, const metadb_handle_ptr &cur_file, unsigned flags, double &latency, abort_callback &)
Definition: dsp_manager.cpp:15
t_size get_count() const
Definition: dsp.cpp:188
const dsp_preset & get_item(t_size p_index) const
Definition: dsp.cpp:193
dsp_chain_config_impl m_config
Definition: dsp_manager.h:29
PFC_NORETURN void SHARED_EXPORT uBugCheck()
bool m_config_changed
Definition: dsp_manager.h:30
void dsp_manager::set_config ( const dsp_chain_config p_data)

Alters the DSP chain configuration. Should be called before the first run() to set the configuration but can be also called anytime later between run() calls.

Definition at line 8 of file dsp_manager.cpp.

9 {
10  //dsp_chain_config::g_instantiate(m_dsp_list,p_data);
11  m_config.copy(p_data);
12  m_config_changed = true;
13 }
void copy(const dsp_chain_config &p_source)
Definition: dsp.cpp:251
dsp_chain_config_impl m_config
Definition: dsp_manager.h:29
bool m_config_changed
Definition: dsp_manager.h:30

Field Documentation

t_dsp_chain dsp_manager::m_chain
private

Definition at line 28 of file dsp_manager.h.

dsp_chain_config_impl dsp_manager::m_config
private

Definition at line 29 of file dsp_manager.h.

bool dsp_manager::m_config_changed
private

Definition at line 30 of file dsp_manager.h.


The documentation for this class was generated from the following files: