The Android Telephony API for GSM

As a software developer for mobile platforms, you may be interested in incorporating telephony features in your app. For instance, your interactive app might need to notify the user when it starts accessing the Internet while roaming; or, your high-bandwidth video chat application might need to alter its stream quality, based on the type of connection and its latency. These are situations where mobile apps need an interface to the basic phone features and its state, which is when the Telephony APIs come in. In this article, we explore Android API support for GSM networks, and the important steps you need to take when embedding telephony support.

All GSM devices use a SIM, a secure smart card, which holds information about the network and the user setting. Android currently provides a read-only interface via the telephony APIs, to access the physical device and SIM information. So, what does the information constitute, and how is it useful? Let’s first get familiar with the context and the basics, before delving into the telephony API.

The SIM Serial Number (SSN) on the SIM card uniquely identifies the SIM card. It’s also referred to as the Integrated Circuit Card ID (ICCID). This holds information related to the SIM’s country, state and operator.

The International Mobile Subscriber Identity (IMSI) identifies the subscriber (Subscriber ID), and network details such as the provider network’s operator country, operator code/name and network state. In addition, Location Area Identity (LAI) provides the region within a provider network, which appears as the operator’s location.

The International Mobile Equipment Identity (IMEI) number uniquely identifies a GSM device internationally. This number is often printed on the instrument panel, and can usually be retrieved by typing *#06# on the phone’s keypad. A stolen or lost phone is tracked (or blocked) by its IMEI.

In addition to the above metrics, during the setup of a development environment with a real device, programmers need to determine a few physical device metrics, such as: (a) USB vendor ID of the device, for the creation of permissions for the device in app debug mode, and (b) device serial number (that appears as a S/N) printed on the device — this is seen as the device, when testing and developing in an IDE such as Eclipse (see Figure 1). Though many popular USB vendor IDs are publicly listed, yours may not be. Both these bits of information can be retrieved using a procedure listed in the box item below.

The above two lines indicate two mobile phones connected to my system via USB, in device debug mode. The four-digit vendor ID of the HTC phone is 0bb4 and that of the unlisted Micromax (appears as ONDA) is 19d2. Along with the vendor ID are the bus number details (001) of the phone, and the device number (005/006). You may note that the device number is not constant, and will change each time you plug/unplug the phone, or enable/disable debugging on your device.

Type the following to determine the serial number and the OS details of the mobile (in this case, the HTC), using udev, which is used by the OS to dynamically map, present, and control USB devices:

The Android Telephony package

Programmers will need ways to not just retrieve telephony data, but also to dial a phone number, intercept outgoing phone calls, or send/receive SMS messages. This is achieved with a combination of classes provided in the android.telephony package, along with inbuilt Intents and phone services.

The most important of these is the TelephonyManager class, which can be used to retrieve metadata about the SIM card, the physical device and the network provider. Programmers will need to use the Android Context, through the getSystemService() method, with a constant as shown below, to obtain an instance of the TelephonyManager class.

Additionally, it is often important to know the change in the call or service state of the phone, in an app. For example, you may want to mute your application when a call arrives. This is done by attaching a listener, called PhoneStateListener to the TelephonyManager.

Finally, it is important to note that information retrieval via TelephonyManager is permission-protected. For the application to access this information, the android.permission.READ_PHONE_STATE permission has to be set in the app’s manifest.xml. Figure 2 shows some metrics retrieved using TelephonyManager.Figure2: Telephony metrics retrievedusing TelephonyManager
The Android emulator includes a mock GSM modem that you can manipulate using the gsm command from the console. An alternative would be to simply use the Swiss knife, which is the Dalvik debug monitoring service (DDMS), which lets you simulate special device status and activities.

With respect to Telephony actions, you can simulate phone calls and send/receive SMS messages to/from the emulator. Other than this, the state of the phone, the network speed and latency (GPRS, EDGE, UMTS, etc.,) can also be set. DDMS can be launched from the tools/ directory in your Android SDK distribution. As we discussed earlier, it could be useful for situations where the existing functionality of App needs to be enhanced with SMS sending feature. Or for building specialized SMS App, such as being able to set a time when the message would leave your phone.

With this background, let’s look at the steps to incorporate SMS feature. As we discussed earlier, it could be useful for situations where the existing functionality of App needs to be enhanced with SMS sending feature. Or for building specialized SMS App, such as being able to set a time when the message would leave your phone.
The steps to sending a simple text message:

The app incorporates the android.telephony package.

Permissions must be set in the manifest file to send and receive SMS messages, as shown below:

Send SMS — android.permission.SEND_SMS

Receive SMS — android.permission.RECEIVE_SMS

The app uses an instance of SmsManager, retrieved using the static method getDefault():

final SmsManager sms = SmsManager.getDefault() ;

A PendingIntent is created in order for the application to track message delivery status. (A PendingIntent provides a means for an application to work beyond its life, for a particular Intent. Even after the owning application dies, a PendingIntent created by it can be run later.) This pending intent is invoked when the sending handset receives an acknowledgement from the network that the destination handset has received the message.

One simple way to test complete SMS functionality, especially the acknowledgement, with a pending intent, is to create two Emulator instances. Let’s say that the instances are 5554 and 5556 (see Figure 3). This number is also the port number, and the emulator can be called at this number. This is a nice way to test without incurring network provider call charges during development and testing periods.Figure3: SMS emulation
You can read more on SMS emulation here.

Summary

With this background, interested developers may take a deep plunge into programming with the help of Android Telephony API website. Another related area to understand would be the standards that are part of 3GPP Evolution model.

POPULAR CATEGORY

Open Source For You is Asia's leading IT publication focused on open source technologies. Launched in February 2003 (as Linux For You), the magazine aims to help techies avail the benefits of open source software and solutions. Techies that connect with the magazine include software developers, IT managers, CIOs, hackers, etc. A free DVD, which contains the latest open source software and Linux distributions/OS, accompanies each issue of Open Source For You. The magazine is also associated with different events and online webinars on open source and related technologies.