Mercurial > hg > beaglert
changeset 149:134bff10e561 ClockSync
Added simple one-variable one-measurement Kalman filter, Pid controller(which output is not used). Virtual clock is now much more precise and reactive for period. Still it is lagging behind a bit on the overall offset.
author | Giulio Moro <giuliomoro@yahoo.it> |
---|---|
date | Mon, 21 Sep 2015 03:12:21 +0100 |
parents | 6cd38e261027 |
children | ebbfb154351a |
files | .cproject core/ClockSync.cpp core/ClockSyncThread.cpp core/I2c_Codec.cpp core/Kalman.cpp core/Pid.cpp core/UdpServer.cpp core/VirtualClock.cpp include/ClockSync.h include/Kalman.h include/Pid.h include/VirtualClock.h projects/scope/render.cpp |
diffstat | 13 files changed, 244 insertions(+), 73 deletions(-) [+] |
line wrap: on
line diff
--- a/.cproject Mon Sep 21 03:11:32 2015 +0100 +++ b/.cproject Mon Sep 21 03:12:21 2015 +0100 @@ -14,7 +14,7 @@ </extensions> </storageModule> <storageModule moduleId="cdtBuildSystem" version="4.0.0"> - <configuration artifactName="${ProjName}" buildArtefactType="org.eclipse.cdt.build.core.buildArtefactType.exe" buildProperties="org.eclipse.cdt.build.core.buildType=org.eclipse.cdt.build.core.buildType.debug,org.eclipse.cdt.build.core.buildArtefactType=org.eclipse.cdt.build.core.buildArtefactType.exe" cleanCommand="rm -rf" description="" id="cdt.managedbuild.config.gnu.exe.debug.528876549" name="Debug" parent="cdt.managedbuild.config.gnu.exe.debug" postannouncebuildStep="Kills the process running on the BeagleBone (if any) and copies the new binary to the BeagleBone in beaglert/" postbuildStep="ssh root@192.168.7.2 "kill -s 2 \`pidof ${BuildArtifactFileName}\` 2>/dev/null; sleep 0.5; scp host:${PWD}/${BuildArtifactFileName} ~/beaglert/ && echo 'done copying\n' | wall || echo 'error'|wall""> + <configuration artifactName="${ProjName}" buildArtefactType="org.eclipse.cdt.build.core.buildArtefactType.exe" buildProperties="org.eclipse.cdt.build.core.buildType=org.eclipse.cdt.build.core.buildType.debug,org.eclipse.cdt.build.core.buildArtefactType=org.eclipse.cdt.build.core.buildArtefactType.exe" cleanCommand="rm -rf" description="" id="cdt.managedbuild.config.gnu.exe.debug.528876549" name="Debug" parent="cdt.managedbuild.config.gnu.exe.debug" postannouncebuildStep="Kills the process running on the BeagleBone (if any) and copies the new binary to the BeagleBone in beaglert/" postbuildStep="ssh root@192.168.7.2 "kill -s 2 \`pidof ${BuildArtifactFileName}\` 2>/dev/null; sleep 0.5;"; scp ${PWD}/${BuildArtifactFileName} bbb:beaglert/ && echo 'done copying\n' | wall || echo 'error'|wall"> <folderInfo id="cdt.managedbuild.config.gnu.exe.debug.528876549." name="/" resourcePath=""> <toolChain id="cdt.managedbuild.toolchain.gnu.exe.debug.681872250" name="Linux GCC" superClass="cdt.managedbuild.toolchain.gnu.exe.debug"> <targetPlatform id="cdt.managedbuild.target.gnu.platform.exe.debug.295375065" name="Debug Platform" superClass="cdt.managedbuild.target.gnu.platform.exe.debug"/> @@ -25,7 +25,7 @@ </outputEntries> </builder> <tool command="arm-linux-gnueabihf-g++ " id="cdt.managedbuild.tool.gnu.archiver.base.1542380883" name="GCC Archiver" superClass="cdt.managedbuild.tool.gnu.archiver.base"/> - <tool command="arm-linux-gnueabihf-g++ " id="cdt.managedbuild.tool.gnu.cpp.compiler.exe.debug.2030825480" name="GCC C++ Compiler" superClass="cdt.managedbuild.tool.gnu.cpp.compiler.exe.debug"> + <tool command="arm-linux-gnueabihf-g++" id="cdt.managedbuild.tool.gnu.cpp.compiler.exe.debug.2030825480" name="GCC C++ Compiler" superClass="cdt.managedbuild.tool.gnu.cpp.compiler.exe.debug"> <option id="gnu.cpp.compiler.exe.debug.option.optimization.level.2006448218" name="Optimization Level" superClass="gnu.cpp.compiler.exe.debug.option.optimization.level" value="gnu.cpp.compiler.optimization.level.none" valueType="enumerated"/> <option id="gnu.cpp.compiler.exe.debug.option.debugging.level.1267706246" name="Debug Level" superClass="gnu.cpp.compiler.exe.debug.option.debugging.level" value="gnu.cpp.compiler.debugging.level.max" valueType="enumerated"/> <option id="gnu.cpp.compiler.option.include.paths.2031219124" name="Include paths (-I)" superClass="gnu.cpp.compiler.option.include.paths" valueType="includePath"> @@ -59,11 +59,9 @@ <tool command="arm-linux-gnueabihf-g++ " id="cdt.managedbuild.tool.gnu.c.linker.exe.debug.214461086" name="GCC C Linker" superClass="cdt.managedbuild.tool.gnu.c.linker.exe.debug"/> <tool command="arm-linux-gnueabihf-g++ " commandLinePattern="${COMMAND} ${FLAGS} ${OUTPUT_FLAG} ${OUTPUT_PREFIX}${OUTPUT} ${INPUTS}" id="cdt.managedbuild.tool.gnu.cpp.linker.exe.debug.1669966018" name="GCC C++ Linker" superClass="cdt.managedbuild.tool.gnu.cpp.linker.exe.debug"> <option id="gnu.cpp.link.option.paths.462980690" name="Library search path (-L)" superClass="gnu.cpp.link.option.paths" valueType="libPaths"> - <listOptionValue builtIn="false" value="/usr/xenomai/lib"/> <listOptionValue builtIn="false" value="/usr/local/linaro/arm-linux-gnueabihf/include/xenomai/lib"/> - <listOptionValue builtIn="false" value="/import/teaching/ECS732/arm-gcc/arm-linux-gnueabihf/lib"/> <listOptionValue builtIn="false" value="/usr/lib/arm-linux-gnueabihf"/> - <listOptionValue builtIn="false" value="/import/teaching/ECS732/arm-gcc/arm-linux-gnueabihf/lib/xenomai"/> + <listOptionValue builtIn="false" value="/usr/arm-linux-gnueabihf/include/xenomai/lib"/> </option> <option id="gnu.cpp.link.option.libs.139390951" name="Libraries (-l)" superClass="gnu.cpp.link.option.libs" valueType="libs"> <listOptionValue builtIn="false" value="rt"/> @@ -95,6 +93,7 @@ <sourceEntries> <entry excluding="default_main.cpp|audio_routines_old.S" flags="VALUE_WORKSPACE_PATH|RESOLVED" kind="sourcePath" name="core"/> <entry flags="VALUE_WORKSPACE_PATH|RESOLVED" kind="sourcePath" name="include"/> + <entry flags="VALUE_WORKSPACE_PATH" kind="sourcePath" name="projects/scope"/> <entry flags="VALUE_WORKSPACE_PATH" kind="sourcePath" name="source"/> </sourceEntries> </configuration> @@ -183,7 +182,7 @@ <sourceEntries> <entry excluding="default_main.cpp|audio_routines_old.S" flags="VALUE_WORKSPACE_PATH|RESOLVED" kind="sourcePath" name="core"/> <entry flags="VALUE_WORKSPACE_PATH|RESOLVED" kind="sourcePath" name="include"/> - <entry flags="VALUE_WORKSPACE_PATH" kind="sourcePath" name="projects/basic"/> + <entry flags="VALUE_WORKSPACE_PATH" kind="sourcePath" name="projects/scope"/> <entry flags="VALUE_WORKSPACE_PATH" kind="sourcePath" name="source"/> </sourceEntries> </configuration>
--- a/core/ClockSync.cpp Mon Sep 21 03:11:32 2015 +0100 +++ b/core/ClockSync.cpp Mon Sep 21 03:12:21 2015 +0100 @@ -70,7 +70,7 @@ myClock_t ClockSync::send(){ // print(); int ret; - ret=client.waitUntilReady(false, 0); + ret=client.waitUntilReady(false, isSlave() ? 110 : 5); if(ret<=0){ //don't retry return -1; } @@ -270,7 +270,7 @@ // printf("-----------OFFSET IS : %04.4f samples, average: %04.4f samples\n", // offset, movingAverage.getAverage()); } else if (calls==10){ //then compensate for initial offset -// printf("compensating for offset: %f\n", offset); + printf("compensating for offset: %f\n", offset); virtualClock->addOffset(movingAverage.getAverage()); movingAverage.reset(); } else if (calls>=10){ //use IIR filter from now on @@ -289,17 +289,24 @@ pastIn[1]=in; offset=out; static float maxOffset=0; - maxOffset=fabsf(offset) > fabsf(maxOffset) ? offset : maxOffset; - printf("%10.3f, %10.3f, %10.3f, %10.3f\n", in, offset, offset-pastOut[2], maxOffset); //unfiltered, filtered - if(fabsf(offset)>10 && calls>30){ - calls=11; - //TODO: correct for offset - float targetSamplingRate=offset>0 ? 44097 : 44103; -#ifndef USE_JUCE - gAudioCodec->setAudioSamplingRate(targetSamplingRate); -#endif -// pastOut[1]=pastOut[2]=pastIn[1]=pastIn[2]=offset; - printf("------setAudioSmplingRate to %f\n", targetSamplingRate); + if(calls > 0 ) { + maxOffset=fabsf(offset) > fabsf(maxOffset) ? offset : maxOffset; + pid.setError(offset); + float correction=pid.getOutput(); + static float oldSamplingRate=44100; + printf("%10.3f, %10.3f, %10.3f, %10.3f, %10.3f, %10.3f\n", in, offset, offset-pastOut[2], maxOffset, correction, oldSamplingRate); //unfiltered, filtered + // if(fabsf(offset)>3 && calls>30){ + //TODO: correct for offset + // float targetSamplingRate=offset>0 ? 44095 : 44105; + float targetSamplingRate = oldSamplingRate - correction; + #ifndef USE_JUCE +// if(oldSamplingRate != targetSamplingRate) +// gAudioCodec->setAudioSamplingRate(targetSamplingRate); + #endif + oldSamplingRate=targetSamplingRate; + // pastOut[1]=pastOut[2]=pastIn[1]=pastIn[2]=offset; + // printf("------setAudioSmplingRate to %f\n", targetSamplingRate); + // } } } calls++;
--- a/core/ClockSyncThread.cpp Mon Sep 21 03:11:32 2015 +0100 +++ b/core/ClockSyncThread.cpp Mon Sep 21 03:12:21 2015 +0100 @@ -52,11 +52,21 @@ void ClockSyncThread::setVirtualClock(VirtualClock &aVirtualClock){ virtualClock=&aVirtualClock; }; - +#ifndef USE_JUCE +extern I2c_Codec* gAudioCodec; +#endif void ClockSyncThread::run(){ - printf("var=["); + printf("variable=["); while(!threadShouldExit()){ + static int count = 0; clockSync.sendReceiveLoop(); +#ifndef USE_JUCE +// if (count == 300){ +// printf("0 0 0\n"); +// gAudioCodec->setAudioSamplingRate(44101); +// } +#endif + count++; // double now=virtualClock->getNow(); // printf("th(end+1)=%f;\n", now); // printf("act(end+1)=%lld;\n", Clock::getTimeUs());
--- a/core/I2c_Codec.cpp Mon Sep 21 03:11:32 2015 +0100 +++ b/core/I2c_Codec.cpp Mon Sep 21 03:12:21 2015 +0100 @@ -47,8 +47,6 @@ // The master clock PLLCLK_IN is 12MHz // K can be varied in intervals of resolution of 0.0001 up to 63.9999 // using P=8 and R=1 gives a resolution of 0.0732421875Hz ( 0.000166% at 44.1kHz) - // for whatever reason, P=8 does not work (i.e.: setting the sampling rate works fine, - // but when changing K by a small-ish value (0.0040), the clock does not seem to change). // to obtain Fs=44100 we need to have K=60.2112 if(setPllP(7)) @@ -220,7 +218,9 @@ // f_{S(ref)} = (PLLCLK_IN × K × R)/(2048 × P) float k = ((double)(newSamplingRate * pllP * 2048.0f/(float)pllR)) / PLLCLK_IN ; int ret = setPllK(k); -// printf("P: %d, R: %d, J: %d, D: %d\n", pllP, pllR, pllJ, pllD); + float actualSamplingRate = PLLCLK_IN * (pllJ + pllD/10000.0) * pllR / (2048.0 * pllP); + printf("P: %d, R: %d, J: %d, D: %d, samplingRate= %f\n", pllP, pllR, pllJ, pllD, actualSamplingRate ); +// printf("fs_ref=%f;\n",actualSamplingRate); return ret; }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/core/Kalman.cpp Mon Sep 21 03:12:21 2015 +0100 @@ -0,0 +1,24 @@ +/* + * Kalman.cpp + * + * Created on: 20 Sep 2015 + * Author: giulio + */ +#include "Kalman.h" +void KalmanOne::init(double newQ, double newR, double newX){ + A = 1; + H = 1; + Q = newQ; // covariance of the error on the prediction + R = newR; // covariance of the measurement error + x = newX; // 5805.09230769231; % predicted x + P = 6; // predicted covariance + return; +} +double KalmanOne:: process(double z){ + double xp = A*x; // I. Prediction of the estimate + double Pp = A*P*A + Q; // Prediction of the error covariance + double K = Pp*H/(H*Pp*H + R); // II. Computation of Kalman gain + x = xp + K*(z - H*xp); // III. Computation of the estimate + P = Pp - K*H*Pp; // IV. Computation of the error covariance + return x; +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/core/Pid.cpp Mon Sep 21 03:12:21 2015 +0100 @@ -0,0 +1,43 @@ +/* + * Pid.cpp + * + * Created on: 14 Sep 2015 + * Author: giulio + */ + +#include "Pid.h" + +Pid::Pid(){ + integralError = 0; + pastError = 0; + error = 0; + differentialError = 0; + kp = 5; + ki = 2; + kd = 0.8; + idleTimeout = 0; + timeoutCount = 0; + output = 0; +// printf("----------%f %f %f %f %f %f\n", kp, error, ki, integralError, kd, differentialError); +} +void Pid::updateIntegralError(){ + integralError += (error + pastError) * 0.5 * ts; +} +void Pid::updateDifferentialError(){ + differentialError = (error - pastError) / ts; +} +float Pid::setError(float anError){ + pastError = error; + error = anError; + ts = 1; //TODO: this should be passed as a parameter, unless setError() gets always called at constant intervals + updateIntegralError(); + updateDifferentialError(); + output= kp * error + ki * integralError + kd * differentialError; +// printf("%f %f %f %f %f %f %f\n", output, kp, error, ki, integralError, kd, differentialError); + return output; +} +float Pid::getOutput(){ + return output; +} + +
--- a/core/UdpServer.cpp Mon Sep 21 03:11:32 2015 +0100 +++ b/core/UdpServer.cpp Mon Sep 21 03:12:21 2015 +0100 @@ -63,15 +63,15 @@ return select(inSocket+1, &stReadFDS, NULL, NULL, NULL); //calling this with a NULL timeout will block indefinitely FD_ZERO(&stReadFDS); FD_SET(inSocket, &stReadFDS); - if(timeoutMsecs>=1000){ - float timeOutSecs=timeoutMsecs*0.001; - stTimeOut.tv_sec=(long int)timeOutSecs; - timeOutSecs-=(int)timeOutSecs; - stTimeOut.tv_usec=(long int)(timeOutSecs*1000000); - } else //faster! - stTimeOut.tv_usec=(long int)timeoutMsecs*1000; + float timeOutSecs=timeoutMsecs*0.001; + stTimeOut.tv_sec=(long int)timeOutSecs; + timeOutSecs-=(int)timeOutSecs; + long int timeOutUsecs=timeOutSecs*1000000; + stTimeOut.tv_usec=timeOutUsecs; int descriptorReady= select(inSocket+1, &stReadFDS, NULL, NULL, &stTimeOut); - return descriptorReady>0? 1 : descriptorReady; +// printf("stTimeOut.tv_sec=%ld, stTimeOut.tv_usec=%ld, descriptorReady: \n",stTimeOut.tv_sec,stTimeOut.tv_usec, descriptorReady); +// return descriptorReady>0 ? (timeOutUsecs-stTimeOut.tv_usec) : descriptorReady; + return descriptorReady>0 ? 1 : descriptorReady; } int UdpServer::read(//Returns the number of bytes read, or -1 if there was an error.
--- a/core/VirtualClock.cpp Mon Sep 21 03:11:32 2015 +0100 +++ b/core/VirtualClock.cpp Mon Sep 21 03:12:21 2015 +0100 @@ -1,58 +1,75 @@ #include "VirtualClock.h" -void VirtualClock::init(){ +void VirtualClock::init(float initialValueUs){ firstRun=true; movingAverage.setLength(101); //TODO: a better filtering algorithm ( Did you say Kalman?) - period=-1; + blockPeriod=-1; elapsedPeriods=0; startTime=0; - startTimeOffset=0; - elapsedPeriodsOffset=0; + elapsedPeriodsOffset = 0; + lastSyncEstimatedTime = 0; + double coefficients[IIR_FILTER_STAGE_COEFFICIENTS] = { + 0.000241359049041961, 0.000482718098083923, 0.000241359049041961, -1.95557824031504, 0.956543676511203 + }; + iir.setNumberOfStages(4); + iir.setCoefficients(coefficients); + printf("kalmanInit=%f\n",initialValueUs); + kalman.init(0.01, 158575.715009816 /*measured var() */, + initialValueUs +//#ifdef USE_JUCE +// 5804.98866213152 /*blockSize/Fs*1e6*/ +//#else +// 5804.98866213152 /*blockSize/Fs*1e6*/ +//#endif + ); } -VirtualClock::VirtualClock(){ - init(); -} +VirtualClock::VirtualClock(){} void VirtualClock::sync(){ sync(1); } void VirtualClock::sync(double numPeriods){ - myClock_t currentTime=Clock::getTimeUs(); - static int calls=0; - elapsedPeriods+=numPeriods; - if(calls==50){ //TODO: this is dangerous as the clock might jump suddenly if currentTime is not precise - calls=0; - startTimeOffset=startTime; - startTime=currentTime; - elapsedPeriodsOffset=elapsedPeriods; + myClock_t currentTime = Clock::getTimeUs(); + elapsedPeriods += numPeriods; + static int calls = 0; + if(calls == 0){ + startTime = currentTime; +//AA lastSyncEstimatedTime = startTime; + lastSyncEstimatedTime = 0; + } else { + double newBlockPeriod = (currentTime - lastSyncTime); +// period = iir.process(movingAverage.add(newPeriod)); //TODO: replace with Kalman filter + blockPeriod = iir.process(kalman.process(newBlockPeriod)); +// period = 22.6760958210091; + period = blockPeriod / numPeriods; + lastSyncEstimatedTime += (period * numPeriods); +// if(calls == 800) +// lastSyncEstimatedTime = lastSyncTime; +// printf("%lld, %lld\n", lastSyncTime, lastSyncEstimatedTime); } + lastSyncTime = currentTime; +// printf("%lld\n", lastSyncTime); calls++; - if(firstRun==true){ - firstRun=false; - startTime=currentTime; - } else { - double newPeriod=(currentTime-lastSync)/numPeriods; - double expectedPeriod=22.67; - double maxPeriodDeviation=10; - if(fabs(newPeriod-expectedPeriod)<maxPeriodDeviation){ // filtering outliers - period=movingAverage.add(newPeriod); //TODO: replace with Kalman filter - } else { - printf("period out of range: %f\n", newPeriod); - } - } - lastSync=currentTime; -// printf("lastSync: %lld\n",lastSync-startTime); } double VirtualClock::getNow(){ myClock_t currentSystemTime=Clock::getTimeUs(); - if(period<=0){ + if(blockPeriod<=0){ return currentSystemTime; // TODO: this is not very meaningful. } - // double beginningOfPeriod=lastSync; // TODO: if sync() does not get called every time (but e.g. only every so often), - // then this line (and the class) needs editing - myClock_t elapsed=(currentSystemTime-startTime); - double now=elapsedPeriodsOffset + elapsed/(double)period; -// printf("elapsed=%lld; sincelastSync=%lld; period=%f; now=%f\n", elapsed, currentSystemTime-lastSync, period, now); + double elapsed = (currentSystemTime - startTime) - lastSyncEstimatedTime; + double now = elapsedPeriods + elapsed / (double)period; +// if(now>currentSystemTime+10*1e6) +// now=0; +// static long long int pastSy=0; +// printf("%lld\n", currentSystemTime-pastSy); +// pastSy=currentSystemTime; + static int count=0; + count++; +// if(count&1) +#ifdef USE_JUCE +#else +// printf("%f %f %f\n", (currentSystemTime - startTime)/1e6*44100.0, blockPeriod, now); +#endif return now; } @@ -62,8 +79,9 @@ printf("ERROR: periodOffset adjustment of %f resulted in elapsedPeriods=%f\n", periodOffset, elapsedPeriods); exit(1); } + printf("this is not called\n"); movingAverage.reset(); } double VirtualClock::getPeriod(){ - return period; + return blockPeriod; }
--- a/include/ClockSync.h Mon Sep 21 03:11:32 2015 +0100 +++ b/include/ClockSync.h Mon Sep 21 03:12:21 2015 +0100 @@ -5,6 +5,7 @@ #include "UdpClient.h" #include "Clock.h" #include "VirtualClock.h" +#include "Pid.h" #ifdef USE_JUCE #else #include <I2c_Codec.h> @@ -51,6 +52,7 @@ void resetTs(); bool areTsValid(); void processOffset(double offset); + Pid pid; public: ClockSync(){}; ClockSync(bool thisIsSlave, int aPort, VirtualClock &aVirtualClock);
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/include/Kalman.h Mon Sep 21 03:12:21 2015 +0100 @@ -0,0 +1,25 @@ +/* + * Kalman.h + * + * Created on: 20 Sep 2015 + * Author: giulio + */ + +#ifndef KALMAN_H_ +#define KALMAN_H_ + +class KalmanOne{ +public: + double A; + double H; + double Q; + double R; + double x; + double P; + void init(double newQ, double newR, double newX); + double process(double z); +}; + + + +#endif /* KALMAN_H_ */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/include/Pid.h Mon Sep 21 03:12:21 2015 +0100 @@ -0,0 +1,36 @@ +/* + * Pid.h + * + * Created on: 14 Sep 2015 + * Author: giulio + */ + +#ifndef PID_H_ +#define PID_H_ +#include <stdio.h> + +class Pid{ +private: + float integralError; + float pastError; + float error; + float differentialError; + float output; + float kp; + float ki; + float kd; + float ts; + int idleTimeout; + int timeoutCount; + void updateIntegralError(); + void updateDifferentialError(); +public: + Pid(); + float setError(float anError); + void setIdleTimeout(int aIdleTimeout); + float getOutput(); +}; + + + +#endif /* PID_H_ */
--- a/include/VirtualClock.h Mon Sep 21 03:11:32 2015 +0100 +++ b/include/VirtualClock.h Mon Sep 21 03:12:21 2015 +0100 @@ -4,6 +4,8 @@ #include "math.h" #include "stats.hpp" #include "Clock.h" +#include "IirFilter.h" +#include "Kalman.h" #ifdef USE_JUCE #else #include <BeagleRT.h> @@ -13,14 +15,19 @@ private: myClock_t startTime; myClock_t startTimeOffset; - myClock_t lastSync; + myClock_t lastSyncTime; +// myClock_t lastSyncEstimatedTime; + double lastSyncEstimatedTime; bool firstRun; double elapsedPeriods; double elapsedPeriodsOffset; + double blockPeriod; double period; MovingAverage<double> movingAverage; + IirFilter iir; + KalmanOne kalman; public: - void init(); + void init(float initialValueUs); VirtualClock(); /** Call this method at regular intervals to sync che virtual clock
--- a/projects/scope/render.cpp Mon Sep 21 03:11:32 2015 +0100 +++ b/projects/scope/render.cpp Mon Sep 21 03:12:21 2015 +0100 @@ -49,7 +49,7 @@ // scope.setPort(1, 10000); // networkSend.setup(context->audioSampleRate, context->audioFrames, 0, 9999, "192.168.7.1"); // clockSynchronizer.setup(); - virtualClock.init(); + virtualClock.init(context->audioFrames / context->audioSampleRate * 1e6); clockSyncThread.init(true, 5000, virtualClock); //start as slave gInverseSampleRate = 1.0/context->audioSampleRate; @@ -84,7 +84,7 @@ phase+=200.0/44100.0*2*M_PI; if(phase>=2*M_PI) phase-=2*M_PI; - context->audioOut[n*2+1]=rand()/(float)RAND_MAX;context->audioIn[n*2]; + context->audioOut[n*2+1]=rand()/(float)RAND_MAX;//context->audioIn[n*2]; } count++; /*