Control LEDs using GSM with Microcontrollers

If you learn how to turn on/off targeted LEDs through your mobile then you can do anything through GSM modules. Therefore at beginner level, I will show you how to control LEDs through GSM module. I used ATmega8 microcontroller in this project which is from the family of Atmel AVR microcontrollers. If you want to study the basics of GSM then click the link below:

Basics of GSM module

Where to start?

As I told before that you must have enough knowledge of Serial communication, Strings handling and AT commands. So for serial communication study my other article on Serial Communication through Atmel AVR microcontrollers. In this article I will start from string handling and after that I’ll explain AT commands.

String Handling in Microcontrollers

While working on GSM you have to handle lot of strings to control your sensors or appliances. I will include string.h header file to handle strings.  I will explain strings handling through a small example.

LED Control through Serial Communication:

Proteus Example for Serial Communicaton
Figure 1: Proteus connection Diagram for example

If you understand this simple example 70 percent work for GSM project will be completed. Download complete code for the example from thelink. Some important functions of code will be explained here.

Functions for String Transmission

 

void uart_transmit (char data){
       while (!( UCSRA & (1<<UDRE)));
       // wait to free the register
       UDR = data;
       // For loading data in the UART Register
}
void string_transmit(const char *str){
unsigned char s=0;
       // Loop will wait for all characters
       // and transmit them one by one
       while (str[s]!=0){
              uart_transmit (str[s]);
              s++;
       }
}

The above two functions are to transmit characters. First function is copied as it is from the datasheet of Atmel AVR microcontrollers and the second function is a general function to send all characters of strings one by one. As every string have null character in the end. So this function will wait for null character and after that terminates the loop.

Functions for String Receiving

unsigned char uart_receive (){
              while((UCSRA&(1<<RXC)) == 0);
              // Return received data from the register
              return UDR;
       }



       char * string_receive1(){
              unsigned char  x,i = 0;
              // this loop will receive the characters
//until "enter(\r)" character comes
              while((x = uart_receive())!='\r'){
                     //and store the received characters
// into the array string[] one-by-one
                     str1[i++] = x;
              }
              //insert NULL to complete the string
              str1[i] = '\0';
              //return the received string
              return str1;
       }

The above two functions are for receiving characters from other serial device like GSM module. First function is copied as it is from the datasheet of Atmega8 Microcontroller and the second function is a general function to receive all characters of strings one by one and save them into str1[] string. This function should use carefully because once it is initiated it will remain inside until some termination character will come. In this example I used enter as a termination character. ‘\r’ is equivalent to enter button.

Note: The above two strings functions I explained above are general functions and they can use any other place where strings are present.

Main loop function:

void loop(){
       data1 = string_receive1();
       if(strncmp(data1,"ledon",5) == 0){
                     PORTB &= ~(1 << 0);
                     string_transmit("LED is ON\r");
       }
       if(strncmp(data1,"ledoff",6) == 0){
                     PORTB |= (1 << 0);
                     string_transmit("LED is OFF\r");
       }
}

data1 is pointer to character type because we don’t know how many characters are we going to receive. After receiving whole string, string compare function will compare the receiving commands and then act accordingly. As in the above function I made a logic that whenever a string “ledon” will came it will turn on the LED present at PORTB.0 and string “ledoff” will turn off the LED.

Where is AT Commands and GSM Module?

In case if you are still confused between serial communication and working on GSM module then I want to tell you that GSM module use serial communication for interfacing with microcontroller. This is the reason that I explained string based serial communication of Atmel AVR Microcontrollers first. AT(Attention) commands are commands to control GSM module. I will consider some important AT commands here.

Most Basic and Important AT Commands

  • AT (will return OK if GSM is working fine)
  • ATE0 or ATE1(Turn Off or On echo i.e. it will show/hide outputs on serial terminal)
  • AT+CMGF=1(To go to regular text messaging mode)
  • AT+CMGS=“+xxxxxxxxxxxx” (press enter  then after writing the message press ctrl + z)
  • AT+CMGR=x (Read the message present at the x state)
  • AT+CMGD=1,4 (Clear the memory of SIM CARD)
  • AT+CNMI=1,1,0,1 (to turn on the notifications whenever a message will come )
  • ATD+xxxxxxxxxxx(To dial the number)
  • ATH(To Hung up the call)

GSM based LED Project on ATmega8:

Controlling LEDs through Mobile
Figure 2: Implemented on Breadboard

I used Atmega8 microcontroller to implement this project which is from Atmel AVR Microcontrollers which you can see in the figure above. The hardware part of this project is really simple one. Just connect two wires of Tx, Rx of Atmega8 Microcontroller to Rx, Tx of GSM module respectively and add two LEDs according to circuit diagram. In the above figure you are watching two messages of “LED is on” in the mobile screen. I added this functionality that whenever some action occur GSM module should reply according to that action. For example if green LED in on then module should reply that Green LED is on. But I removed this functionally in this project for simplicity.

Circuit Diagram for LED interfaced with GSM Module
Figure 3: Complete Circuit Diagram

Coding Part

You can get the whole code from the link present below. I will explain some important parts only.

GSM Initialization Function:

void gsm_init()
{
       string_transmit("\r\nAT\r\n");
       _delay_ms(500);
       string_transmit("ATE1\r\n");
       _delay_ms(500);
       string_transmit("AT+CMGF=1\r\n");
       _delay_ms(500);
       string_transmit("AT+CMGD=1,4\r\n");
       _delay_ms(500);
       string_transmit("AT+CNMI=1,1,0,1\r\n");
}

This function is really necessary for initialization without this function GSM module will not start receiving messages.

String Handler Function:

char *compare(){
                     int i = 0;
                     // s = start of new string
                     // e = end of new string
while(s<e ){
                           //and store the received characters                          //into the array string[] one-by-one
                           y[i++] = data1[s++];
                     }
                     //insert NULL to terminate the string
                     y[i] = '\0';
                     //return the received string
              return(y);
              }

This function is very necessary to understand while working on GSM modules. When GSM module receive messages, it does not contain only message but also other details like phone number, time, date etc. To get only text message from that details I used this “compare()” function.

Main loop commands:

_delay_ms(300);
       data1=string_receive1();
       index=uart_receive();
       _delay_ms(300);
       string_transmit("AT+CMGR=");
       uart_transmit(index);
       string_transmit("\r\n");
       data1=string_receive2();
       _delay_ms(300);
       s=78;e=86;
       data2=compare();
       _delay_ms(300);
       if(strncmp(data2,"Yellow",6)==0)
       {if ((PORTC & (1 << 4) ) == 0){
              PORTC |= 1 << 4;    
       }
       else{
              PORTC &= ~(1 << 4);
        }}

First of all data1 will receive the interrupt command of received message from GSM module. After that Index character will save the index of received message which shows the number at which message is saved. To read the received message we have to transmit “AT+CMGR=index” as I did in the above code. After that we will receive the message with other details and we have to capture only message from that details. So I used compare() function to get message which is started from 78th element.

I think that much detail is enough for this project. If you still need help feel free to comment below and don’t forget to like our facebook page. 🙂

 To download complete code click the button below:
Complete Code

Ismail

Electrical engineering is my profession, my hobby and my passion. I completed bachelors of electrical engineering in 2015. Currently I am working with a utility company which provides electricity to its consumers. Power Electronics, Embedded Systems and Energy Metering are my fields of specialization. In free time I listen music and watch movies.

What do you think?