|
TOBI SignalServer
0.1
|
00001 /* 00002 This file is part of the TOBI SignalServer. 00003 00004 Commercial Usage 00005 Licensees holding valid Graz University of Technology Commercial 00006 licenses may use this file in accordance with the Graz University 00007 of Technology Commercial License Agreement provided with the 00008 Software or, alternatively, in accordance with the terms contained in 00009 a written agreement between you and Graz University of Technology. 00010 00011 -------------------------------------------------- 00012 00013 GNU General Public License Usage 00014 Alternatively, this file may be used under the terms of the GNU 00015 General Public License version 3.0 as published by the Free Software 00016 Foundation and appearing in the file gpl.txt included in the 00017 packaging of this file. Please review the following information to 00018 ensure the GNU General Public License version 3.0 requirements will be 00019 met: http://www.gnu.org/copyleft/gpl.html. 00020 00021 In case of GNU General Public License Usage ,the TOBI SignalServer 00022 is distributed in the hope that it will be useful, 00023 but WITHOUT ANY WARRANTY; without even the implied warranty of 00024 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00025 GNU General Public License for more details. 00026 00027 You should have received a copy of the GNU General Public License 00028 along with the TOBI SignalServer. If not, see <http://www.gnu.org/licenses/>. 00029 00030 Copyright 2010 Graz University of Technology 00031 Contact: SignalServer@tobi-project.org 00032 */ 00033 00038 #include "hardware/sine_generator.h" 00039 #include <boost/current_function.hpp> 00040 00041 #include <cmath> 00042 00043 namespace tobiss 00044 { 00045 using boost::uint16_t; 00046 00047 using std::string; 00048 using std::cout; 00049 using std::endl; 00050 00051 const HWThreadBuilderTemplateRegistrator<SineGenerator> SineGenerator::factory_registrator_ ("sinegen", "sinegenerator"); 00052 00053 //----------------------------------------------------------------------------- 00054 00055 SineGenerator::SineGenerator(boost::asio::io_service& io, ticpp::Iterator<ticpp::Element> hw) 00056 : ArtificialSignalSource(io, hw) 00057 { 00058 #ifdef DEBUG 00059 cout << "SineGenerator: Constructor" << endl; 00060 #endif 00061 00062 setType("Sine Generator"); 00063 setHardware(hw); 00064 init(); 00065 } 00066 00067 //----------------------------------------------------------------------------- 00068 00069 SineGenerator::~SineGenerator() 00070 { 00071 } 00072 00074 00075 //void SineGenerator::run() 00076 //{ 00077 // std::cout << BOOST_CURRENT_FUNCTION << std::endl << std::flush; 00078 00079 // shd_ptr_.reset(this); 00080 // ArtificialSignalSource::run(); 00081 //} 00082 00084 00085 //void SineGenerator::stop() 00086 //{ 00087 // std::cout << BOOST_CURRENT_FUNCTION << std::endl << std::flush; 00088 00089 // shd_ptr_.reset(); 00090 // ArtificialSignalSource::stop(); 00091 //} 00092 00093 //----------------------------------------------------------------------------- 00094 00095 void SineGenerator::genSine() 00096 { 00097 #ifdef DEBUG 00098 cout << "SineGenerator: genSine" << endl; 00099 #endif 00100 00101 for(uint16_t n = 0; n < nr_ch_ ; n++) 00102 samples_[n] = sin(step_ * 2 * M_PI + n/4); 00103 00104 (step_ < 1-cycle_dur_ ? step_ += cycle_dur_ : step_ = 0); 00105 t_->expires_at(t_->expires_at() + td_); 00106 00107 if(blocks_ == 1) 00108 { 00109 boost::unique_lock<boost::shared_mutex> lock(rw_); 00110 boost::unique_lock<boost::mutex> syn(sync_mut_); 00111 samples_available_ = true; 00112 data_.setSamples(samples_); 00113 lock.unlock(); 00114 cond_.notify_all(); 00115 if(isMaster() && acquiring_) 00116 { 00117 cond_.wait(sync_mut_); 00118 // if( !cond_.timed_wait(sync_mut_, td_)) 00119 // cerr << "Warning: New data was not fetched fast enough!" << endl; 00120 // throw std::runtime_error("SineGenerator::genSine() -- Timeout; New data was not fetched fast enough!"); 00121 } 00122 syn.unlock(); 00123 } 00124 else 00125 { 00126 buffer_.appendBlock(samples_, 1); 00127 current_block_++; 00128 00129 if(current_block_ == blocks_ ) 00130 { 00131 boost::unique_lock<boost::shared_mutex> lock(rw_); 00132 boost::unique_lock<boost::mutex> syn(sync_mut_); 00133 samples_available_ = true; 00134 data_ = buffer_; 00135 lock.unlock(); 00136 cond_.notify_all(); 00137 buffer_.reset(); 00138 current_block_ = 0; 00139 if(isMaster() && acquiring_) 00140 { 00141 cond_.wait(sync_mut_); 00142 // if( !cond_.timed_wait(sync_mut_, td_)) 00143 // cerr << "Warning: New data was not fetched fast enough!" << endl; 00144 // throw std::runtime_error("SineGenerator::genSine() -- Timeout; New data was not fetched fast enough!"); 00145 } 00146 syn.unlock(); 00147 } 00148 } 00149 if(running_) 00150 t_->async_wait(boost::bind(&SineGenerator::genSine, this )); 00151 } 00152 00153 //----------------------------------------------------------------------------- 00154 00155 void SineGenerator::setHardware(ticpp::Iterator<ticpp::Element>const &hw) 00156 { 00157 #ifdef DEBUG 00158 cout << "SineGenerator: setHardware" << endl; 00159 #endif 00160 00161 checkMandatoryHardwareTags(hw); 00162 ticpp::Iterator<ticpp::Element> ds(hw->FirstChildElement(hw_devset_, true)); 00163 00164 setDeviceSettings(ds); 00165 00166 ticpp::Iterator<ticpp::Element> cs(hw->FirstChildElement(hw_chset_, false)); 00167 if (cs != cs.end()) 00168 { 00169 for(ticpp::Iterator<ticpp::Element> it(cs); ++it != it.end(); ) 00170 if(it->Value() == hw_chset_) 00171 { 00172 string ex_str(type_ + " -- "); 00173 ex_str += "Multiple channel_settings found!"; 00174 throw(std::invalid_argument(ex_str)); 00175 } 00176 setChannelSettings(cs); 00177 } 00178 } 00179 00180 //----------------------------------------------------------------------------- 00181 00182 void SineGenerator::setDeviceSettings(ticpp::Iterator<ticpp::Element>const &father) 00183 { 00184 #ifdef DEBUG 00185 cout << "SineGenerator: setDeviceSettings" << endl; 00186 #endif 00187 00188 ticpp::Iterator<ticpp::Element> elem(father->FirstChildElement(hw_fs_,true)); 00189 setSamplingRate(elem); 00190 00191 elem = father->FirstChildElement(hw_channels_,false); 00192 if(elem != elem.end()) 00193 setDeviceChannels(elem); 00194 00195 elem = father->FirstChildElement(hw_blocksize_,false); 00196 if(elem != elem.end()) 00197 setBlocks(elem); 00198 } 00199 00200 //--------------------------------------------------------------------------------------- 00201 00202 void SineGenerator::setChannelSettings(ticpp::Iterator<ticpp::Element>const &father) 00203 { 00204 #ifdef DEBUG 00205 cout << "SineGenerator: setChannelSettings" << endl; 00206 #endif 00207 00208 ticpp::Iterator<ticpp::Element> elem(father->FirstChildElement(hw_chset_sel_,false)); 00209 if (elem != elem.end()) 00210 setChannelSelection(elem); 00211 } 00212 00213 //--------------------------------------------------------------------------------------- 00214 00215 } // Namespace tobiss