//
//
// hello.stepper.44.half.c
//
// half stepping hello-world
//
// Neil Gershenfeld
// 11/14/10
//
// (c) Massachusetts Institute of Technology 2010
// This work may be reproduced, modified, distributed,
// performed, and displayed for any purpose. Copyright is
// retained and must be preserved. The work is provided
// as is; no warranty is provided, and users accept all
// liability.
//

#include <avr/io.h>
#include <util/delay.h>

#define output(directions,pin) (directions |= pin) // set port direction for output
#define set(port,pin) (port |= pin) // set port pin
#define clear(port,pin) (port &= (~pin)) // clear port pin
#define pin_test(pins,pin) (pins & pin) // test for port pin
#define bit_test(byte,bit) (byte & (1 << bit)) // test for bit set

//Motor 0
#define MOSFET_port_0 PORTC // MOSFET port
#define MOSFET_direction_0 DDRC // MOSFET direction
#define brown_0 (1 << PC2) // MOSFET output pins
#define black_0 (1 << PC3) // "
#define yellow_0 (1 << PC1) // "
#define orange_0 (1 << PC0)


//Motor 1
#define MOSFET_port_1 PORTD // MOSFET port
#define MOSFET_direction_1 DDRD // MOSFET direction
#define brown_1 (1 << PD4) // MOSFET output pins
#define black_1 (1 << PD5) // "
#define yellow_1 (1 << PD3) // "
#define orange_1 (1 << PD2) // "


//#define on_delay() _delay_us(50) // PWM on time
//#define off_delay() _delay_us(10) // PWM off time
//#define PWM_count 100 // number of PWM cycles

#define on_delay() _delay_us(90) // PWM on time
#define off_delay() _delay_us(10) // PWM off time
#define PWM_count 100 // number of PWM cycles

static uint8_t count;
static uint8_t activeMotor = 1;

//
// yellow PWM pulse
//
void pulse_yellow() {
   for (count = 0; count < PWM_count; ++count) {
       if(activeMotor == 0) {
           set(MOSFET_port_0, yellow_0);
           on_delay();
           clear(MOSFET_port_0, yellow_0);
           off_delay();
       } else {
           set(MOSFET_port_1, yellow_1);
           on_delay();
           clear(MOSFET_port_1, yellow_1);
           off_delay();
       }
   }
}
//
// black PWM pulse
//
void pulse_black() {
    for (count = 0; count < PWM_count; ++count) {
        if(activeMotor == 0) {
            set(MOSFET_port_0, black_0);
            on_delay();
            clear(MOSFET_port_0, black_0);
            off_delay();
        } else {
            set(MOSFET_port_1, black_1);
            on_delay();
            clear(MOSFET_port_1, black_1);
            off_delay();
        }
   }
}
//
// orange PWM pulse
//
void pulse_orange() {
    for (count = 0; count < PWM_count; ++count) {
      if(activeMotor == 0) {
        set(MOSFET_port_0, orange_0);
        on_delay();
        clear(MOSFET_port_0, orange_0);
        off_delay();
      } else {
        set(MOSFET_port_1, orange_1);
        on_delay();
        clear(MOSFET_port_1, orange_1);
        off_delay();
      }
    }
}

