iOS Telegram Forensics. Part I: Acquisition and Database Analysis
In digital forensic investigations and cyber incident response procedures, Telegram, like many messengers and social apps, can reveal a considerable amount of information about its users. In our first article in the Telegram forensics series, we have covered how the app works and what you can find in Telegram cloud data. Telegram files acquired from a device can open up a broader spectrum of details, yet their examination requires special knowledge.
In this article, we will explain how to approach iOS Telegram forensics, focusing on the following topics:
- How to acquire Telegram data from iOS devices
- iOS Telegram files of interest
- How to read the iOS Telegram database:
We will show how to work with iOS Telegram's SQLite database in Belkasoft X, a digital forensics tool that not only extracts data from applications but also provides low-level analysis instruments that help efficiently validate digital artifacts.
Acquiring iOS Telegram data
Telegram stores messaging data on its servers and does not save it using iOS backup mechanisms such as iTunes and iCloud. On the one hand, this approach is beneficial for digital forensics because it allows you to access user data even if the device is damaged or unavailable. On the other hand, it does not let you obtain Telegram data using the iTunes and iCloud backup acquisition methods that are less technically demanding. Cloud acquisition can work as an initial step in Telegram analysis, but the information acquired from the cloud may be incomplete.
Here are some additional Telegram artifacts you can find on mobile devices:
- Secret chats
- Private channels whose content can only be viewed online by participants
- Deleted messages and previous versions of edited messages (under favorable conditions)
All these sought-after Telegram artifacts can only be obtained from the full file system copy of the device. To acquire iOS devices, you can use a specialized digital forensics tool.
With Belkasoft X, you can extract the full file system of Apple mobile phones and tablets on different iOS versions with the help of agent-based acquisition or checkm8-based acquisition, and acquire jailbroken devices (with checkra1n, odyssey, unc0ver, or other jailbreaks installed).
Exploring iOS Telegram files
After you obtain the full file system copy of an iOS device, you can find Telegram files in the ..\private\var\mobile\Containers\Shared\AppGroup\{GUID} folder. The GUID is an alphanumeric number that the system assigned to the application when it was installed on the device.
Figure 1: Telegram folder structure in an iPhone file system
Data related to Telegram accounts used on the device is located in the telegram-data directory. One client instance (device) can house up to three accounts (as of Telegram version 11.0.2), each having a separate folder. In the example above, one account folder is available.
When looking for Telegram artifacts related to an account, you will typically be interested in the postbox folder that contains the following:
- a db folder with the application database and
- a media folder with exchanged files.
Note that the amount of data stored in the media folder may be limited as it depends on the application settings. Since Telegram stores user data in the cloud, users do not have to keep all exchanged files on their devices. They can configure the application to auto-remove cached files after a certain period and when the application cache reaches a certain size.
Figure 2: iOS Telegram media storage settings
Understanding iOS Telegram data
Telegram stores messaging data in the db_sqlite database and the associated transactional files. The database, as you may guess by its name, has the SQLite format, which is familiar to many forensic examiners. However, unlike many other applications, Telegram stores most of the records in the serialized binary format. What does it mean? When a user takes some action within the application, the database entry associated with it (for example, a message and all associated details) is recorded as a stream of bytes organized in a series. This process helps transmit information more easily, but when it comes to forensic examination, you must know how to deserialize the records to read their contents.
In this section, we will explore how to understand db_sqlite records in the columns of interest:
- t0 that includes account settings
- t2 that stores the information about the user's chats
- t7 that includes chat messages and their properties
Before you begin
When reading binary data, it is important to understand the concept of endianness that defines how computers store multi-byte values in the memory. Two storage formats are possible:
- Big-endian: In this format, the most significant byte (the one representing the highest order value) is stored at the highest memory address, while the least significant byte is stored at the lowest memory address. Think of it like writing numbers from left to right, where the biggest digits come first. For instance, the number 1234567 in big-endian looks like this in memory:
31 32 33 34 35 36 37
- Little-endian: This format is the opposite—the least significant byte is stored at the highest memory address, and the most significant byte is stored at the lowest memory address. This arrangement is akin to writing numbers from right to left, with the smallest digits first. In the little-endian format, the number 1234567 is stored like this:
37 36 35 34 33 32 31
Telegram database includes records in both of these formats, which is important to consider when interpreting records that include numeric values, such as integers and floats. String (text) values in Telegram records are encoded in UTF-8, where each character is represented by a single byte; that is why you do not need to take endianness into account when interpreting them.
For example, let us look at a message record in t7 with Belkasoft X SQLite viewer that has a built-in Hex viewer for convenient analysis of binary records. t7 includes two columns, key and value, and both of them contain binary data:
Figure 3: A Telegram message record in the Belkasoft X SQLite viewer
The key column stores data in the big-endian format. When inspecting it with the Hex viewer, you can locate and convert the chat ID value represented by an integer. The Type converter helps you decode binary code into various data types:
Figure 4: Decoding a multi-byte value stored in the big-endian format with the Type converter
In the value column, you can find the same binary value organized in reverse order since this column stores data in the little-endian format. To decode the bytes correctly, you need to switch the Type converter from the big-endian to little-endian mode:
Figure 5: Decoding a multi-byte value stored in the little-endian format with the Type converter
Account settings: t0
When inspecting an iOS Telegram database, you should first examine the t0 table to find out the numeric ID of the Telegram account owner. The record that stores it is located under key 2:
Figure 6: A Telegram account owner ID record in db_sqlite, t0
The corresponding value column includes a stream of bytes, also referred to as BLOB. Here, you need to locate the peerId string. It indicates the beginning of an eight-byte integer value that represents the account owner ID number in the current database. In this example, it is 8E A5 13 59 08 00 00 00. The value column stores data in the little-endian format. To decode the ID, select the eight bites and switch the Type converter to the little-endian mode.
Chat details: t2
In the t2 table, the key column includes numeric IDs of the user's chats within the current device.
Telegram can include the following chat types:
- One-to-one chats
- Secret chats
- Group chats
- Channels (public and private) and channel topics
- Bots
- Saved messages
Based on our observations, bots and some public accounts, like Telegram's official account, tend to have the same key numbers on different devices. Other types of chat IDs, however, are typically unique to the database, and if a user has several secret chats with the same contact, each of them will have a unique ID as well.
Let us locate the account owner ID in the key column:
Figure 7: A chat record in db_sqlite, t2, with contact details highlighted
The associated value column includes information about the chat (in this example, account owner details) encoded as a stream of bytes in the little-endian format. When inspecting it with the Hex viewer, you can spot some decoded text representing keys and values. In this example:
- Bytes 02 66 6E 04 represent the fn (first name) key; the first byte in the group indicates the number of bytes in the key name, and the last one indicates the type of the value this key defines (0-Integer32, 1-Integer64, 2-Boolean, 3-Double, 4-String, and so on)
- 04 00 00 00 that go next declare the number of bytes in the value, which is four in this example
- 4E 69 6E 6F are the next four bytes representing the value, and when converted to a text string, they reveal the account owner's name, which is Nino
Using the same approach, you can figure out the last name (ln), user name (un), and phone number (p) if they are available. Note that string values may also include special characters and emojis that are not visible as decoded text but hold additional bytes in the string.
Since those are text values, you can read them with the Hex viewer without much effort, but what else can you find here?
If a chat has a profile picture assigned, the ph key includes an array of objects with the properties of the picture file. To make it simpler, we will not decode all objects but will focus on figuring out the name of the file. In the lower part of the record, you can find the following keys and values:
Figure 8: A chat record in db_sqlite, t2, with the profile photo details highlighted
- Bytes 01 64 00 reveal the d key that defines the first numeric part of the file name; the last byte in the array indicates it is a four-byte integer value
- 02 00 00 00 represent the value, which is two in our example
- 01 70 01 stand for the p key that defines the second part of the file name that comprises an eight-byte integer value
- B0 C5 31 1B 6B 42 89 48 represent the second part of the name (you can see it decoded by the Type converter in Figure 8)
- 01 73 00 reveal the s key that defines the last part of the file name, which is an four-byte integer value
- 01 00 00 00 reveal the value (one)
As a result, we receive 2-5226781870325351856-0, which is part of the profile photo name. Now, we can locate this file in the media folder of the current Telegram account:
Figure 9: Telegram media folder filtered by the numeric part of the profile picture name
When analyzing records of one-to-one chats in t2, you will typically find the name and contact information of the other chat participant, while group chat and channel records will include a topic (t key). For example:
Figure 10: A Telegram group chat topic highlighted in the Hex viewer
If you come across a record with no distinctive keys and values, it may be a chat with a deleted account or a secret chat record.
Message records: t7
The t7 table in the db_sqlite database includes the Telegram account owner's messaging details. It consists of the key and value columns, both with binary data.
The key column stores data in the big-endian format. Let us explore what information it includes:
- The first eight bytes represent the numeric ID of the chat where the message belongs; you can calculate the number and then check the chat details in the t2 table
Figure 11: A record in db_sqlite, t7, key column, with the chat ID highlighted
- After four empty bytes, you can find a four-byte integer representing the Unix timestamp of the record
Figure 12: A record in db_sqlite, t7, key column, with the message timestamp decoded in the Hex viewer
The value column in t7 includes the details and contents of exchanged messages. Telegram users can exchange texts, emojis and stickers, audio and video calls, files, voice and video messages, location pins, polls, and more. The data in the value column depends on the type of information in it. It is also important to keep in mind that it stores data in the little-endian format.
Let us first examine a simple text message:
Figure 13: A record in db_sqlite, t7, value column with text message details highlighted
- The first eight bytes of interest begin at byte 21. This group represents the numeric ID of the message sender. In our example, it is the same number as the chat ID in the key column because we are inspecting a message sent in a one-to-one chat. In a group chat, these IDs would differ.
- The next four bytes indicate the number of bytes in the text of the message
- Then goes the message itself
Another example is a call record. Here is what you can find in one:
Figure 14: A record in db_sqlite, t7, value column, with call details highlighted
- The caller ID typically starts at byte 25 and is represented by an eight-byte value
- Next, we should look for the _rawValue key that defines the event included in the record
- 0E 00 00 00 that come after the key represent the value 14, which indicates the call event; you can see it decoded in Figure 14
- One more important piece in this type of record goes after the d key, which defines the call duration in seconds
- 09 00 00 00 represent the call duration value—nine seconds in this example
As investigators, you may also be interested in geolocation pins:
Figure 15: A record in db_sqlite, t7, value column, with geolocation information highlighted
- At byte 21, you can find an eight-byte integer with the sender ID
- Bytes 02 6C 61 03 represent the la key that defines the latitude value; according to the last byte in the group, it has a double (float64) type
- Next goes the value itself that reveals the location latitude in decimal degrees; you can see it in Figure 15 converted to 41.7467826935336 in the Type converter
- Bytes 02 6C 6F 03 represent the lo key that defines the longitude value, which is also a double (float64) type
- The following eight bytes are the longitude in decimal degrees; in our example, it is 44.791361713752
Another example is a record of a picture transfer:
Figure 16: A record in db_sqlite, t7, value column, with the picture file name details highlighted
- Like in many other message records, at byte 21, you can find an eight-byte integer with the sender ID
- Next, you need to look for the d key followed by the i key in decoded text
- The d key defines the first numeric part of the attached picture, which you can decode from the next four bytes (02 00 00 00 = 2)
- The i key defines the second part of the picture name encoded in the next eight bytes, which you can see in Figure 16 decoded in the Type converter; a typical picture transfer will contain several repetitions of the file name
- After you decode the file name, you can locate the picture in the media folder
Figure 17: Telegram media folder filtered by a part of the picture name
The t7 examples we have shown are typical for one-to-one chat records. When messages are exchanged in secret chats or received through channels, the structure of the records may differ. When manually analyzing t7 value records, a good approach will be to first check what decoded text reveals to understand what type of message you are dealing with. Then, you can look for familiar keys and their values to identify the exchanged objects and their properties.
Conclusion
In this first part of our iOS Telegram forensics series, we have covered the key steps for acquiring and analyzing Telegram data from iOS devices. By obtaining a full file system extraction and decoding the application SQLite database, investigators can access valuable information, such as account information, chat details, and exchanged messages.
Digital forensics tools like Belkasoft X can assist throughout the process—from acquiring data to decoding binary Telegram records and extracting valuable data, such as contact, group, and channel details, secret chats, messages, and exchanged media files. However, if your investigation requires manual validation of the extracted artifacts, it is important to understand how Telegram stores its data to interpret it accurately.
In the next article on iOS Telegram forensics, we will dive deeper into analyzing Telegram artifacts in Belkasoft X, covering secret chats, deleted messages, and more. Stay tuned!