Linux ALSA sound card programming __arduino

Source: Internet
Author: User
I. Introduction

The ALSA standard is an advanced Linux sound system. It contains kernel-driven collections, API libraries, and tools to support Linux sounds. The ALSA contains a series of kernel-driven support for different sound cards, as well as an API library for Libasound. Using these to write a program does not need to open the device and so on, so programmers in the writing process will not be bothered by the underlying things. In contrast to this oss/free drive at the kernel level calls, you need to specify the device name and call IOCTL. To provide backward compatibility, ALSA provides kernel modules to mimic the Oss/free drive, so most programs do not need to be changed. ALSA has the ability to invoke Plug-ins to provide extensions to new devices, including those that are simulated with software. ALSA also provides a set of command-line tools including mixer, sound file player and tools to control the special functions of some special sound cards.

two. ALSA System:

The ALSA API is mainly divided into the following types of interfaces:

• Control Interface: Provides a flexible way to manage registered sound cards and queries for existing sound cards.

PCM interface: To provide the management of digital audio capture and playback.

L Original MIDI Interface: Support MIDI (musical instrument Digital Interface), a standard electronic music instruction set. These APIs provide access to the MIDI bus on the sound card. These original excuses work directly on the MIDI event, and programmers only need to manage protocols and time.

L-Time Interface: Provides access to the timer on the sound card for synchronization events that support sound.

L Sequencer Interface: A high-level interface for MIDI programming and voice synchronization that is higher than the original MIDI interface. It can handle a lot of MIDI protocols and timers.

L Mixer Interface: Controls the device on the sound card that transmits the signal and controls the sound size.

three. The sound card's cache and the data transmission:

A sound card has a sound card memory used to store samples of records. An interruption occurs when it is fully written. The kernel driver uses DMA to transfer data to memory. Similarly, when playing, the audio sample in memory is transferred to the sound card in memory using DMA.

The sound card's cache is looped, and only the memory structure in the application is discussed: ALSA divides the data into contiguous fragments and transmits it to the cell fragment.

Four: Typical sound program structure:

Open interface for capture or playback

Set Hardware parameters

(access mode, data format, channels, rate, etc.)

While there are data to processed:

Read PCM data (capture)

or write PCM data (playback)

Close interface

Five. Some examples: 1. Show some types and formats of PCM:

#include <iostream>

#include <alsa/asoundlib.h>

int main ()

{

Std::cout << "ALSA library version:" << snd_lib_version_str << Std::endl;

Std::cout << "PCM stream types:" << Std::endl;

for (int val=0; Val <= snd_pcm_stream_last; ++val)

Std::cout << Snd_pcm_stream_name ((snd_pcm_stream_t) val) << Std::endl;

Std::cout << Std::endl;

Std::cout << "PCM access types:" << Std::endl;

for (int val=0; Val <= snd_pcm_access_last; ++val)

Std::cout << Snd_pcm_access_name ((snd_pcm_access_t) val) << Std::endl;

Std::cout << Std::endl;

Std::cout << "PCM subformats:" << Std::endl;

for (int val=0; Val <= snd_pcm_subformat_last; ++val)

Std::cout << Snd_pcm_subformat_name ((snd_pcm_subformat_t) val) << "(<< snd_pcm_subformat_ Description ((snd_pcm_subformat_t) val) << ")" << Std::endl;

Std::cout << Std::endl;

Std::cout << "PCM states:" << Std::endl;

for (int val=0; Val <= snd_pcm_state_last; ++val)

Std::cout << Snd_pcm_state_name ((snd_pcm_state_t) val) << Std::endl;

Std::cout << Std::endl;

Std::cout << "PCM formats:" << Std::endl;

for (int val=0; Val <= snd_pcm_format_last; ++val)

Std::cout << Snd_pcm_format_name ((snd_pcm_format_t) val) << "(" << snd_pcm_format_description (snd_ pcm_format_t) (val) << ")" << Std::endl;

Std::cout << Std::endl;

}

2. Open PCM device and set parameters

#include <iostream>

#include <alsa/asoundlib.h>

int main ()

{

int RC;

Snd_pcm_t* handle;

snd_pcm_hw_params_t* params;

unsigned int val, val2;

int dir;

snd_pcm_uframes_t frames;

if (rc = Snd_pcm_open (&handle, "Default", Snd_pcm_stream_playback, 0)) < 0)

{

Std::cerr << "Unable to open PCM devices:" << snd_strerror (RC) << Std::endl;

Exit (1);

}

Snd_pcm_hw_params_alloca (&params);

Snd_pcm_hw_params_any (handle, params);

Snd_pcm_hw_params_set_access (handle, params, snd_pcm_access_rw_interleaved);

Snd_pcm_hw_params_set_format (handle, params, snd_pcm_format_s16_le);

Snd_pcm_hw_params_set_channels (handle, params, 2);

val = 44100;

Snd_pcm_hw_params_set_rate_near (handle, params, &val, &dir);

if (rc = Snd_pcm_hw_params (handle, params)) < 0)

{

Std::cerr << "Unable to set HW parameters:" << snd_strerror (RC) << Std::endl;

Exit (1);

}

Std::cout << "PCM Handle name =" << snd_pcm_name (handle) << Std::endl;

Std::cout << "PCM state =" << snd_pcm_state_name (snd_pcm_state (handle)) << Std::endl;

Snd_pcm_hw_params_get_access (params, (snd_pcm_access_t *) &val);

Std::cout << "Access type =" << snd_pcm_access_name ((snd_pcm_access_t) val) << Std::endl;

Snd_pcm_hw_params_get_format (params, (snd_pcm_format_t*) (&val));

Std::cout << "format = '" << snd_pcm_format_name (snd_pcm_format_t) val) << "(" << Snd_pcm_forma T_description ((snd_pcm_format_t) val) << ")" << Std::endl;

Snd_pcm_hw_params_get_subformat (params, (snd_pcm_subformat_t *) &val);

Std::cout << "Subformat = '" <<

Snd_pcm_subformat_name ((snd_pcm_subformat_t) val) << "' (" << snd_pcm_subformat_description (snd_pcm_ subformat_t) (val) << ")" << Std::endl;

Snd_pcm_hw_params_get_channels (params, &val);

Std::cout << "channels =" << val << Std::endl;

Snd_pcm_hw_params_get_rate (params, &val, &dir);

Std::cout << "rate =" << val << "bps" << std::endl;

Snd_pcm_hw_params_get_period_time (params, &val, &dir);

Std::cout << "Period time =" << val << "Us" << Std::endl;

Snd_pcm_hw_params_get_period_size (params, &frames, &dir);

Std::cout << "Period size =" << static_cast<int> (frames) << "frames" << Std::endl;

Snd_pcm_hw_params_get_buffer_time (params, &val, &dir);

Std::cout << "Buffer time =" << val << "Us" << Std::endl;

Snd_pcm_hw_params_get_buffer_size (params, (snd_pcm_uframes_t *) &val);

Std::cout << "Buffer size =" << val << "frames" << Std::endl;

Snd_pcm_hw_params_get_periods (params, &val, &dir);

Std::cout << "periods per buffer =" << val << "frames" << Std::endl;

Snd_pcm_hw_params_get_rate_numden (params, &val, &val2);

Std::cout << "Exact rate =" << val/val2 << "bps" << std::endl;

val = snd_pcm_hw_params_get_sbits (params);

Std::cout << "significant bits =" << val << Std::endl;

Snd_pcm_hw_params_get_tick_time (params, &val, &dir);

Std::cout << "Tick time =" << val << "Us" << Std::endl;

val = Snd_pcm_hw_params_is_batch (params);

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.