Project showcase
Automatic Gate with FSM and ISR

Automatic Gate with FSM and ISR © GPL3+

The purpose of this project was to the control an automatic gate with Arduino Nano using finite state machine method and interrupts.

  • 1,314 views
  • 0 comments
  • 2 respects

Components and supplies

About this project

About

This project was part of our practical work inside the Microprocessors class under the Electrical and Electronics Engineering degree at Universidade do Algarve.

We were introduced to Arduino philosophy based upon fisical computing and internet self-education, during class was introduced information about useful functions such as ISR (Interrupt Service Routines) through function attachInterrupt() as well as the utility of adopting FSM finite state machine (we already learned before) to the Arduino code on a way to reduce code and system resources, and keep the code much more simple to understand and use.

Utilization FSM (Finite State Machine)

In a simple way a finite state machine (in Arduino) is a computer program that, at any moment, can be in one of a predetermined number of states.

The state is a specific action such for example “Wait for a certain button to be activated”, or “Moving the servo motor to 69°” . An Finite State Machine can replace in programming most of the While, For or similar structures.

ISR

With ISR (Interrupt Service Routines) we don't need code inside loop() , turning the processor free to attend an interrupt quickly. The main limitation is the ATmega328 only attends one interruption at the same time, but on our case that's not a problem.

A real limitation for us is because millis() doesn't work inside ISR due to the fact it uses interruptions to count - the only "clock" function that works during an interruption is delayMicroseconds() but it is limited to about 16 miliseconds and in this case it is not enough. So we decided to call the functions of the FSM3 (state_2_next()) and FSM4 (state_2_out()) and digitalWrite (I) inside loop() .

Getting it done

In this problem, we intend to implement with the Arduino an FSM that commands an automatic gate, through two stimuli, a command and open&close micro-switch. The utilization of interrupts in this problem is with a objective the machine does not the resources consume.

The first step of our project was making the architecture design (attached) with the system inputs and outputs.

The second step was designing the state diagram (we used Moore diagram method) with the several states, inputs related to state transition and outputs linked to each state.

The third step was designing two flowcharts for each FSM, one for the next-state and another for the outputs.

Finally, we have written the C code and have made the wiring diagram.

Code

Automatic Gate using FSM and ISRArduino
This code was developed to control an automatic gate under an university project, using finit state machines and interruption service routines.
/*
Universidade do Algarve - Instituto Superior de Engenharia * Microprocessors * Professor: António João Freitas Gomes da Silva
André Neves nº 49960
Nuno Martins nº 11854
Code to control an automatic gate using FSM (Finite State Machines) and ISR (Interrupt Service Routines)
 */

volatile int tpin = 2; // Sinal de comando (abre/fecha) do portão, pin 12   | Command Signal (Open/Close) the gate, pin 12
volatile int dpin = 3; // Sinal de fim de curso aberto/fechado, pin 13      | Open&close micro-switch signal open/close, pin 13  
volatile int t; // Variável de impulso de comando                           | Command Impulse Variable
volatile int ti; // Variável de armazenamento do sinal de comando           | Variable to memorize the command signal
volatile int d; // Variável para armazenar o sinal de fim de curso          | Variable to memorize Open&close micro-switch signal
volatile int A = 6; // led_A: Abertura de portão, pin 6                     | Open gate,pin 6
volatile int F = 7; // led_F: Fecho do portão, pin 7                        | Close gate, pin 7
volatile int I = 5; // led_I: Luz intermitente, pin 5                       | Blinking light, pin 5
volatile int Abre; // Variável para armazenar o sinal de abertura           | Variable to memorize the open signal
volatile int Fecha; // Variável para armazenar o sinal de fecho             | Variable to memorize the close signal
volatile int Interm; // Variável para armazenar o sinal da luz intermitente | Variable to memorize the Blinking light signal
volatile int state_1 = 0; // Variável dos estados de abertura/fecho/paragem | Variable of States the open/close/stop
volatile int state_2 = 0; // Variável dos estados da luz intermitente       | Variable of Blinking light state
volatile int state_s = 0; // Variável dos estados do sinal de comando       | Variable of Command signal state
volatile unsigned long currentmillis; // tempo actual                       | Current Time
volatile unsigned long previousmillis;// tempo anterior                     | Previous Time

void setup() {
  // put your setup code here, to run once:

pinMode (A, OUTPUT);      // Definição do pin associado a A como saída       | Configures the pin associated to A as Output
pinMode (F, OUTPUT);      // Definição do pin associado a F como saída       | Configures the pin associated to A as Output
pinMode (I, OUTPUT);      // Definição do pin associado a I como saída       | Configures the pin associated to A as Output
pinMode (tpin, INPUT);    // Definição do pin associado a tpin como entrada  | Configures the pin associated to tpin as Input
pinMode (dpin, INPUT);    // Definição do pin associado a dpin como entrada  | Configures the pin associated to dpin as Input
 // Attach an interrupt to the ISR vector
attachInterrupt(0, pin_ISR, CHANGE);        //Interrupção por acionamento do botão de comando   |Interruption due to command button
attachInterrupt(1, pin_ISR, CHANGE);        //Interrupção por acionamento do fim de curso       |Interruptdue to close/open micro-switch
}

