SIM900A GSM module Interfacing with AVR ATmega16/ATmega32
SIM900A GSM module is a communication device which is used to make or receive calls, send or receive SMS, connecting to the internet over GPRS.

Introduction
Global System for Mobile communication (GSM) is a digital cellular system used for mobile devices. It is an international standard for mobile which is widely used for long-distance communication.
There are various GSM modules available in the market like SIM900, SIM700, SIM800, SIM808, SIM5320, etc.
SIM900A module allows users to send/receive data over GPRS, send/receive SMS, and make/receive voice calls.
It communicates serially with the devices like a microcontroller, PC using AT commands.
To interface the SIM900A module with the cellular network, it requires a SIM card provided by a network operator.
For more information about Sim900A and how to use it, refer to the topic SIM900A GSM/GPRS Module in the sensors and modules section.
The GSM/GPRS module uses USART communication to communicate with a microcontroller or PC terminal.
For information about USART in AVR ATmega16/ ATmega32 and how to use it, refer the topic USART in AVR ATmega16/ATmega32 in the ATmega inside section.

SIM900A GSM Module Interfacing With Atmega16/32


Send SMS using SIM900 GSM Module and ATmega16/32
Let’s design a little application in which the user will receive SMS “call me” and immediately user will call that message sender.
SIM900 GSM Module Code for Atmega16
/*
SIM900 GSM Interfacing with ATmega16/32
http://www.electronicwings.com
*/
#define F_CPU 8000000UL /* define Clock Frequency */
#include <avr/io.h>
#include <avr/interrupt.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <stdbool.h>
#include "LCD_16x2_H_file.h" /* include 16x2 LCD Header file */
#include "USART_Interrupt.h" /* include USART Header file */
#define SREG _SFR_IO8(0x3F)
void GSM_Begin();
void GSM_Calling(char *);
void GSM_HangCall();
void GSM_Response();
void GSM_Response_Display();
void GSM_Msg_Read(int);
bool GSM_Wait_for_Msg();
void GSM_Msg_Display();
void GSM_Msg_Delete(unsigned int);
void GSM_Send_Msg(char* , char*);
void GSM_Delete_All_Msg();
char buff[160]; /* buffer to store responses and messages */
char status_flag = 0; /* for checking any new message */
volatile int buffer_pointer;
char Mobile_no[14]; /* store mobile no. of received message */
char message_received[60]; /* save received message */
int position = 0; /* save location of current message */
int main(void)
{
buffer_pointer = 0;
int is_msg_arrived;
memset(message_received, 0, 60);
LCD_Init();
USART_Init(9600); /* initialize USART */
sei();
LCD_String_xy(1,0,"GSM Initializing");
_delay_ms(3000);
LCD_Clear();
LCD_String_xy(1,0,"AT");
GSM_Begin(); /* Start GSM with AT*/
LCD_Clear();
while (1){
/*check if any new message received */
if(status_flag==1){
is_msg_arrived = GSM_Wait_for_Msg(); /*check for message arrival*/
if(is_msg_arrived== true)
{
LCD_Clear();
LCD_String_xy(1,0,"new message"); /* new message arrived */
_delay_ms(1000);
LCD_Clear();
GSM_Msg_Read(position); /* read arrived message */
_delay_ms(3000);
/*check if received message is "call me" */
if(strstr( message_received,"call me")){
GSM_Calling(Mobile_no); /* call sender of message */
LCD_Clear();
LCD_String_xy(1,0,"Calling...");
_delay_ms(15000);
GSM_HangCall(); /* hang call */
LCD_String_xy(1,0,"Hang Call");
_delay_ms(1000);
}
LCD_Clear();
GSM_Msg_Delete(position); /* to save SIM memory delete current message */
LCD_String_xy(1,0,"Clear msg");
GSM_Response();
_delay_ms(1000);
}
is_msg_arrived=0;
status_flag=0;
LCD_Clear();
}
LCD_String_xy(1,0,"waiting for msg");
memset(Mobile_no, 0, 14);
memset(message_received, 0, 60);
}
}
void GSM_Begin()
{
while(1)
{
LCD_Command(0xc0);
USART_SendString("ATE0\r"); /* send ATE0 to check module is ready or not */
_delay_ms(500);
if(strstr(buff,"OK"))
{
GSM_Response();
memset(buff,0,160);
break;
}
else
{
LCD_String("Error");
}
}
_delay_ms(1000);
LCD_Clear();
LCD_String_xy(1,0,"Text Mode");
LCD_Command(0xc0);
USART_SendString("AT+CMGF=1\r"); /* select message format as text */
GSM_Response();
_delay_ms(1000);
}
void GSM_Msg_Delete(unsigned int position)
{
buffer_pointer=0;
char delete_cmd[20];
/* delete message at specified position */
sprintf(delete_cmd,"AT+CMGD=%d\r",position);
USART_SendString(delete_cmd);
}
void GSM_Delete_All_Msg()
{
USART_SendString("AT+CMGDA=\"DEL ALL\"\r"); /* delete all messages of SIM */
}
bool GSM_Wait_for_Msg()
{
char msg_location[4];
int i;
_delay_ms(500);
buffer_pointer=0;
while(1)
{
/*eliminate "\r \n" which is start of string */
if(buff[buffer_pointer]=='\r' || buff[buffer_pointer]== '\n'){
buffer_pointer++;
}
else
break;
}
/* "CMTI:" to check if any new message received */
if(strstr(buff,"CMTI:")){
while(buff[buffer_pointer]!= ',')
{
buffer_pointer++;
}
buffer_pointer++;
i=0;
while(buff[buffer_pointer]!= '\r')
{
msg_location[i]=buff[buffer_pointer]; /* copy location of received message where it is stored */
buffer_pointer++;
i++;
}
/* convert string of position to integer value */
position = atoi(msg_location);
memset(buff,0,strlen(buff));
buffer_pointer=0;
return true;
}
else
{
return false;
}
}
/* ISR routine to save responses/new message */
ISR(USART_RXC_vect)
{
buff[buffer_pointer] = UDR; /* copy UDR (received value) to buffer */
buffer_pointer++;
status_flag = 1; /* flag for new message arrival */
}
void GSM_Send_Msg(char *num,char *sms)
{
char sms_buffer[35];
buffer_pointer=0;
sprintf(sms_buffer,"AT+CMGS=\"%s\"\r",num);
USART_SendString(sms_buffer); /*send command AT+CMGS="Mobile No."\r */
_delay_ms(200);
while(1)
{
if(buff[buffer_pointer]==0x3e) /* wait for '>' character*/
{
buffer_pointer = 0;
memset(buff,0,strlen(buff));
USART_SendString(sms); /* send msg to given no. */
USART_TxChar(0x1a); /* send Ctrl+Z */
break;
}
buffer_pointer++;
}
_delay_ms(300);
buffer_pointer = 0;
memset(buff,0,strlen(buff));
memset(sms_buffer,0,strlen(sms_buffer));
}
void GSM_Calling(char *Mob_no)
{
char call[20];
sprintf(call,"ATD%s;\r",Mob_no);
USART_SendString(call); /* send command ATD<Mobile_No>; for calling*/
}
void GSM_HangCall()
{
LCD_Clear();
USART_SendString("ATH\r"); /*send command ATH\r to hang call*/
}
void GSM_Response()
{
unsigned int timeout=0;
int CRLF_Found=0;
char CRLF_buff[2];
int Response_Length=0;
while(1)
{
if(timeout>=60000) /*if timeout occur then return */
return;
Response_Length = strlen(buff);
if(Response_Length)
{
_delay_ms(2);
timeout++;
if(Response_Length==strlen(buff))
{
for(int i=0;i<Response_Length;i++)
{
memmove(CRLF_buff,CRLF_buff+1,1);
CRLF_buff[1]=buff[i];
if(strncmp(CRLF_buff,"\r\n",2))
{
if(CRLF_Found++==2) /* search for \r\n in string */
{
GSM_Response_Display();
return;
}
}
}
CRLF_Found = 0;
}
}
_delay_ms(1);
timeout++;
}
status_flag=0;
}
void GSM_Response_Display()
{
buffer_pointer = 0;
int lcd_pointer = 0;
while(1)
{
/* search for \r\n in string */
if(buff[buffer_pointer]== '\r' || buff[buffer_pointer]== '\n')
{
buffer_pointer++;
}
else
break;
}
LCD_Command(0xc0);
while(buff[buffer_pointer]!='\r') /* display response till "\r" */
{
LCD_Char(buff[buffer_pointer]);
buffer_pointer++;
lcd_pointer++;
if(lcd_pointer==15) /* check for end of LCD line */
LCD_Command(0x80);
}
buffer_pointer = 0;
memset(buff,0,strlen(buff));
}
void GSM_Msg_Read(int position)
{
char read_cmd[10];
sprintf(read_cmd,"AT+CMGR=%d\r",position);
USART_SendString(read_cmd); /* read message at specified location/position */
GSM_Msg_Display(); /* display message */
}
void GSM_Msg_Display()
{
_delay_ms(500);
if(!(strstr(buff,"+CMGR"))) /*check for +CMGR response */
{
LCD_String_xy(1,0,"No message");
}
else
{
buffer_pointer = 0;
while(1)
{
/*wait till \r\n not over*/
if(buff[buffer_pointer]=='\r' || buff[buffer_pointer]== 'n') {
buffer_pointer++;
}
else
break;
}
/* search for 1st ',' to get mobile no.*/
while(buff[buffer_pointer]!=',')
{
buffer_pointer++;
}
buffer_pointer = buffer_pointer+2;
/* extract mobile no. of message sender */
for(int i=0;i<=12;i++)
{
Mobile_no[i] = buff[buffer_pointer];
buffer_pointer++;
}
do
{
buffer_pointer++;
}while(buff[buffer_pointer-1]!= '\n');
LCD_Command(0xC0);
int i=0;
/* display and save message */
while(buff[buffer_pointer]!= '\r' && i<31)
{
LCD_Char(buff[buffer_pointer]);
message_received[i]=buff[buffer_pointer];
buffer_pointer++;
i++;
if(i==16)
LCD_Command(0x80); /* display on 1st line */
}
buffer_pointer = 0;
memset(buff,0,strlen(buff));
}
status_flag = 0;
}
Video of Send SMS using SIM900 using ATmega16/32
Components Used
Powered by



