Commit 576cd3b4 authored by 杉下大河's avatar 杉下大河
Browse files

DSPライブラリ未使用版実装完了…まぁ重いよね

parent 5729f693
...@@ -3,8 +3,10 @@ ...@@ -3,8 +3,10 @@
{ {
"name": "Win32", "name": "Win32",
"includePath": [ "includePath": [
"${workspaceRoot}",
"C:\\Users\\morson\\AppData\\Local\\Arduino15\\packages\\STM32\\tools\\**", "C:\\Users\\morson\\AppData\\Local\\Arduino15\\packages\\STM32\\tools\\**",
"C:\\Users\\morson\\AppData\\Local\\Arduino15\\packages\\STM32\\hardware\\stm32\\1.9.0\\**", "C:\\Users\\morson\\AppData\\Local\\Arduino15\\packages\\STM32\\hardware\\stm32\\1.9.0\\**",
"C:\\Program Files (x86)\\Arduino\\libraries\\**",
"C:\\Users\\morson\\Documents\\Arduino\\libraries\\**" "C:\\Users\\morson\\Documents\\Arduino\\libraries\\**"
], ],
"forcedInclude": [ "forcedInclude": [
......
#define _USE_MATH_DEFINES //for Visual Studio #define _USE_MATH_DEFINES //for Visual Studio
#include "ANCcontroller.h" #include "ANCcontroller.h"
WaveGenerator::WaveGenerator() WaveGenerator::WaveGenerator(int sp_rate,int quantifying_bit_number)
{ {
AS_nBIT_MAX_NUM = pow(2,quantifying_bit_number)-1;
SAMPLE_RATE = sp_rate;
CreateSinWave(); CreateSinWave();
CreateChirpWave(); CreateChirpWave();
} }
//sin波作る //符号あり整数値sin波を生成する(-AS_nBIT_MAX_NUM ~ AS_nBIT_MAX_NUM)
void WaveGenerator::CreateSinWave() { void WaveGenerator::CreateSinWave() {
auto rad_step = 2 * M_PI * FREQ / SAMPLE_RATE; auto rad_step = 2 * M_PI * FREQ / SAMPLE_RATE;
for (int i = 0; i < SAMPLE_RATE / FREQ; i++) for (int i = 0; i < SAMPLE_RATE ; i++)
{ {
wave_sin.push_back(AS_16BIT_MAX_NUM * sin(rad_step * i) *GAIN); wave_sin.push_back(AS_nBIT_MAX_NUM * sin(rad_step * i) *GAIN);
} }
} }
...@@ -47,22 +49,54 @@ void WaveGenerator::CreateChirpWave() { ...@@ -47,22 +49,54 @@ void WaveGenerator::CreateChirpWave() {
for (const auto & w : waveChirpSignal) { for (const auto & w : waveChirpSignal) {
waveChirp.emplace_back(int(w * AS_16BIT_MAX_NUM * GAIN)); waveIntChirp.emplace_back(int(w * AS_nBIT_MAX_NUM * GAIN));
}
for (const auto & w : waveChirpSignal) {
waveUnsingedIntChirp.emplace_back(int((w+1) * AS_nBIT_MAX_NUM * GAIN * 0.5));
} }
} }
//16bit情報に変換したsinを吐き出す //1コールに付き1信号分sinを吐き出す
int16_t WaveGenerator::playWaveSin() int16_t WaveGenerator::playWaveSin(char mode)
{ {
auto out = wave_sin[sound_cnt % wave_sin.size()]; int out=0;
switch(mode){
case INT_WAVE:
out = wave_sin[sound_cnt % wave_sin.size()];
break;
case UNSINGED_INT_WAVE:
out = (wave_sin[sound_cnt % wave_sin.size()]+AS_nBIT_MAX_NUM)/2;
break;
case FLOAT_WAVE:
//TODO もし実装するならCreateSinWaveを直すところから
break;
}
sound_cnt++; sound_cnt++;
return out; return out;
} }
//16bit情報に変換したチャープ信号を吐き出す //1コールに付き1信号分チャープ信号を吐き出す
int16_t WaveGenerator::playWaveCharp() int16_t WaveGenerator::playWaveCharp(char mode)
{ {
auto out = waveChirp[sound_cnt % waveChirp.size()]; int out=0;
switch(mode){
case INT_WAVE:
out = waveIntChirp[sound_cnt % waveIntChirp.size()];
break;
case UNSINGED_INT_WAVE:
out = waveUnsingedIntChirp[sound_cnt % waveUnsingedIntChirp.size()];
break;
case FLOAT_WAVE:
//TODO もし実装するならCreateSinWaveを直すところから
break;
}
sound_cnt++; sound_cnt++;
return out; return out;
} }
...@@ -220,3 +254,17 @@ float ANC_Controller::calcANCwave(const char methodNum , float errGain , float r ...@@ -220,3 +254,17 @@ float ANC_Controller::calcANCwave(const char methodNum , float errGain , float r
return DB.y; return DB.y;
} }
void ANC_Controller::printCoefC(){
for(const auto& e : DB.coefC){
printf("%d,",e);
}
printf("\n");
}
void ANC_Controller::printCoefH(){
for(const auto& e : DB.coefH){
printf("%d,",e);
}
printf("\n");
}
\ No newline at end of file
...@@ -4,48 +4,47 @@ ...@@ -4,48 +4,47 @@
#include <deque> #include <deque>
#include <numeric> #include <numeric>
#include <math.h> #include <math.h>
//#include <stdlib.h>
#include <Arduino.h>
#include "array.h" #include "array.h"
class WaveGenerator class WaveGenerator
{ {
private: private:
const int16_t AS_16BIT_MAX_NUM = 32767; const int16_t AS_16BIT_MAX_NUM = 32767;
const int16_t AS_12BIT_MAX_NUM = 4095;
const float FREQ = 120; const float FREQ = 120;
const float SAMPLE_RATE = 48000;
const float GAIN = 0.8; const float GAIN = 0.8;
float SAMPLE_RATE;
int AS_nBIT_MAX_NUM; //量子化ビット数から算出した最大値(dex)
//charp信号用_Juceから移植したのでリファクタリング推奨 //charp信号用_Juceから移植したのでリファクタリング推奨
const float fMin = 50; const float fMin = 50;
const float fMax = 700; const float fMax = 700;
const float tLength = 0.15; const float tLength = 0.15;
std::deque<int16_t> wave_sin; std::deque<int16_t> wave_sin;
std::deque<int16_t> waveChirp; std::deque<int16_t> waveIntChirp;
std::deque<int16_t> waveUnsingedIntChirp;
void CreateSinWave(); void CreateSinWave();
void CreateChirpWave(); void CreateChirpWave();
public: public:
uint32_t sound_cnt = 0; static const char INT_WAVE = 0;
static const char UNSINGED_INT_WAVE = 1;
WaveGenerator(); static const char FLOAT_WAVE = 2;
int16_t playWaveSin(); uint32_t sound_cnt = 0;
int16_t playWaveCharp();
void dumpWaveDat() {
#if 0 //チャープ信号の内容をCSVで出力できます
std::string outFileName = "Charpwave.csv";
std::ofstream wavedat(outFileName);
for (auto &w : waveChirpSignal )
wavedat << w << ",";
#endif
} WaveGenerator(int sp_rate,int quantifying_bit_number);
int16_t playWaveSin(char mode);
int16_t playWaveCharp(char mode);
}; };
...@@ -59,7 +58,7 @@ class ANC_DataBase { ...@@ -59,7 +58,7 @@ class ANC_DataBase {
//WaveBufLen >= CoefLenであること //WaveBufLen >= CoefLenであること
static const int16_t CoefWLen = (882 + 2400) ; static const int16_t CoefWLen = (882 + 2400) ;
static const int16_t CoefCLen = 900 ; static const int16_t CoefCLen = 300 ;//900
static const int16_t CoefHLen = 3800; static const int16_t CoefHLen = 3800;
inoArray<float, CoefCLen> coefC;//主経路 inoArray<float, CoefCLen> coefC;//主経路
...@@ -146,6 +145,9 @@ class ANC_Controller { ...@@ -146,6 +145,9 @@ class ANC_Controller {
//算出後の波形データを吐き出す //算出後の波形データを吐き出す
float playANCwave() {return DB.y;} float playANCwave() {return DB.y;}
void printCoefH();
void printCoefC();
private: private:
}; };
#include "ANCcontroller.h"
//#include <STM32ADC.h>
//#include <libmaple/adc.h>
//#include <CMSIS_DSP.h>
HardwareTimer Timer1(TIM1); HardwareTimer Timer1(TIM1);
// the setup function runs once when you press reset or power the board // the setup function runs once when you press reset or power the board
uint8_t sw = LOW; uint8_t sw = LOW;
int sensorPin = A6; // select the input pin for the potentiometer int sensorPin = A6; // select the input pin for the potentiometer
int biasPin = A12; int biasPin = A12;
int audioOut = A13; int audioOutPin = A13;
int sensorValue = 0; // variable to store the value coming from the sensor
const int Q_BIT_NUM = 12;
const int AS_SYS_SAMPLERATE = 4000*2;
const int AUDIO_BIAS = 2482;//3.3V中の2V(12bit)
char anc_state;
bool Sendflg = true; bool Sendflg = true;
bool calocReadyFlg = false;
int sendTimingCnt=0; int sendTimingCnt=0;
int audioInValue = 0; // variable to store the value coming from the sensor
int audioOutValue = 0;
uint32_t t1,t2;
WaveGenerator s_sound(AS_SYS_SAMPLERATE,Q_BIT_NUM);
ANC_Controller ANC;
void sendDebugdat(){ void sendDebugdat(){
sw ^=1; sw ^=1;
digitalWrite(LED_GREEN, sw); digitalWrite(LED_GREEN, sw);
printf("%d\n",sensorValue); printf("%d\n",audioInValue);
} }
//adcは最適値を設定すれば高速化できる余地あり現在30μs
void audioreader() { void audioreader() {
sensorValue = analogRead(sensorPin);//多分12bitで読み取る
audioInValue = analogRead(sensorPin);//多分12bitで読み取る
analogWrite(audioOutPin,audioOutValue);
sendTimingCnt++;
calocReadyFlg = true;
}
void audioreader_debug() {
t1 = micros();
audioInValue = analogRead(sensorPin);//多分12bitで読み取る
sendTimingCnt++; sendTimingCnt++;
analogWrite(audioOut,sensorValue*5);
t2 = micros();
printf(" t=%d \n",t2-t1);
} }
void setup() { void setup() {
// initialize digital pin LED_BUILTIN as an output. // initialize digital pin LED_BUILTIN as an output.
pinMode(LED_GREEN, OUTPUT); pinMode(LED_GREEN, OUTPUT);
pinMode(audioOut, OUTPUT); pinMode(audioOutPin, OUTPUT);
pinMode(biasPin, OUTPUT); pinMode(biasPin, OUTPUT);
pinMode(sensorPin,INPUT_ANALOG);
analogWriteResolution(12);//analogwriteを12bit(MAX4095)で利用できるように設定 analogWriteResolution(Q_BIT_NUM);//analogwriteを12bit(MAX4095)で利用できるように設定
analogReadResolution(12); analogReadResolution(Q_BIT_NUM);
analogWrite(biasPin,2482); analogWrite(biasPin,2482);//MAX3.3vの2.0V
Timer1.pause(); // タイマー停止 Timer1.pause(); // タイマー停止
//Timer1.setOverflow(4000,HERTZ_FORMAT); // 4000Hzで呼び出し
Timer1.setOverflow(48000,HERTZ_FORMAT); // 48000Hzで呼び出し Timer1.setOverflow(AS_SYS_SAMPLERATE,HERTZ_FORMAT);//サンプルレートHzでよびだす
Timer1.attachInterrupt( // 割り込みハンドラの登録 Timer1.attachInterrupt( // 割り込みハンドラの登録
audioreader // 呼び出す関数 audioreader // 呼び出す関数
); );
...@@ -43,13 +76,42 @@ void setup() { ...@@ -43,13 +76,42 @@ void setup() {
Timer1.refresh(); // タイマ更新 Timer1.refresh(); // タイマ更新
Timer1.resume(); // タイマースタート Timer1.resume(); // タイマースタート
tone(PB4,200); tone(PB4,200);
analogWrite(biasPin,2482); analogWrite(biasPin,AUDIO_BIAS);
anc_state = ANC.IDENTIFICAT_COEFC;
} }
// the loop function runs over and over again forever // the loop function runs over and over again forever
void loop() { void loop() {
if(sendTimingCnt >= 2000){ //デバグ情報の送信
if(sendTimingCnt >= AS_SYS_SAMPLERATE / 4){
sendDebugdat(); sendDebugdat();
sendTimingCnt=0; sendTimingCnt=0;
} }
//ANC状態の管理
if (anc_state == ANC.IDENTIFICAT_COEFC) {
t1 = micros();
//伝達関数の推定をしている。非同期処理なのでタイミングがずれるかも
if(calocReadyFlg){
ANC.calc2ndPassTF(audioInValue-AUDIO_BIAS,audioOutValue);
audioOutValue = s_sound.playWaveCharp(s_sound.UNSINGED_INT_WAVE);
calocReadyFlg=false;
}
t2 = micros();
printf(" t=%d \n",t2-t1);
//起動から15sでモード移行 正確に処理したい場合はタイマーを使おう!
if (millis() > 15 * 1000) {
ANC.printCoefC();
anc_state = ANC.ACTIVATION_ANC;
}
}
else if (anc_state == ANC.ACTIVATION_ANC) {
audioOutValue = 0;
}
} }
...@@ -10,5 +10,11 @@ ...@@ -10,5 +10,11 @@
"path": "..\\IMC_ANC_test" "path": "..\\IMC_ANC_test"
} }
], ],
"settings": {} "settings": {
"files.associations": {
"xiosbase": "cpp",
"xlocale": "cpp",
"ios": "cpp"
}
}
} }
\ No newline at end of file
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment