Indholdsfortegnelse:

3 -faset sinusbølge -generator baseret på Arduino Due: 5 trin
3 -faset sinusbølge -generator baseret på Arduino Due: 5 trin

Video: 3 -faset sinusbølge -generator baseret på Arduino Due: 5 trin

Video: 3 -faset sinusbølge -generator baseret på Arduino Due: 5 trin
Video: Работа с крупноформатной плиткой. Оборудование. Бесшовная укладка. Клей. 2024, Juli
Anonim
3 -faset sinusbølge -generator baseret på Arduino Due
3 -faset sinusbølge -generator baseret på Arduino Due

formålet med denne deling er at hjælpe nogen, der forsøger at udnytte Due's større ydeevne + mangel på reference + ikke-nyttigt datablad.

dette projekt er i stand til at generere op til 3 -faset sinusbølge @ 256 prøver / cyklus ved lav frekvens (<1kHz) og 16 prøver / cyklus @ høj frekvens (op til 20kHz), hvilket er godt nok til at udjævnes ved simple LPF'er og output er næsten perfekt.

den vedhæftede fil var ikke min endelige version, for jeg tilføjede en ekstra funktion, men kernen er den samme. Bemærk prøverne/cyklussen blev sat lavere end ovenstående erklæring.

da CPU -kapaciteten maksimeres ved den fremgangsmåde, der er vist i den vedhæftede fil, brugte jeg en Arduino Uno som kontrolenhed, der udnytter Arduino Due's eksterne afbrydelse til at videregive frekvensværdi til Arduino Due. Ud over frekvenskontrol styrer Arduino Uno også amplitude (gennem digital potentialmåler + OpAmp) samt I/O --- der vil være meget plads at lege med.

Trin 1: Generer sinusdatamatrix

Da beregning i realtid er CPU-krævende, kræves et sinusdatamatrix for bedre ydeevne

uint32_t sin768 PROGMEM =….imens x = [0: 5375]; y = 127+127*(sin (2*pi/5376/*eller nogle # du foretrækker afhænger af krav*/))

Trin 2: Aktivering af parallel output

I modsætning til Uno har Due begrænset reference. Men for at generere 3 -faset sinusbølge baseret på Arduino Uno, først og fremmest, er ydeevnen ikke applaus på grund af dens lave MCLK (16MHz, mens Due er 84MHz), 2., det er begrænset GPIO kan producere maks. 2 -faset output, og du har brug for yderligere analogt kredsløb til fremstilling af 3. fase (C = -AB).

At følge GPIO -aktivering var for det meste baseret på forsøg og forsøg+ikke et nyttigt datablad for SAM3X

PIOC-> PIO_PER = 0xFFFFFFFE; // PIO-controller PIO Aktiver register (se p656 i ATMEL SAM3X-datablad) og https://arduino.cc/en/Hacking/PinMappingSAM3X, Arduino Due pin 33-41 og 44-51 blev aktiveret

PIOC-> PIO_OER = 0xFFFFFFFE; // PIO controller output output register, se p657 i ATMEL SAM3X datablad PIOC-> PIO_OSR = 0xFFFFFFFE; // PIO controller output status status register, se p658 i ATMEL SAM3X datablad

PIOC-> PIO_OWER = 0xFFFFFFFE; // PIO output skrive aktiveringsregister, se p670 i ATMEL SAM3X datablad

// PIOA-> PIO_PDR = 0x30000000; // valgfri som forsikring, synes ikke at påvirke ydeevnen, digital pin 10 tilsluttes både PC29 og PA28, digital pin 4 tilsluttes både PC29 og PA28, her for at deaktivere deaktiver PIOA #28 & 29

Trin 3: Aktivering af afbrydelse

For at maksimere ydelsen skal CPU -belastningen være så lav som muligt. På grund af ikke-1to1-korrespondancen mellem CPU-stiften og Due-stiften er bitoperation imidlertid nødvendig.

Du kan yderligere optimere algoritmen, men rummet er meget begrænset.

void TC7_Handler (void) {TC_GetStatus (TC2, 1);

t = t%prøver; // brug t%prøver i stedet for 'hvis' for at undgå overløb af t

phaseAInc = (forudindstillet*t)%5376; // brug %5376 for at undgå array -indeksoverløb

phaseBInc = (phaseAInc+1792)%5376;

phaseCInc = (phaseAInc+3584)%5376;

p_A = sin768 [phaseAInc] << 1; // se PIOC: PC1 til PC8, tilsvarende Arduino Due pin: pin 33-40, skift derfor til venstre for 1 ciffer

p_B = sin768 [phaseBInc] << 12; // se PIOC: PC12 til PC19, tilsvarende Arduino Due pin: pin 51-44, skift derfor til venstre 12 cifre

p_C = sin768 [phaseCInc]; // fase C -udgang anvender PIOC: PC21, PC22, PC23, PC24, PC25, PC26, PC28 og PC29, tilsvarende Arduino Due pin: digital pin: 9, 8, 7, 6, 5, 4, 3, 10

p_C2 = (p_C & B11000000) << 22; // dette genererer PC28 og PC29

p_C3 = (p_C & B00111111) << 21; // dette genererer PC21-PC26

p_C = p_C2 | p_C3; // dette genererer parallel output af fase C

p_A = p_A | p_B | p_C; // 32 bit output = fase A (8bit) | fase B | fase C

PIOC-> PIO_ODSR = p_A; // output register = p_A

t ++; }

Trin 4: R/2R DAC

bygge 3x8bit R/2R DAC, masser af ref på google.

Trin 5: Fuld kode

#define _BV (x) (1 << (x)); uint32_t sin768 PROGMEM = /* x = [0: 5375]; y = 127+127*(sin (2*pi/5376))*/

