Commit 5fc67d3b authored by Jake Read's avatar Jake Read

at video of operation

parent eb0a69c5
......@@ -167,6 +167,7 @@ That's it for now.
- One chip is both BLDC driver and Stepper driver ?
- software-selectable gain, pwm mode, etc
- notes in code for shunt calculation
- dipswitch for manual gate enable ! no more tiny-outs ! ?
# Footnotes
1. Part Number. Searching Digikey (or octopart, or what have you) for bits is an art, kind of. It's intimidating, but offers much gold at the end of the rainbow.
......
......@@ -36,7 +36,7 @@ Loc="0 0 1919 1039"
State=1
Number=2
File="mkbldcdriver.sch"
View="22.7296 -3.86164 205.412 59.2135"
View="-18.3248 -28.0797 297.35 80.9142"
WireWidths=" 0.0762 0.1016 0.127 0.15 0.2 0.2032 0.254 0.3048 0.4064 0.508 0.6096 0.8128 1.016 1.27 2.54 0.1524"
PadDiameters=" 0.254 0.3048 0.4064 0.6096 0.8128 1.016 1.27 1.4224 1.6764 1.778 1.9304 2.1844 2.54 3.81 6.4516 0"
PadDrills=" 0.2 0.25 0.3 0.35 0.4 0.45 0.5 0.55 0.65 0.7 0.75 0.8 0.85 0.9 1 0.6"
......@@ -75,7 +75,7 @@ ArcDirection=0
AddLevel=2
PadsSameType=0
Layer=91
Views=" 1: 22.7296 -3.86164 205.412 59.2135"
Views=" 1: -18.3248 -28.0797 297.35 80.9142"
Sheet="1"
[Win_2]
......@@ -84,7 +84,7 @@ Loc="0 0 1919 1039"
State=1
Number=1
File="mkbldcdriver.brd"
View="-13.2576 7.21144 74.7968 63.1623"
View="-7.02111 10.2916 81.0333 66.2425"
WireWidths=" 0.0762 0.1016 0.127 0.15 0.2 0.2032 0.254 0.3048 0.4064 0.508 0.6096 0.8128 1.016 1.27 2.54 0.1524"
PadDiameters=" 0.254 0.3048 0.4064 0.6096 0.8128 1.016 1.27 1.4224 1.6764 1.778 1.9304 2.1844 2.54 3.81 6.4516 0"
PadDrills=" 0.2 0.25 0.3 0.35 0.4 0.45 0.5 0.55 0.65 0.7 0.75 0.8 0.85 0.9 1 0.6"
......@@ -131,7 +131,7 @@ State=1
Number=0
[Desktop]
Screen="3840 2160"
Screen="3840 1080"
Window="Win_1"
Window="Win_2"
Window="Win_3"
......@@ -221,4 +221,14 @@ I'm using the ATSAM's SPI Peripheral. I am *really* swimming in the datasheet at
Although I've double checked through the layers, it seems like I'm getting my MOSI output on the CLK line... ah, I was reading my labels incorrectly.
OK - I've got this set up properly. Now I'll try plugging the encoder in an reading some values!
\ No newline at end of file
OK - I've got this set up properly. Now I'll try plugging the encoder in an reading some values!
Great, and with a shift in some setting (I was wrong) I'm reading SPI values nicely. Next test is to see if these values get all messed up when I turn the motor on (update: nope, yay), introducing lots of EMF and noise into the system... Then I'll write some open-loop commutation using the encoder values (update: done). Then I'll think about writing a simple PID position loop. If I get through all of that tonight, I'll go to bed (haha).
But what's the larger goal here? I have one more day.
Also: a note, I'm having odd reset events occasionally. Related to the earlier issue w/ usb power. I think I need to revisit the 'bfpsu' issue - wherein I want a 24V PSU that will deliver nice consistent power ~ 65 amps (that's about as much juice as is possible to pull out of a wall socket). I may need to build this, as these don't seem readily available. My other thought is to find a big switching PSU, and hook up a *giant* capacitor to the output to smooth it out.
OMG it's the SWITCH is being super intermittent. Don't use a switch rated for 7.5 amps past 7.5 amps. Heck!
OK - like 8th loop on this. I fixed that wiring and was still having a reset issue. Back at it now, added extra capacitance to the 5V output, and a diode that I had previously omitted soldering on. Seems better, but I make no promises to myself.
\ No newline at end of file
......@@ -370,7 +370,6 @@
<Value>../src/ASF/sam/drivers/wdt</Value>
</ListValues>
</armgcc.compiler.directories.IncludePaths>
<armgcc.compiler.optimization.level>Optimize (-O1)</armgcc.compiler.optimization.level>
<armgcc.compiler.optimization.OtherFlags>-fdata-sections</armgcc.compiler.optimization.OtherFlags>
<armgcc.compiler.optimization.PrepareFunctionsForGarbageCollection>True</armgcc.compiler.optimization.PrepareFunctionsForGarbageCollection>
<armgcc.compiler.optimization.DebugLevel>Maximum (-g3)</armgcc.compiler.optimization.DebugLevel>
......
......@@ -231,6 +231,19 @@ void UART0_Handler(){
}
}
void readencoder(uint16_t *data){
while(!(SPI0->SPI_SR & SPI_SR_TXEMPTY)); // wait 4 ready
SPI0->SPI_TDR = SPI_TDR_TD(0xFFFF);// | SPI_TDR_PCS(1);
while(!(SPI0->SPI_SR & SPI_SR_TXEMPTY)); // wait 4 ready
SPI0->SPI_TDR = SPI_TDR_TD(0x0000);// | SPI_TDR_PCS(1);
*data = SPI0->SPI_RDR & SPI_RDR_RD_Msk;
//uint16_t pard = data >> 15;
*data = *data << 2; // shift parity and error bit out
*data /= 4;
}
int main (void)
{
/* Insert system clock initialization code here (sysclk_init()). */
......@@ -238,119 +251,130 @@ int main (void)
board_init();
sysclk_init();
wdt_disable(WDT);
abcdselects();
setuppwm();
setuppio();
setupuart();
tp2 = tinyport_new(UART0, PIOA, PERIPHERAL_A, PIO_PER_P9, PIO_PER_P10);
tp_init(&tp2);
setupinterrupts();
setupspi();
startupflash();
uarthello();
uint8_t maxscalar = 64;
uint8_t scalar = 26; // 0 -> 255 (these will be chars from serial)
uint8_t scalar = 24; // 0 -> 255 (these will be chars from serial)
uint8_t period = 20; // us between ++ in phase
uint32_t phaseu = 0; // 0 -> 1023
uint32_t phasev = 341; // advanced 120 degrees
uint32_t phasew = 682; // advanced 240 degrees
gates(0); // boots the gates, or don't
gates(1); // boots the gates, or don't
/* Command Table
uint32_t putCounter = 0;
0 <0> | <1> - run close or open gates
1 <val> - open loop terq
2 <val> - period to run open loop on
3 <0> | - read encoder, or cal,
*/
uint16_t offset = 100;
uint16_t reverse = 1; // encoder
uint16_t dir = 1; // commutation
uint16_t resolution = 16384;
uint16_t modulo = 2340; // AS5047_RESOLUTION / MOTOR_POLEPAIRS -> MT4108 = 1489 || MT5208 = 2340
while(1){
uint16_t data = 0xFFFF;
uint16_t noOp = 0x0000;
uint32_t read = 0xFFFF;
while(!(SPI0->SPI_SR & SPI_SR_TXEMPTY)); // wait 4 ready
SPI0->SPI_TDR = SPI_TDR_TD(data);// | SPI_TDR_PCS(1);
while(!(SPI0->SPI_SR & SPI_SR_TXEMPTY)); // wait 4 ready
SPI0->SPI_TDR = SPI_TDR_TD(noOp);// | SPI_TDR_PCS(1);
read = SPI0->SPI_RDR & SPI_RDR_RD_Msk;
uint16_t pard = read >> 15;
uint16_t position = read;
position /= 4;
tp_putchar(&tp2, position);
// begin message handling
/* Command Table
0 <0> | <1> - run close or open gates
1 <val> - open loop terq
2 <val> - period to run open loop on
3 <0> | - read encoder, or cal,
*/
if(mready){
switch(d1){
case 0:
if(d2 == 1){
gates(1);
if(d2 == 1){
gates(1);
} else {
gates(0);
}
break;
gates(0);
}
break;
case 1:
scalar = min(d2, maxscalar);
break;
scalar = min(d2, maxscalar);
break;
case 2:
period = max(d2, 5);
break;
period = max(d2, 5);
break;
case 3:
tp_putchar(&tp2, 'Y');
break;
if (d2 == 0){
reverse = 0;
dir = 0;
} else {
reverse = 1;
dir = 1;
}
break;
default:
gates(0); // bail, shutdown gates
tp_putchar(&tp2, 'X');
break;
gates(0); // bail, shutdown gates
tp_putchar(&tp2, 'X');
break;
}
tp_putchar(&tp2, d1);
tp_putchar(&tp2, d2);
mready = 0;
} // end message handler
uint16_t encoder;
readencoder(&encoder);
if(reverse){
encoder = resolution - encoder;
}
uint16_t elecpos = (encoder + offset) % modulo; // 0 -> 2*PI in rads
// to update, must use duty update register, not just 'duty'
phaseu ++;
phasev ++;
phasew ++;
if(dir){
phaseu = elecpos/(modulo / 1024);
phasev = elecpos/(modulo / 1024) + 341;
phasew = elecpos/(modulo / 1024) + 682;
} else {
phaseu = elecpos/(modulo / 1024) + 682;
phasev = elecpos/(modulo / 1024) + 341;
phasew = elecpos/(modulo / 1024);
}
if (phaseu > 1023){
phaseu = 0;
phaseu -= 1023;
}
if(phasev > 1023){
phasev = 0;
phasev -= 1023;
}
if(phasew > 1023){
phasew = 0;
phasew -= 1023;
}
PWM1->PWM_CH_NUM[1].PWM_CDTYUPD = PWM_CDTY_CDTY(sinelut[phaseu] * scalar / 255 + 4);
PWM1->PWM_CH_NUM[2].PWM_CDTYUPD = PWM_CDTY_CDTY(sinelut[phasev] * scalar / 255 + 4);
PWM1->PWM_CH_NUM[3].PWM_CDTYUPD = PWM_CDTY_CDTY(sinelut[phasew] * scalar / 255 + 4);
delay_us(period * 2000);
/*
putCounter ++;
if(!(putCounter % 100)){
tp_putchar(&tp2, phasew / (1024 / 255));
}
*/
PWM1->PWM_CH_NUM[1].PWM_CDTYUPD = PWM_CDTY_CDTY(sinelut[phaseu] * scalar / 255);
PWM1->PWM_CH_NUM[2].PWM_CDTYUPD = PWM_CDTY_CDTY(sinelut[phasev] * scalar / 255);
PWM1->PWM_CH_NUM[3].PWM_CDTYUPD = PWM_CDTY_CDTY(sinelut[phasew] * scalar / 255);
//delay_cycles(1);
delay_us(200); // nets about 4khz loop, granting 2 pwm cycles per update. lots!
if(pin_get_state(&stlb)){ // ?
pin_clear(&stlb);
......
......@@ -34,7 +34,7 @@ var SerialPort = require('serialport');
var ByteLength = SerialPort.parsers.ByteLength;
var port = new SerialPort('COM15', {
var port = new SerialPort('COM4', {
baudRate: 115200,
dataBits: 8,
parity: 'none',
......
Markdown is supported
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