SIM900A is dual band GSM/GPRS 900/1800MHz module board used to utilize GSM and GPRS services around the globe. It is used to make/receive voice calls, send/receive text messages, connect to and access the internet over GPRS.
170-M031-D

Downloads
Comments39
Join the discussion — share a question or tip.
- CL
will it work for atmega32? I am getting message undeclared USART....... and LCD.....
- AM
Hi, I checked the code on Atmega16, it is working... But when I dump the same code on Atmega1284P... It is not working... Kindly help
- AM
I am also using Osc freq 8MHz with 9600 baudrate
- SU
the code is working fine but when the whole system is power off and then on for the first time, lcd display GSM Initializing Error and if i again reset the microcontroller then it works fine, can anybody help me that if the gsm module is not ready for communication after power on then the lcd module again check that the gsm module is ready or not?in this code it does not working. I know gsm module takes little time to initializing but the lcd is not checking if the module is ready or not so how to solve it? please!!!
- TE
Hi sir I got a funny issue Im using atmega 16a and gsm module sim 900a when I connect gsm module to USB to TTL and send commands it works fine But when I connect gsm module to the atmega 16a MCU im unable to control it with code Please help me, sir Check the below pics for clarity https://1drv.ms/u/s!AgeRUh26in4nlUHE5ksF2P_NYIkr?e=BwIdXu
- CH
Good morning, pls i dont understand what this line of code is doing: if(CRLF_Found++==2)........in gsmresponse function
- CH
how can I send sms at a fixed time using GPS I am using this GPS module. http://bigbelectronics.in/product.php?product=sim800l-gprs-gsm-module-microsim-card-core-boardquad-band-ttl-serial-port-pcbantenna
- VO
hi, i have some proplem: #define SREG _SFR_IO8(0x3F) what does it do? and if i use F_CPU 16Mhz , do code have change? i use atmel studio 6 to compile tks
- LO
This macro is for SREG (Status Register) which is used while dealing with an interrupt routine. whereas 0x3F is an I/O address of SREG. sometimes it is necessary to check the status register before and after interrupt service routine is getting affected or not. If you change the F_CPU 16MHz, then your delay functions need to be changed for the proper 1ms delay.
- VO
Replying to @lokeshc
thanh you. if i dont use (#define SREG _SFR_IO8(0x3F)), will this code have logic error ?
- AN
What is the code for just sending sms
- OM
Code is not works !!!!!!!!!!!1
- SU
I am wanting if someone call on the number (missed call) then that number should reply with sms. please help
- RA
I'm using atmega16a with 8mhz external osci. In beginusart OK is not being returned. The module works with arduino uno. Is it due to baud rate what could be the possible errors?
- AH
ATMEGA32 , I have the same problem In GSM_begin OK is not being returned , i try it by simulation in proteus .
- BR
Bro it's not showing anything on LCD. i have checked my connections many time but it still not showing anything Ans should i have to make any change if i use indian mobile number?? and i am making notice board i don't need of calling..i only wanna that message should display on LCD only then for this purpous will i need to write mobile number in programming???
- ANAndre3000· edited
When we are calling the GSM _Calling () function in main, do we need to hard code the mobile number here like: GSM_Calling("90xxxxxxxx") Or do we need to only use the variable GSM_Calling(Mobile_no)? I figured that the mobile number is supposed to be extracted when a message is sent to the module. However, the call function does not work unless I actually hard code the mobile number. I just need a little further clarification.
- LO
In above program, controller waits for message to receive from user. When call me message received from user then above program extract the Mobile no. from received message and dial a call. So, if you want to use calling function without rely on message then you need to provide mobile no. Otherwise it will extract mobile no. from message.
- AB
Replying to @lokeshc
earlier when I was referring this program I had same doubt but after reading program I cleared my doubt. you can see GSM_Msg_Display() In this function mobile no. is extracted from received message.
- ANAndre3000· edited
Replying to @abhalerao0123
Thank you for your help. The number extraction was not working for me until in the for loop for(int i=0;i<=12;i++) { Mobile_no[i] = buff[buffer_pointer]; buffer_pointer++; } I changed i<=12 to 11. I think it may have something to do with Indian mobile numbers and US mobile numbers being of different lengths.
- AU
i think you need to check hardware connection again, since most of the time it solves the matters. and when you confirm with your hardware connection then it can be solved with program check/debug. go step by step, after hardware connection check for only lcd working and the remaining
- EB
Tried the simulation with proteus, it works just fine. Thanks to you boss!
- AH
how , can you send me the simulation
- LO
@prabu Appu: I found these files on this same page in Supporting Files--> source code -->ATmega16 Interface with GSM Project File