//
// brown PWM pulse
//
void pulse_brown() {
  for (count = 0; count < PWM_count; ++count) {
    if(activeMotor == 0) {
      set(MOSFET_port_0, brown_0);
      on_delay();
      clear(MOSFET_port_0, brown_0);
      off_delay();
    } else {
      set(MOSFET_port_1, brown_1);
      on_delay();
      clear(MOSFET_port_1, brown_1);
      off_delay();
    }
  }
}
//
// yellow, brown PWM pulse
//
void pulse_yellow_brown() {
  for (count = 0; count < PWM_count; ++count) {
    if(activeMotor == 0) {
      set(MOSFET_port_0, yellow_0);
      set(MOSFET_port_0), brown_0);
      on_delay();
      clear(MOSFET_port_0, yellow_0);
      clear(MOSFET_port_0, brown_0);
      off_delay();
    } else {
      set(MOSFET_port_1, yellow_1);
      set(MOSFET_port_1, brown_1);
      on_delay();
      clear(MOSFET_port_1, yellow_1);
      clear(MOSFET_port_1, brown_1);
      off_delay();
    }
  }
}
//
// yellow, black PWM pulse
//
void pulse_yellow_black() {
  for (count = 0; count < PWM_count; ++count) {
    if(activeMotor == 0) {
      set(MOSFET_port_0, yellow_0);
      set(MOSFET_port_0, black_0);
      on_delay();
      clear(MOSFET_port_0, yellow_0);
      clear(MOSFET_port_0, black_0);
      off_delay();
    } else {
      set(MOSFET_port_1, yellow_1);
      set(MOSFET_port_1, black_1);
      on_delay();
      clear(MOSFET_port_1, yellow_1);
      clear(MOSFET_port_1, black_1);
      off_delay();
    }
  }
}
//
// orange, brown PWM pulse
//
void pulse_orange_brown() {
  for (count = 0; count < PWM_count; ++count) {
    if(activeMotor == 0) {
      set(MOSFET_port_0, orange_0);
      set(MOSFET_port_0, brown_0);
      on_delay();
      clear(MOSFET_port_0, orange_0);
      clear(MOSFET_port_0, brown_0);
      off_delay();
    } else {
      set(MOSFET_port_1, orange_1);
      set(MOSFET_port_1, brown_1);
      on_delay();
      clear(MOSFET_port_1, orange_1);
      clear(MOSFET_port_1, brown_1);
      off_delay();
    }
  }
}
//
// orange, black PWM pulse
//
void pulse_orange_black() {
  for (count = 0; count < PWM_count; ++count) {
    if(activeMotor == 0) {
      set(MOSFET_port_0, orange_0);
      set(MOSFET_port_0, black_0);
      on_delay();
      clear(MOSFET_port_0, orange_0);
      clear(MOSFET_port_0, black_0);
      off_delay();
    } else {
      set(MOSFET_port_1, orange_1);
      set(MOSFET_port_1, black_1);
      on_delay();
      clear(MOSFET_port_1, orange_1);
      clear(MOSFET_port_1, black_1);
      off_delay();
    }
  }
}
//
// clockwise step
//
void step_cw() {
   pulse_yellow_brown();
   pulse_yellow();
   pulse_yellow_black();
   pulse_black();
   pulse_orange_black();
   pulse_orange();
   pulse_orange_brown();
   pulse_brown();
   }
//
// counter-clockwise step
//
void step_ccw() {
   pulse_brown();
   pulse_orange_brown();
   pulse_orange();
   pulse_orange_black();
   pulse_black();
   pulse_yellow_black();
   pulse_yellow();
   pulse_yellow_brown();
   }

int main(void) {
   //
   // main
   //
   static uint8_t i,j;
   //
   // set clock divider to /1
   //
   CLKPR = (1 << CLKPCE);
   CLKPR = (0 << CLKPS3) | (0 << CLKPS2) | (0 << CLKPS1) | (0 << CLKPS0);
   //
   // initialize MOSFET pins
   //
   clear(MOSFET_port_0, brown_0);
   output(MOSFET_direction_0, brown_0);
   clear(MOSFET_port_0, black_0);
   output(MOSFET_direction_0, black_0);
   clear(MOSFET_port_0, yellow_0);
   output(MOSFET_direction_0, yellow_0);
   clear(MOSFET_port_0, orange_0);
   output(MOSFET_direction_0, orange_0);

   clear(MOSFET_port_1, brown_1);
   output(MOSFET_direction_1, brown_1);
   clear(MOSFET_port_1, black_1);
   output(MOSFET_direction_1, black_1);
   clear(MOSFET_port_1, yellow_1);
   output(MOSFET_direction_1, yellow_1);
   clear(MOSFET_port_1, orange_1);
   output(MOSFET_direction_1, orange_1);
   //
   // main loop
   //
   while (1) {
     activeMotor = 0;
     step_ccw();
     step_ccw();
     activeMotor = 1;
     step_ccw();
     step_ccw();
     _delay_ms(1500);

     activeMotor = 0;
     step_cw();
     step_cw();
     activeMotor = 1;
     step_cw();
     step_cw();
     _delay_ms(1500);
   }
}
