# Software
This section provides detailed information about audio software
components.
## PulseAudio
PulseAudio manages all audio applications, local and network streams,
devices, filters, and audio I/O.

### PulseAudio PAL plug-in
The PulseAudio PAL plug-in is responsible for loading PAL. It allows the
client to configure the audio devices and invoke various audio use
cases.
The following are the components of the PulseAudio PAL plug-in:
| **Card** | Represents a sound card which is a collection of supported
profiles, ports, sinks, and sources.
Functionalities of a card module are:
|
| --- | --- |
| **Sink** | Responsible for configuration of the audio playback path.
>
>
> Functionalities of a sink module are:
>
> |
| **Source** | Responsible for configuration of the audio capture path.
>
>
> Functionalities of a source module are:
>
> |
## Platform Adaptation Layer (PAL)
The Platform Adaptation Layer (PAL) provides higher-level audio-specific
APIs to access the underlying audio hardware and drivers to enable
feature-rich audio use cases.
PulseAudio uses the same PAL APIs for different audio use cases. The
source code for the PAL module is located at:
`build-qcom-wayland/workspace/sources/qcom-pal/opensource/arpal-lx`
All APIs that are exposed by the PAL module are declared in:
`build-qcom-wayland/workspace/sources/qcom-pal/opensource/arpal-lx/inc/PalApi.h`
Some frequently used PAL APIs are described below.
### pal\_init
Initializes the PAL, parses the related configuration files, and stores
them in local structure to be used during a use case.
int32_t pal_init( )
Copy to clipboard
**Parameters**
None
**Return value**
- 0 on success
- Error code on failure
### pal\_deinit
De-initializes PAL and frees up the resources allocated during
initialization.
void pal_deinit()
Copy to clipboard
**Parameters**
None
**Return value**
- 0 on success
- Error code on failure
### pal\_stream\_open
Opens a stream with the specified configuration such as source/sink
devices, media configuration, etc. Returns the stream handle on
successful execution.
int32_t pal_stream_open(
struct pal_stream_attributes *attributes,
uint32_t no_of_devices,
struct pal_device *devices,
uint32_t no_of_modifiers,
struct modifier_kv *modifiers,
pal_stream_callback cb,
uint64_t cookie,
pal_stream_handle_t **stream_handle)
Copy to clipboard
**Parameters**
| attributes | Valid stream attributes obtained from pal\_stream\_open |
| --- | --- |
| no\_of\_devices | Number of audio devices with which to initially start the stream |
| devices | Array of pal\_devices. The size of the array is based on the
no\_of\_devices specified by the client. |
| no\_of\_modifiers | Number of modifiers |
| modifiers | Array of modifiers. Modifiers are used to add additional
key-value pairs. |
| cb | Callback function associated with the stream. Any event is
notified through this callback function. |
| cookie | Client data associated with the stream. This cookie is
returned in the callback function. |
| stream\_handle | Updated with valid stream handle if the operation is successful |
**Return value**
- 0 on success
- Error code on failure
### pal\_stream\_start
Starts a stream.
int32_t pal_stream_start(
pal_stream_handle_t *stream_handle)
Copy to clipboard
**Parameters**
| stream\_handle | Valid stream handle obtained from pal\_stream\_open |
| --- | --- |
**Return value**
- 0 on success
- Error code on failure
### pal\_stream\_read
Reads the audio buffer captured from the audio source device.
ssize_t pal_stream_read(
pal_stream_handle_t *stream_handle,
struct pal_buffer *buf)
Copy to clipboard
**Parameters**
| stream\_handle | Valid stream handle obtained from pal\_stream\_open |
| --- | --- |
| buf | Pointer to pal\_buffer containing audio samples and metadata |
**Return value**
- Number of bytes read
- Error code on failure
### pal\_stream\_write
Writes the audio buffer for stream rendering over sink device.
ssize_t pal_stream_write(
pal_stream_handle_t *stream_handle,
struct pal_buffer *buf)
Copy to clipboard
**Parameters**
| stream\_handle | Valid stream handle obtained from pal\_stream\_open |
| --- | --- |
| buf | Pointer to pal\_buffer containing audio samples and metadata |
**Return value**
- Number of bytes read
- Error code on failure
### pal\_stream\_stop
Stops a stream.
int32_t pal_stream_stop(
pal_stream_handle_t *stream_handle)
Copy to clipboard
**Parameters**
| stream\_handle | Valid stream handle obtained from pal\_stream\_open |
| --- | --- |
**Return value**
- 0 on success
- Error code on failure
### pal\_stream\_close
Closes a stream.
int32_t pal_stream_close(
pal_stream_handle_t *stream_handle)
Copy to clipboard
**Parameters**
| stream\_handle | Valid stream handle obtained from pal\_stream\_open |
| --- | --- |
**Return value**
- `0` on success
- Error code on failure
## TinyALSA
TinyALSA is a library that wraps ALSA kernel interface into APIs that
clients can invoke and provides a plug-in interface to emulate ALSA
APIs.
TinyALSA source code can be found at:
`build-qcom-wayland/workspace/sources/tinyalsa` and
`build-qcom-wayland/workspace/sources/tinycompress`.
Some of the frequently used TinyALSA APIs are described below. See the
[open source TinyALSA
documentation](https://github.com/tinyalsa/tinyalsa/blob/master/include/tinyalsa/pcm.h)
for a complete description of all APIs.
Additional details about TinayAlsa based applications are available for
developers who have full access to the proprietary software shipped with
Qualcomm Linux. See the [Qualcomm Linux Audio Guide –
Addendum](https://docs.qualcomm.com/bundle/resource/topics/80-70017-16A/customize_addendum.html#tinyalsa-based-applications)
for more information.
### pcm\_open
Used to open a PCM audio device for input and output operations.
Initializes a PCM device for communication, allowing subsequent
read/write operations in audio data.
struct pcm *pcm_open(
unsigned int card,
unsigned int device,
unsigned int flags,
struct pcm_config *config)
Copy to clipboard
**Parameters**
| card | Specifies the card number |
| --- | --- |
| device | Specifies the device number in the chosen card |
| flags | Flags to configure various aspects of pcm device |
| config | Structure variable used to specify audio stream parameters |
**Return value**
`pcm* handle`
### pcm\_is\_ready
Used to check if the PCM device is ready for input/output operations.
int pcm_is_ready(struct pcm *pcm)
Copy to clipboard
**Parameters**
| pcm | Pointer to opened PCM device |
| --- | --- |
**Return value**
- 0 on success
- Error code on failure
### pcm\_prepare
Prepares audio device input and output operations.
int pcm_prepare(
struct pcm *pcm)
Copy to clipboard
**Parameters**
| pcm | Pointer to opened PCM device |
| --- | --- |
**Return value**
- 0 on success
- Error code on failure
### pcm\_start
Used to start the PCM audio device for input and output operations.
int pcm_start(
struct pcm *pcm)
Copy to clipboard
**Parameters**
|pcm|Pointer to the PCM device that has been opened|
**Return value**
- 0 on success
- Error code on failure
### pcm\_write
Used to write audio data to the audio PCM device. Takes audio data as
input and sends it to the PCM device for playback or processing.
int pcm_write(
struct pcm *pcm,
const void *data,
unsigned int count)
Copy to clipboard
**Parameters**
| pcm | Pointer to PCM device that has been opened |
| --- | --- |
| data | Audio data to be written |
| count | Number of audio frames to be written |
**Return value**
- 0 on success
- Error code on failure
### pcm\_read
Retrieves audio data from the PCM device, which allows the application
to capture audio data from a microphone.
int pcm_read(
struct pcm *pcm,
void *data,
unsigned int count)
Copy to clipboard
**Parameters**
| pcm | Pointer to the PCM device that has been opened |
| --- | --- |
| data | Audio data to be read |
| count | Number of audio frames to be read |
**Return value**
- 0 on success
- Error code on failure
### pcm\_stop
Used to stop the PCM audio device from further input and output
operations.
int pcm_stop(
struct pcm *pcm)
Copy to clipboard
**Parameters**
| pcm | Pointer to the PCM device that has been opened |
| --- | --- |
**Return value**
- 0 on success
- Error code on failure
### pcm\_close
Used to close the PCM audio device. This releases the resources
associated with PCM device and releases the memory.
int pcm_close(
struct pcm *pcm)
Copy to clipboard
**Parameters**
| pcm | Pointer to the PCM device that has been opened |
| --- | --- |
**Return value**
- 0 on success
- Error code on failure
## Audio Graph Manager (AGM)
AGM provides interfaces to allow TinyALSA-based mixer controls and
PCM/compress plug-ins to interact and enable various audio use cases.
AGM runs as part of PulseAudio service that runs in the user space.

AGM provides APIs for mixer plugins and PCM/compress APIs to set up
audio use cases. It maintains multiple ALSA clients to set up use cases.
AGM also handles management of front-end to back-end connections.
The following diagram shows the AGM block at a high level.

| Object | Description |
| --- | --- |
| **Session** |
A session object represents an audio playback or capture
session.
It is created when session-specific mixer controls or APIs
are invoked.
Responsibilities include providing APIs for TinyALSA
plug-ins to configure streams and managing state transitions
of graph and device objects.
|
| **Graph** |
A graph object represents an audio use case.
It interacts with GSL to open, manage, and close graphs.
Responsibilities include providing APIs for graph creation,
managing graphs, and configuring stream and device
endpoints.
|
| **Device** | |
## AudioReach Graph Service (ARGS)
The AudioReach graph services (ARGS) consists of the graph service layer
(GSL), generic packet router (GPR), and ACDB management layer (AML). It
handles initialization and creation of graphs, and creation of
packets for sending series of commands to SPF.

| Component | Description |
| --- | --- |
| **GSL** |
The Graph Service Layer (GSL) is a software driver for SPF
which manages graphs, subgraphs, buffers, and
configurations.
GSL loads and initializes graphs using graph key vectors
(GKVs).
It handles data commands and SPF module calibration.
|
| **GPR** | |
| **AML** |
AML provides get/set APIs to retrieve and adjust data in
Audio Calibration Database (ACDB) files.
It provides data abstractions and organization for how
calibration data is to be consumed by the audio driver and
its components.
|
## Signal Processing Framework (SPF)
Signal Processing Framework runs in the LPAI subsystem and is
responsible for performing audio data processing.

The following diagram provides a high-level overview of the functional
blocks used in SPF.

| Component | Description |
| --- | --- |
| **Audio Processing Manager (APM)** | APM is responsible for setting up and managing the use case
graphs in signal processing framework (SPF). It provides the
standard APIs to the graph management library and APM client
for setting up and configuring audio use cases. |
| **Modules** | A module is an addressable functionality in the SPF. It is
responsible for performing real-time audio processing within
the LPAI subsystem. |
| **Containers** | A container is a framework implementation that helps execute a
group of data processing modules together in the same software
thread. Each container instance runs in its own software
thread. |
## Realization of audio use cases
Each audio use case is represented as a graph consisting of subgraphs of
a specific type. Each subgraph consists of one or more functional
software blocks (referred to as modules) that perform a specific
function.
### Audio graph concepts and terminology
| **Use case** | A graph of modules from source endpoint(s) to sink endpoint(s)
that satisfies the product defined use case. |
| --- | --- |
| **Graph** | A logical interpretation of a group of one or more sub-graphs
connected together to realize a specific use case. |
| **Subgraph** | A logical abstraction for a group of modules that are connected
and manipulated as a single entity. |
| **Container** | Object that allows the system designer to group and execute
audio processing modules together in single software thread. |
| **Module** | The smallest independent processing unit within signal
processing framework. |
| **Key value (KV) pair** | The individual key and associated values in a key vector.
For example, a key can be a sound device and a value can be
headphone, speaker, or some other sound device. |
| **Key vector** | Uniquely identifies a graph or subgraph through a set of KV
pairs. |
| **Graph key vector (GKV)** | GKV is a unique identifier used to retrieve a graph which is
represented by a set of multiple KV pairs. The graph or system
designer associates a set of unique <keys> and <values> when
creating a subgraph from the QACT UI canvas. |
| **Calibration key vector (CKV)** | CKV is a unique identifier used to retrieve calibration data
which is represented by a set of multiple KV pairs. The graph
or system designer associates a set of unique <keys> and
<values> when storing calibration data. |
| **Tag and tag key vector (TKV)** | A tag is an identifier used to set runtime parameters for one or
more modules. It allows updating module configurations (for example,
enabling/disabling features like echo cancellation or
equalization) within a graph at runtime. |
### Graph segments
An audio use case is comprised of the following segments. The front-end
represents stream and streamPP subgraphs, while the back-end
represents the PSPD, devicePP, and device subgraphs.
| **Stream** | Provides a data write/read interface and performs decoding and
encoding of data if it is compressed |
| --- | --- |
| **StreamPP** | Contains stream-based processing modules (for example,
equalizer) |
| **Per-stream per-device (PSPD)** | Contains a module to convert the stream media format to the
device media format |
| **DevicePP** | Contains of processing modules for sound device tuning |
| **Device** | Hardware endpoint such as CodecDMA (Soundwire), I2S, or TDM port |
Once a front-end is connected to a back-end using a routing mixer control,
the full GKV is formed by concatenating the subgraph GKVs and the CKVs
assigned using mixer controls. Upon opening the front-end PCM or compress
device, AGM invokes GSL APIs with concatenated GKVs and CKVs to set up
the graph in SPF and apply calibration. At the same time, AGM opens a
kernel PCM device corresponding to the connected back-ends to begin
audio peripheral setup.
### Sample audio graph
The follow diagram shows an example audio graph for a playback scenario.

In this graph:
1. The stream subgraph consists of a write shared memory endpoint, PCM
decoder, and PCM converter. The client passes PCM samples to write
shared memory endpoint.
2. The PCM converter converts PCM samples to a format supported by the
stream-specific post-processing modules if conversion is necessary.
3. Output of the stream subgraph is fed into the stream-device subgraph,
which contains the media format converter (MFC). MFC converts the
stream-subgraph PCM to the device-subgraph PCM format.
4. After conversion, output of the stream-device subgraph is fed into
the device PP subgraph for device-specific post-processing. A mixer
is placed at the beginning of subgraph to mix input streams.
5. Output of the devicePP subgraph is then fed into the device subgraph,
which contains a hardware endpoint module such as an I2S driver.
The following is the GKV for this example graph:
GKV1:
GKV2:
Copy to clipboard
### Audio calibration database (ACDB)
The ACDB is a static database located on the apps processor. It contains
all tuning/calibration parameters for the LPAI. Calibration data for
various audio modules for various use cases is organized in an \*.acdb
file format that can be edited using a PC-based tool called QACT and
placed on the device file system in the /etc/acdbdata/ folder. During
use case initialization or device switch, the AML queries the ACDB
database with a specified GKV and pushes the device calibration data to SPF.
Last Published: Aug 13, 2025
[Previous Topic
APIs and Sample Apps](https://docs.qualcomm.com/bundle/publicresource/80-70017-16/topics/apis_and_sample_apps.md) [Next Topic
Customize](https://docs.qualcomm.com/bundle/publicresource/80-70017-16/topics/customize.md)