void loop() {
  // put your main code here, to run repeatedly:
  state_2_next();
  state_2_out ();
  digitalWrite(I, Interm);             
}

void pin_ISR() {              //Rotina de Interrupção                      | Interrupt Service Routine.
  t = digitalRead(tpin);      // Leitura da Variavel T                     | Reading of Variable T.
  d = digitalRead(dpin);      // Leitura da Variavel D                     | Reading of Variable D.
  state_1_next();             // Chamada da função FSM1 - estado seguinte  | Calls function FSM1 - next state
  state_1_out();              // Chamada da função FSM2 - saída do estado  | Calls function FSM2 - output state
  digitalWrite (A, Abre);     // Leitura da Variavel A.                    | Reading of Variable A
  digitalWrite (F, Fecha);    // Leitura da Variavel F.                    | Reading of Variable F
 
}
 // Na função abaixo está descrito o funcionamento da FSM1 referente aos estados do motor do portão, em função das entradas T e D.
//The function state_1_next includes the code of FSM1 - gate motor state, in order of inputs T and D.
void state_1_next(){
   switch (state_1){
    case 0:
     if (t==HIGH){
     state_1=1;
     }
     break;
    case 1:
     if (d==HIGH){
     state_1=2;
     }
     else if (t==HIGH){
     state_1=4;
     }
     break;
    case 2:
     if (t==HIGH){
     state_1=3;
     }
     break;
    case 3:
     if (d==HIGH){
     state_1=0;
     }
     else if (t==HIGH){
     state_1=5;
     }
     break;
    case 4:
     if (t==HIGH){
     state_1=3;
     }
     break;
    case 5:
     if (t==HIGH){
     state_1=1;
     }
     break;}
 }
  //A função state_1_out diz respeito aos Outputs dos estados da função state_1_next.
 // The function state_1_out define the state_1 output.
void state_1_out(){
   switch (state_1){
    case 0:
     Abre=0;
     Fecha=0;
     break;
    case 1:
     Abre=1;
     Fecha=0;
     break;
    case 2:
     Abre=0;
     Fecha=0;
     break;
    case 3:
     Abre=0;
     Fecha=1;
     break;
    case 4:
     Abre=0;
     Fecha=0;
     break;
    case 5:
     Abre=0;
     Fecha=0;
     break;}
}
//Na funçao state_2_next está o codigo relativo à FSM3 - estado da luz intermintente durante a abertura/fecho do portão
//The function state_2_next includes the code of FSM3 - related to the blinking light state during opening/closing gate
void state_2_next(){
  currentmillis = millis();
  switch (state_2){
    case 0:
     if ((state_1==1 || state_1==3) && (currentmillis-previousmillis)>=50){
      state_2=1;
      previousmillis = currentmillis;}
     break;
    case 1:
     if (state_1==0 || state_1==2 || state_1==4 || state_1==5){
     state_2=0;}
     else if ((state_1==1 || state_1==3) && (currentmillis-previousmillis)>=50){
      state_2=0;
      previousmillis = currentmillis;}
     break;}
}
  //A função state_2_out diz respeito aos Outputs dos estados da função state_2_next.
 // The function state_2_out define the state_2 output.
void state_2_out(){
  switch (state_2){
    case 0:
    Interm=0;
    break;
    case 1:
    Interm=1;
    break;}
}

Schematics

Automatic Gate Interrupt - Project
Architecture and FSM (finite state machine) flowcharts
Electric diagram of automatic gate
Electric diagram of automatic gate control with arduino using FSM and ISR
circuito_arduino_portaobom_Zwf32puyxt.fzz
Breadboard scheme
Electric diagram

Comments

Similar projects you might like

Advance Automatic Railway Crossing System

Project showcase by Pawan singh and Akansh Saxena

  • 1,841 views
  • 1 comment
  • 13 respects

Automatic Sliding Door for the Garage

Project tutorial by DVDMDN

  • 13,375 views
  • 32 comments
  • 64 respects

Arduino Burglar

Project showcase by paolo_cravero

  • 2,380 views
  • 2 comments
  • 6 respects

Automatic Baby Rocker!

Project showcase by SindreKragsrud

  • 996 views
  • 0 comments
  • 7 respects

RFID Based Automatic Door System

Project showcase by Robodia Technology

  • 35,759 views
  • 20 comments
  • 97 respects

Password-Protected, Arduino-Controlled Servo Gate

Project tutorial by Aayush Sharma

  • 714 views
  • 0 comments
  • 6 respects
Add projectSign up / Login