uint32_t p_A, p_B, p_C, p_C2, p_C3; // fase A fase B fase C værdi-selvom output kun er 8bits, vil p_A og p_B værdi blive betjent for at generere en ny 32 bit værdi for at klare 32bit PIOC output

uint16_t phaseAInc, phaseBInc, phaseCInc, freq, freqNy; uint32_t interval; uint16_t prøver, forudindstillede; uint32_t t = 0;

ugyldig opsætning () {

// parallel output PIOC-opsætning: Arduino Due pin33-40 bruges som fase A-output, mens pin 44-51 arbejder for fase B-output

PIOC-> PIO_PER = 0xFFFFFFFE; // PIO-controller PIO Aktiver register (se p656 i ATMEL SAM3X-datablad) og https://arduino.cc/en/Hacking/PinMappingSAM3X, Arduino Due pin 33-41 og 44-51 blev aktiveret

PIOC-> PIO_OER = 0xFFFFFFFE; // PIO controller output output register, se p657 i ATMEL SAM3X datablad

PIOC-> PIO_OSR = 0xFFFFFFFE; // PIO controller output status status register, se p658 i ATMEL SAM3X datablad

PIOC-> PIO_OWER = 0xFFFFFFFE; // PIO output skrive aktiveringsregister, se p670 i ATMEL SAM3X datablad

// PIOA-> PIO_PDR = 0x30000000; // valgfri som forsikring, synes ikke at påvirke ydeevnen, digital pin 10 tilsluttes både PC29 og PA28, digital pin 4 tilsluttes både PC29 og PA28, her for at deaktivere deaktivering af PIOA #28 & 29 // timeropsætning, se https://arduino.cc/en/Hacking/PinMappingSAM3X, pmc_set_writeprotect (falsk); // deaktiver skrivebeskyttelse af Power Management Control -registre

pmc_enable_periph_clk (ID_TC7); // Aktiver tidstæller for perifert ur 7

TC_Configure (/ * clock */TC2,/ * channel */1, TC_CMR_WAVE | TC_CMR_WAVSEL_UP_RC | TC_CMR_TCCLKS_TIMER_CLOCK1); // TC -ur 42MHz (ur, kanal, sammenligningstilstandsindstilling) TC_SetRC (TC2, 1, interval); TC_Start (TC2, 1);

// aktiver timerafbrydelser på timeren TC2-> TC_CHANNEL [1]. TC_IER = TC_IER_CPCS; // IER = afbryd aktiveringsregister TC2-> TC_CHANNEL [1]. TC_IDR = ~ TC_IER_CPCS; // IDR = afbryd deaktiver register

NVIC_EnableIRQ (TC7_IRQn); // Aktiver afbrydelsen i den indlejrede vektorafbrydelsesstyringsfreq = 60; // initialiser frekvensen som 60Hz forudindstillet = 21; // stigning i matrixindeks med 21 prøver = 256; // output -prøver 256/cyklusinterval = 42000000/(freq*prøver); // afbryd tællinger TC_SetRC (TC2, 1, interval); // start TC Serial.begin (9600); // til testformål}

ugid checkFreq ()

{freqNew = 20000;

hvis (freq == freqNew) {} andet

{freq = freqNy;

hvis (freq> 20000) {freq = 20000; /*maks. frekvens 20 kHz*/};

hvis (freq <1) {freq = 1; /*min frekvens 1Hz*/};

hvis (freq> 999) {forudindstillet = 384; samples = 14;} // for frekvens> = 1kHz, 14 samples for hver cyklus

ellers hvis (freq> 499) {forudindstillet = 84; samples = 64;} // for 500 <= frekvens99) {forudindstillet = 42; samples = 128;} // for 100Hz <= frekvens <500Hz, 128 prøver/cyklus

ellers {forudindstillet = 21; prøver = 256;}; // for frekvens <100 Hz, 256 prøver for hver cyklus

interval = 42000000/(freq*prøver); t = 0; TC_SetRC (TC2, 1, interval); }}

void loop () {

checkFreq (); forsinkelse (100); }

ugyldig TC7_Handler (ugyldig)

{TC_GetStatus (TC2, 1);

t = t%prøver; // brug t%-prøver for at undgå overløb af t phaseAInc = (forudindstillet*t)%5376; // brug %5376 for at undgå array -indeksoverløb

phaseBInc = (phaseAInc+1792)%5376;

phaseCInc = (phaseAInc+3584)%5376;

p_A = sin768 [phaseAInc] << 1; // se PIOC: PC1 til PC8, tilsvarende Arduino Due pin: pin 33-40, skift derfor til venstre for 1 ciffer

p_B = sin768 [phaseBInc] << 12; // se PIOC: PC12 til PC19, tilsvarende Arduino Due pin: pin 51-44, skift derfor til venstre 12 cifre

p_C = sin768 [phaseCInc]; // fase C -udgang anvender PIOC: PC21, PC22, PC23, PC24, PC25, PC26, PC28 og PC29, tilsvarende Arduino Due pin: digital pin: 9, 8, 7, 6, 5, 4, 3, 10

p_C2 = (p_C & B11000000) << 22; // dette genererer PC28 og PC29

p_C3 = (p_C & B00111111) << 21; // dette genererer PC21-PC26 //Serial.println(p_C3, BIN); p_C = p_C2 | p_C3; // dette genererer parallel output af fase C

p_A = p_A | p_B | p_C; // 32 bit output = fase A (8bit) | fase B | fase C //Serial.println(p_A>>21, BIN); // PIOC-> PIO_ODSR = 0x37E00000;

PIOC-> PIO_ODSR = p_A; // output register = p_A t ++; }

Anbefalede: