void CMPerformFFT( CMFFT *fft, float *input, float *output ) { int i, n, nby2 ; n = fft->size ; nby2 = n/2 ; switch ( fft->style ) { case PowerSpectrum: vDSP_ctoz( ( COMPLEX* )input, 2, &fft->z, 1, nby2 ) ; if ( fft->window ) { for ( i = 0; i < nby2; i++ ) { fft->z.realp[i] *= fft->window[i] ; fft->z.imagp[i] *= fft->window[i] ; } } vDSP_fft_zript( fft->vfft, &fft->z, 1, &fft->tempBuf, fft->log2n, FFT_FORWARD ) ; vDSP_vsq( fft->z.realp, 1, fft->z.realp, 1, nby2 ) ; vDSP_vsq( fft->z.imagp, 1, fft->z.imagp, 1, nby2 ) ; vDSP_vadd( fft->z.realp, 1, fft->z.imagp, 1, &output[0], 1, nby2 ) ; break ; default: break ; } }
// windowSize and windowInterval are constrained to be multiples of the block size void DspEnvelope::processDspWithIndex(int fromIndex, int toIndex) { // copy the input into the signal buffer memcpy(signalBuffer + numSamplesReceived, dspBufferAtInlet0, numBytesInBlock); numSamplesReceived += blockSizeInt; numSamplesReceivedSinceLastInterval += blockSizeInt; if (numSamplesReceived >= windowSize) { numSamplesReceived = 0; } if (numSamplesReceivedSinceLastInterval == windowInterval) { numSamplesReceivedSinceLastInterval -= windowInterval; // apply hanning window to signal and calculate Root Mean Square float rms = 0.0f; if (ArrayArithmetic::hasAccelerate) { #if __APPLE__ vDSP_vsq(signalBuffer, 1, rmsBuffer, 1, windowSize); // signalBuffer^2 vDSP_vmul(rmsBuffer, 1, hanningCoefficients, 1, rmsBuffer, 1, windowSize); // * hanning window vDSP_sve(rmsBuffer, 1, &rms, windowSize); // sum the result #endif } else { for (int i = 0; i < windowSize; i++) { rms += signalBuffer[i] * signalBuffer[i] * hanningCoefficients[i]; } } // finish RMS calculation. sqrt is removed as it can be combined with the log operation. // result is normalised such that 1 RMS == 100 dB rms = 10.0f * log10f(rms) + 100.0f; PdMessage *outgoingMessage = getNextOutgoingMessage(0); // graph will schedule this at the beginning of the next block because the timestamp will be // behind the block start timestamp outgoingMessage->setTimestamp(0.0); outgoingMessage->setFloat(0, (rms < 0.0f) ? 0.0f : rms); graph->scheduleMessage(this, 0, outgoingMessage); } }
void siglab_cbPwr(float *src, float *dst, int nfft) { // requires dst to be nel/2+1 element or more // src is in separated Re and Im arrays, A(Im) = A(Re) + NFFT/2 vDSP_vsq(src,1,dst,1,nfft); int nfft2 = nfft/2; vDSP_vadd(dst+1,1,dst+nfft2+1,1,dst+1,1,nfft2-1); }
/******************************************************************************* VectorPower */ Error_t VectorPower(float* dest, const float* in, float power, unsigned length) { #ifdef __APPLE__ if (power == 2.0) { vDSP_vsq(in, 1, dest, 1, length); } else { unsigned i; const unsigned end = 4 * (length / 4); for (i = 0; i < end; i+=4) { dest[i] = powf(in[i], power); dest[i + 1] = powf(in[i + 1], power); dest[i + 2] = powf(in[i + 2], power); dest[i + 3] = powf(in[i + 3], power); } for (i = end; i < length; ++i) { dest[i] = powf(in[i], power); } } #else unsigned i; const unsigned end = 4 * (length / 4); for (i = 0; i < end; i+=4) { dest[i] = powf(in[i], power); dest[i + 1] = powf(in[i + 1], power); dest[i + 2] = powf(in[i + 2], power); dest[i + 3] = powf(in[i + 3], power); } for (i = end; i < length; ++i) { dest[i] = powf(in[i], power); } #endif return NOERR; }
Float32 DTW32_getSimilarityScore(DTW32 *self, Float32 *inputData, size_t inputRowCount, Float32 *comparisonData, size_t comparisonDataRowCount, size_t currentColumnCount) { // Float32_printContiguous2DArray(inputData, inputRowCount, currentColumnCount, "input"); // Float32_printContiguous2DArray(comparisonData, comparisonDataRowCount, currentColumnCount, "compare"); Float32 similarity = INFINITY; self->currentInputRowCount = inputRowCount; self->currentComparisonDataRowCount = comparisonDataRowCount; vDSP_vsq(inputData, 1, self->inputTemp, 1, inputRowCount * currentColumnCount); vDSP_vsq(comparisonData, 1, self->comparisonDataTemp, 1, comparisonDataRowCount * currentColumnCount); vDSP_mtrans(self->inputTemp, 1, self->multiplicationTemp, 1, currentColumnCount, inputRowCount); vDSP_mmul(self->ones, 1, self->multiplicationTemp, 1, self->inputTemp, 1, 1, inputRowCount, currentColumnCount); vDSP_mtrans(self->comparisonDataTemp, 1, self->multiplicationTemp, 1, currentColumnCount, comparisonDataRowCount); vDSP_mmul(self->ones, 1, self->multiplicationTemp, 1, self->comparisonDataTemp, 1, 1, comparisonDataRowCount, currentColumnCount); const int elementCountInput = (int)inputRowCount; const int elementCountComparisonData = (int)comparisonDataRowCount; vvsqrtf(self->inputTemp, self->inputTemp, &elementCountInput); vvsqrtf(self->comparisonDataTemp, self->comparisonDataTemp, &elementCountComparisonData); cblas_sgemm(CblasRowMajor, CblasNoTrans, CblasTrans, (SInt32)inputRowCount, (SInt32)comparisonDataRowCount, 1, 1.0, self->inputTemp, 1, self->comparisonDataTemp, 1, 0., self->normalisationMatrix, (SInt32)comparisonDataRowCount); cblas_sgemm(CblasRowMajor, CblasNoTrans, CblasTrans, (SInt32)inputRowCount, (SInt32)comparisonDataRowCount, (SInt32)currentColumnCount, 1.0, inputData, (SInt32)currentColumnCount, comparisonData, (SInt32)currentColumnCount, 0., self->distanceMatrix, (SInt32)comparisonDataRowCount); vDSP_vdiv(self->normalisationMatrix, 1, self->distanceMatrix, 1, self->distanceMatrix, 1, inputRowCount * comparisonDataRowCount); // Float32_printContiguous2DArray(self->distanceMatrix, inputRowCount, comparisonDataRowCount, "norm"); Float32 minusOne = -1.f; vDSP_vsma(self->distanceMatrix, 1, &minusOne, self->ones, 1, self->distanceMatrix, 1, inputRowCount * comparisonDataRowCount); // Float32_printContiguous2DArray(self->distanceMatrix, inputRowCount, comparisonDataRowCount, "norm"); vDSP_mmov(self->distanceMatrix, &self->globalDistanceMatrix[comparisonDataRowCount + 2], comparisonDataRowCount, inputRowCount, comparisonDataRowCount, comparisonDataRowCount + 1); Float32 nan = NAN; vDSP_vfill(&nan, &self->globalDistanceMatrix[1], 1, comparisonDataRowCount); vDSP_vfill(&nan, &self->globalDistanceMatrix[comparisonDataRowCount + 1], comparisonDataRowCount + 1, inputRowCount); Float32 comparisonArray[3] = {0}; for (size_t i = 0; i < inputRowCount; ++i) { for (size_t j = 0; j < comparisonDataRowCount; ++j) { comparisonArray[0] = self->globalDistanceMatrix[i * (comparisonDataRowCount + 1) + j]; comparisonArray[1] = self->globalDistanceMatrix[i * (comparisonDataRowCount + 1) + (j + 1)]; comparisonArray[2] = self->globalDistanceMatrix[(i + 1) * (comparisonDataRowCount + 1) + j]; Float32 dmax; size_t index; vDSP_minvi(comparisonArray, 1, &dmax, &index, 3); self->phi[(i * comparisonDataRowCount) + j] = index + 1; self->globalDistanceMatrix[(i + 1) * (comparisonDataRowCount + 1) + (j + 1)] = self->globalDistanceMatrix[(i + 1) * (comparisonDataRowCount + 1) + (j + 1)] + dmax; } } similarity = self->globalDistanceMatrix[(comparisonDataRowCount + 1) * (inputRowCount + 1) - 1]; return similarity; }