Merge changes I84b3ca1e,I41db99f8 into msm-3.0
* changes:
ASoc: msm: Add support for adie RX & TX calibration
Revert "msm: audio: qdsp6v2: Support for out-of-band calibration"
diff --git a/arch/arm/mach-msm/include/mach/qdsp6v2/audio_acdb.h b/arch/arm/mach-msm/include/mach/qdsp6v2/audio_acdb.h
index 16751fe..a55dee6 100644
--- a/arch/arm/mach-msm/include/mach/qdsp6v2/audio_acdb.h
+++ b/arch/arm/mach-msm/include/mach/qdsp6v2/audio_acdb.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2011, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 and
@@ -28,9 +28,15 @@
uint32_t cal_paddr;
};
+struct acdb_atomic_cal_block {
+ atomic_t cal_size;
+ atomic_t cal_kvaddr;
+ atomic_t cal_paddr;
+};
+
struct acdb_cal_data {
- uint32_t num_cal_blocks;
- struct acdb_cal_block *cal_blocks;
+ uint32_t num_cal_blocks;
+ struct acdb_atomic_cal_block *cal_blocks;
};
uint32_t get_voice_rx_topology(void);
@@ -44,6 +50,7 @@
void get_all_vocstrm_cal(struct acdb_cal_block *cal_block);
void get_all_vocvol_cal(struct acdb_cal_block *cal_block);
void get_anc_cal(struct acdb_cal_block *cal_block);
+void get_afe_cal(int32_t path, struct acdb_cal_block *cal_block);
void get_audproc_cal(int32_t path, struct acdb_cal_block *cal_block);
void get_audstrm_cal(int32_t path, struct acdb_cal_block *cal_block);
void get_audvol_cal(int32_t path, struct acdb_cal_block *cal_block);
diff --git a/arch/arm/mach-msm/qdsp6v2/audio_acdb.c b/arch/arm/mach-msm/qdsp6v2/audio_acdb.c
index 37a6900..2e61e90 100644
--- a/arch/arm/mach-msm/qdsp6v2/audio_acdb.c
+++ b/arch/arm/mach-msm/qdsp6v2/audio_acdb.c
@@ -22,43 +22,52 @@
#define MAX_NETWORKS 12
+struct sidetone_atomic_cal {
+ atomic_t enable;
+ atomic_t gain;
+};
+
+
struct acdb_data {
struct mutex acdb_mutex;
/* ANC Cal */
- struct acdb_cal_block anc_cal;
+ struct acdb_atomic_cal_block anc_cal;
/* AudProc Cal */
- uint32_t asm_topology;
- uint32_t adm_topology[MAX_AUDPROC_TYPES];
- struct acdb_cal_block audproc_cal[MAX_AUDPROC_TYPES];
- struct acdb_cal_block audstrm_cal[MAX_AUDPROC_TYPES];
- struct acdb_cal_block audvol_cal[MAX_AUDPROC_TYPES];
+ atomic_t asm_topology;
+ atomic_t adm_topology[MAX_AUDPROC_TYPES];
+ struct acdb_atomic_cal_block audproc_cal[MAX_AUDPROC_TYPES];
+ struct acdb_atomic_cal_block audstrm_cal[MAX_AUDPROC_TYPES];
+ struct acdb_atomic_cal_block audvol_cal[MAX_AUDPROC_TYPES];
/* VocProc Cal */
- uint32_t voice_rx_topology;
- uint32_t voice_tx_topology;
- struct acdb_cal_block vocproc_cal[MAX_NETWORKS];
- struct acdb_cal_block vocstrm_cal[MAX_NETWORKS];
- struct acdb_cal_block vocvol_cal[MAX_NETWORKS];
+ atomic_t voice_rx_topology;
+ atomic_t voice_tx_topology;
+ struct acdb_atomic_cal_block vocproc_cal[MAX_NETWORKS];
+ struct acdb_atomic_cal_block vocstrm_cal[MAX_NETWORKS];
+ struct acdb_atomic_cal_block vocvol_cal[MAX_NETWORKS];
/* size of cal block tables above*/
- uint32_t vocproc_cal_size;
- uint32_t vocstrm_cal_size;
- uint32_t vocvol_cal_size;
+ atomic_t vocproc_cal_size;
+ atomic_t vocstrm_cal_size;
+ atomic_t vocvol_cal_size;
/* Total size of cal data for all networks */
- uint32_t vocproc_total_cal_size;
- uint32_t vocstrm_total_cal_size;
- uint32_t vocvol_total_cal_size;
+ atomic_t vocproc_total_cal_size;
+ atomic_t vocstrm_total_cal_size;
+ atomic_t vocvol_total_cal_size;
+
+ /* AFE cal */
+ struct acdb_atomic_cal_block afe_cal[MAX_AUDPROC_TYPES];
/* Sidetone Cal */
- struct sidetone_cal sidetone_cal;
+ struct sidetone_atomic_cal sidetone_cal;
/* PMEM information */
- int pmem_fd;
- unsigned long paddr;
- unsigned long kvaddr;
- unsigned long pmem_len;
- struct file *file;
+ atomic_t pmem_fd;
+ atomic64_t paddr;
+ atomic64_t kvaddr;
+ atomic64_t pmem_len;
+ struct file *file;
};
@@ -67,90 +76,105 @@
uint32_t get_voice_rx_topology(void)
{
- return acdb_data.voice_rx_topology;
+ return atomic_read(&acdb_data.voice_rx_topology);
}
void store_voice_rx_topology(uint32_t topology)
{
- acdb_data.voice_rx_topology = topology;
+ atomic_set(&acdb_data.voice_rx_topology, topology);
}
uint32_t get_voice_tx_topology(void)
{
- return acdb_data.voice_tx_topology;
+ return atomic_read(&acdb_data.voice_tx_topology);
}
void store_voice_tx_topology(uint32_t topology)
{
- acdb_data.voice_tx_topology = topology;
+ atomic_set(&acdb_data.voice_tx_topology, topology);
}
uint32_t get_adm_rx_topology(void)
{
- return acdb_data.adm_topology[RX_CAL];
+ return atomic_read(&acdb_data.adm_topology[RX_CAL]);
}
void store_adm_rx_topology(uint32_t topology)
{
- acdb_data.adm_topology[RX_CAL] = topology;
+ atomic_set(&acdb_data.adm_topology[RX_CAL], topology);
}
uint32_t get_adm_tx_topology(void)
{
- return acdb_data.adm_topology[TX_CAL];
+ return atomic_read(&acdb_data.adm_topology[TX_CAL]);
}
void store_adm_tx_topology(uint32_t topology)
{
- acdb_data.adm_topology[TX_CAL] = topology;
+ atomic_set(&acdb_data.adm_topology[TX_CAL], topology);
}
uint32_t get_asm_topology(void)
{
- return acdb_data.asm_topology;
+ return atomic_read(&acdb_data.asm_topology);
}
void store_asm_topology(uint32_t topology)
{
- acdb_data.asm_topology = topology;
+ atomic_set(&acdb_data.asm_topology, topology);
}
void get_all_voice_cal(struct acdb_cal_block *cal_block)
{
- cal_block->cal_kvaddr = acdb_data.vocproc_cal[0].cal_kvaddr;
- cal_block->cal_paddr = acdb_data.vocproc_cal[0].cal_paddr;
- cal_block->cal_size = acdb_data.vocproc_total_cal_size +
- acdb_data.vocstrm_total_cal_size +
- acdb_data.vocvol_total_cal_size;
+ cal_block->cal_kvaddr =
+ atomic_read(&acdb_data.vocproc_cal[0].cal_kvaddr);
+ cal_block->cal_paddr =
+ atomic_read(&acdb_data.vocproc_cal[0].cal_paddr);
+ cal_block->cal_size =
+ atomic_read(&acdb_data.vocproc_total_cal_size) +
+ atomic_read(&acdb_data.vocstrm_total_cal_size) +
+ atomic_read(&acdb_data.vocvol_total_cal_size);
}
void get_all_cvp_cal(struct acdb_cal_block *cal_block)
{
- cal_block->cal_kvaddr = acdb_data.vocproc_cal[0].cal_kvaddr;
- cal_block->cal_paddr = acdb_data.vocproc_cal[0].cal_paddr;
- cal_block->cal_size = acdb_data.vocproc_total_cal_size +
- acdb_data.vocvol_total_cal_size;
+ cal_block->cal_kvaddr =
+ atomic_read(&acdb_data.vocproc_cal[0].cal_kvaddr);
+ cal_block->cal_paddr =
+ atomic_read(&acdb_data.vocproc_cal[0].cal_paddr);
+ cal_block->cal_size =
+ atomic_read(&acdb_data.vocproc_total_cal_size) +
+ atomic_read(&acdb_data.vocvol_total_cal_size);
}
void get_all_vocproc_cal(struct acdb_cal_block *cal_block)
{
- cal_block->cal_kvaddr = acdb_data.vocproc_cal[0].cal_kvaddr;
- cal_block->cal_paddr = acdb_data.vocproc_cal[0].cal_paddr;
- cal_block->cal_size = acdb_data.vocproc_total_cal_size;
+ cal_block->cal_kvaddr =
+ atomic_read(&acdb_data.vocproc_cal[0].cal_kvaddr);
+ cal_block->cal_paddr =
+ atomic_read(&acdb_data.vocproc_cal[0].cal_paddr);
+ cal_block->cal_size =
+ atomic_read(&acdb_data.vocproc_total_cal_size);
}
void get_all_vocstrm_cal(struct acdb_cal_block *cal_block)
{
- cal_block->cal_kvaddr = acdb_data.vocstrm_cal[0].cal_kvaddr;
- cal_block->cal_paddr = acdb_data.vocstrm_cal[0].cal_paddr;
- cal_block->cal_size = acdb_data.vocstrm_total_cal_size;
+ cal_block->cal_kvaddr =
+ atomic_read(&acdb_data.vocstrm_cal[0].cal_kvaddr);
+ cal_block->cal_paddr =
+ atomic_read(&acdb_data.vocstrm_cal[0].cal_paddr);
+ cal_block->cal_size =
+ atomic_read(&acdb_data.vocstrm_total_cal_size);
}
void get_all_vocvol_cal(struct acdb_cal_block *cal_block)
{
- cal_block->cal_kvaddr = acdb_data.vocvol_cal[0].cal_kvaddr;
- cal_block->cal_paddr = acdb_data.vocvol_cal[0].cal_paddr;
- cal_block->cal_size = acdb_data.vocvol_total_cal_size;
+ cal_block->cal_kvaddr =
+ atomic_read(&acdb_data.vocvol_cal[0].cal_kvaddr);
+ cal_block->cal_paddr =
+ atomic_read(&acdb_data.vocvol_cal[0].cal_paddr);
+ cal_block->cal_size =
+ atomic_read(&acdb_data.vocvol_total_cal_size);
}
void get_anc_cal(struct acdb_cal_block *cal_block)
@@ -162,13 +186,12 @@
goto done;
}
- mutex_lock(&acdb_data.acdb_mutex);
-
- cal_block->cal_kvaddr = acdb_data.anc_cal.cal_kvaddr;
- cal_block->cal_paddr = acdb_data.anc_cal.cal_paddr;
- cal_block->cal_size = acdb_data.anc_cal.cal_size;
-
- mutex_unlock(&acdb_data.acdb_mutex);
+ cal_block->cal_kvaddr =
+ atomic_read(&acdb_data.anc_cal.cal_kvaddr);
+ cal_block->cal_paddr =
+ atomic_read(&acdb_data.anc_cal.cal_paddr);
+ cal_block->cal_size =
+ atomic_read(&acdb_data.anc_cal.cal_size);
done:
return;
}
@@ -177,23 +200,69 @@
{
pr_debug("%s,\n", __func__);
- if (cal_block->cal_offset > acdb_data.pmem_len) {
+ if (cal_block->cal_offset > atomic64_read(&acdb_data.pmem_len)) {
pr_err("%s: offset %d is > pmem_len %ld\n",
__func__, cal_block->cal_offset,
- acdb_data.pmem_len);
+ (long)atomic64_read(&acdb_data.pmem_len));
goto done;
}
- mutex_lock(&acdb_data.acdb_mutex);
+ atomic_set(&acdb_data.anc_cal.cal_kvaddr,
+ cal_block->cal_offset + atomic64_read(&acdb_data.kvaddr));
+ atomic_set(&acdb_data.anc_cal.cal_paddr,
+ cal_block->cal_offset + atomic64_read(&acdb_data.paddr));
+ atomic_set(&acdb_data.anc_cal.cal_size,
+ cal_block->cal_size);
+done:
+ return;
+}
- acdb_data.anc_cal.cal_kvaddr =
- cal_block->cal_offset + acdb_data.kvaddr;
- acdb_data.anc_cal.cal_paddr =
- cal_block->cal_offset + acdb_data.paddr;
- acdb_data.anc_cal.cal_size =
- cal_block->cal_size;
+void store_afe_cal(int32_t path, struct cal_block *cal_block)
+{
+ pr_debug("%s, path = %d\n", __func__, path);
- mutex_unlock(&acdb_data.acdb_mutex);
+ if (cal_block->cal_offset > atomic64_read(&acdb_data.pmem_len)) {
+ pr_err("%s: offset %d is > pmem_len %ld\n",
+ __func__, cal_block->cal_offset,
+ (long)atomic64_read(&acdb_data.pmem_len));
+ goto done;
+ }
+ if ((path >= MAX_AUDPROC_TYPES) || (path < 0)) {
+ pr_err("ACDB=> Bad path sent to %s, path: %d\n",
+ __func__, path);
+ goto done;
+ }
+
+ atomic_set(&acdb_data.afe_cal[path].cal_kvaddr,
+ cal_block->cal_offset + atomic64_read(&acdb_data.kvaddr));
+ atomic_set(&acdb_data.afe_cal[path].cal_paddr,
+ cal_block->cal_offset + atomic64_read(&acdb_data.paddr));
+ atomic_set(&acdb_data.afe_cal[path].cal_size,
+ cal_block->cal_size);
+done:
+ return;
+}
+
+void get_afe_cal(int32_t path, struct acdb_cal_block *cal_block)
+{
+ pr_debug("%s, path = %d\n", __func__, path);
+
+ if (cal_block == NULL) {
+ pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
+ goto done;
+ }
+ if ((path >= MAX_AUDPROC_TYPES) || (path < 0)) {
+ pr_err("ACDB=> Bad path sent to %s, path: %d\n",
+ __func__, path);
+ goto done;
+ }
+
+ cal_block->cal_kvaddr =
+ atomic_read(&acdb_data.afe_cal[path].cal_kvaddr);
+ cal_block->cal_paddr =
+ atomic_read(&acdb_data.afe_cal[path].cal_paddr);
+ cal_block->cal_size =
+ atomic_read(&acdb_data.afe_cal[path].cal_size);
done:
return;
}
@@ -202,12 +271,10 @@
{
pr_debug("%s, path = %d\n", __func__, path);
- mutex_lock(&acdb_data.acdb_mutex);
-
- if (cal_block->cal_offset > acdb_data.pmem_len) {
+ if (cal_block->cal_offset > atomic64_read(&acdb_data.pmem_len)) {
pr_err("%s: offset %d is > pmem_len %ld\n",
__func__, cal_block->cal_offset,
- acdb_data.pmem_len);
+ (long)atomic64_read(&acdb_data.pmem_len));
goto done;
}
if (path >= MAX_AUDPROC_TYPES) {
@@ -216,15 +283,13 @@
goto done;
}
- acdb_data.audproc_cal[path].cal_kvaddr =
- cal_block->cal_offset + acdb_data.kvaddr;
- acdb_data.audproc_cal[path].cal_paddr =
- cal_block->cal_offset + acdb_data.paddr;
- acdb_data.audproc_cal[path].cal_size =
- cal_block->cal_size;
-
+ atomic_set(&acdb_data.audproc_cal[path].cal_kvaddr,
+ cal_block->cal_offset + atomic64_read(&acdb_data.kvaddr));
+ atomic_set(&acdb_data.audproc_cal[path].cal_paddr,
+ cal_block->cal_offset + atomic64_read(&acdb_data.paddr));
+ atomic_set(&acdb_data.audproc_cal[path].cal_size,
+ cal_block->cal_size);
done:
- mutex_unlock(&acdb_data.acdb_mutex);
return;
}
@@ -242,13 +307,12 @@
goto done;
}
- mutex_lock(&acdb_data.acdb_mutex);
-
- cal_block->cal_kvaddr = acdb_data.audproc_cal[path].cal_kvaddr;
- cal_block->cal_paddr = acdb_data.audproc_cal[path].cal_paddr;
- cal_block->cal_size = acdb_data.audproc_cal[path].cal_size;
-
- mutex_unlock(&acdb_data.acdb_mutex);
+ cal_block->cal_kvaddr =
+ atomic_read(&acdb_data.audproc_cal[path].cal_kvaddr);
+ cal_block->cal_paddr =
+ atomic_read(&acdb_data.audproc_cal[path].cal_paddr);
+ cal_block->cal_size =
+ atomic_read(&acdb_data.audproc_cal[path].cal_size);
done:
return;
}
@@ -257,12 +321,10 @@
{
pr_debug("%s, path = %d\n", __func__, path);
- mutex_lock(&acdb_data.acdb_mutex);
-
- if (cal_block->cal_offset > acdb_data.pmem_len) {
+ if (cal_block->cal_offset > atomic64_read(&acdb_data.pmem_len)) {
pr_err("%s: offset %d is > pmem_len %ld\n",
__func__, cal_block->cal_offset,
- acdb_data.pmem_len);
+ (long)atomic64_read(&acdb_data.pmem_len));
goto done;
}
if (path >= MAX_AUDPROC_TYPES) {
@@ -271,15 +333,13 @@
goto done;
}
- acdb_data.audstrm_cal[path].cal_kvaddr =
- cal_block->cal_offset + acdb_data.kvaddr;
- acdb_data.audstrm_cal[path].cal_paddr =
- cal_block->cal_offset + acdb_data.paddr;
- acdb_data.audstrm_cal[path].cal_size =
- cal_block->cal_size;
-
+ atomic_set(&acdb_data.audstrm_cal[path].cal_kvaddr,
+ cal_block->cal_offset + atomic64_read(&acdb_data.kvaddr));
+ atomic_set(&acdb_data.audstrm_cal[path].cal_paddr,
+ cal_block->cal_offset + atomic64_read(&acdb_data.paddr));
+ atomic_set(&acdb_data.audstrm_cal[path].cal_size,
+ cal_block->cal_size);
done:
- mutex_unlock(&acdb_data.acdb_mutex);
return;
}
@@ -297,13 +357,12 @@
goto done;
}
- mutex_lock(&acdb_data.acdb_mutex);
-
- cal_block->cal_kvaddr = acdb_data.audstrm_cal[path].cal_kvaddr;
- cal_block->cal_paddr = acdb_data.audstrm_cal[path].cal_paddr;
- cal_block->cal_size = acdb_data.audstrm_cal[path].cal_size;
-
- mutex_unlock(&acdb_data.acdb_mutex);
+ cal_block->cal_kvaddr =
+ atomic_read(&acdb_data.audstrm_cal[path].cal_kvaddr);
+ cal_block->cal_paddr =
+ atomic_read(&acdb_data.audstrm_cal[path].cal_paddr);
+ cal_block->cal_size =
+ atomic_read(&acdb_data.audstrm_cal[path].cal_size);
done:
return;
}
@@ -312,12 +371,10 @@
{
pr_debug("%s, path = %d\n", __func__, path);
- mutex_lock(&acdb_data.acdb_mutex);
-
- if (cal_block->cal_offset > acdb_data.pmem_len) {
+ if (cal_block->cal_offset > atomic64_read(&acdb_data.pmem_len)) {
pr_err("%s: offset %d is > pmem_len %ld\n",
__func__, cal_block->cal_offset,
- acdb_data.pmem_len);
+ (long)atomic64_read(&acdb_data.pmem_len));
goto done;
}
if (path >= MAX_AUDPROC_TYPES) {
@@ -326,15 +383,13 @@
goto done;
}
- acdb_data.audvol_cal[path].cal_kvaddr =
- cal_block->cal_offset + acdb_data.kvaddr;
- acdb_data.audvol_cal[path].cal_paddr =
- cal_block->cal_offset + acdb_data.paddr;
- acdb_data.audvol_cal[path].cal_size =
- cal_block->cal_size;
-
+ atomic_set(&acdb_data.audvol_cal[path].cal_kvaddr,
+ cal_block->cal_offset + atomic64_read(&acdb_data.kvaddr));
+ atomic_set(&acdb_data.audvol_cal[path].cal_paddr,
+ cal_block->cal_offset + atomic64_read(&acdb_data.paddr));
+ atomic_set(&acdb_data.audvol_cal[path].cal_size,
+ cal_block->cal_size);
done:
- mutex_unlock(&acdb_data.acdb_mutex);
return;
}
@@ -352,13 +407,12 @@
goto done;
}
- mutex_lock(&acdb_data.acdb_mutex);
-
- cal_block->cal_kvaddr = acdb_data.audvol_cal[path].cal_kvaddr;
- cal_block->cal_paddr = acdb_data.audvol_cal[path].cal_paddr;
- cal_block->cal_size = acdb_data.audvol_cal[path].cal_size;
-
- mutex_unlock(&acdb_data.acdb_mutex);
+ cal_block->cal_kvaddr =
+ atomic_read(&acdb_data.audvol_cal[path].cal_kvaddr);
+ cal_block->cal_paddr =
+ atomic_read(&acdb_data.audvol_cal[path].cal_paddr);
+ cal_block->cal_size =
+ atomic_read(&acdb_data.audvol_cal[path].cal_size);
done:
return;
}
@@ -375,31 +429,28 @@
goto done;
}
-
- mutex_lock(&acdb_data.acdb_mutex);
-
- acdb_data.vocproc_total_cal_size = 0;
+ atomic_set(&acdb_data.vocproc_total_cal_size, 0);
for (i = 0; i < len; i++) {
- if (cal_blocks[i].cal_offset > acdb_data.pmem_len) {
+ if (cal_blocks[i].cal_offset >
+ atomic64_read(&acdb_data.pmem_len)) {
pr_err("%s: offset %d is > pmem_len %ld\n",
__func__, cal_blocks[i].cal_offset,
- acdb_data.pmem_len);
- acdb_data.vocproc_cal[i].cal_size = 0;
+ (long)atomic64_read(&acdb_data.pmem_len));
+ atomic_set(&acdb_data.vocproc_cal[i].cal_size, 0);
} else {
- acdb_data.vocproc_total_cal_size +=
- cal_blocks[i].cal_size;
- acdb_data.vocproc_cal[i].cal_size =
- cal_blocks[i].cal_size;
- acdb_data.vocproc_cal[i].cal_paddr =
+ atomic_add(cal_blocks[i].cal_size,
+ &acdb_data.vocproc_total_cal_size);
+ atomic_set(&acdb_data.vocproc_cal[i].cal_size,
+ cal_blocks[i].cal_size);
+ atomic_set(&acdb_data.vocproc_cal[i].cal_paddr,
cal_blocks[i].cal_offset +
- acdb_data.paddr;
- acdb_data.vocproc_cal[i].cal_kvaddr =
+ atomic64_read(&acdb_data.paddr));
+ atomic_set(&acdb_data.vocproc_cal[i].cal_kvaddr,
cal_blocks[i].cal_offset +
- acdb_data.kvaddr;
+ atomic64_read(&acdb_data.kvaddr));
}
}
- acdb_data.vocproc_cal_size = len;
- mutex_unlock(&acdb_data.acdb_mutex);
+ atomic_set(&acdb_data.vocproc_cal_size, len);
done:
return;
}
@@ -413,12 +464,8 @@
goto done;
}
- mutex_lock(&acdb_data.acdb_mutex);
-
- cal_data->num_cal_blocks = acdb_data.vocproc_cal_size;
+ cal_data->num_cal_blocks = atomic_read(&acdb_data.vocproc_cal_size);
cal_data->cal_blocks = &acdb_data.vocproc_cal[0];
-
- mutex_unlock(&acdb_data.acdb_mutex);
done:
return;
}
@@ -434,30 +481,28 @@
goto done;
}
- mutex_lock(&acdb_data.acdb_mutex);
-
- acdb_data.vocstrm_total_cal_size = 0;
+ atomic_set(&acdb_data.vocstrm_total_cal_size, 0);
for (i = 0; i < len; i++) {
- if (cal_blocks[i].cal_offset > acdb_data.pmem_len) {
+ if (cal_blocks[i].cal_offset >
+ atomic64_read(&acdb_data.pmem_len)) {
pr_err("%s: offset %d is > pmem_len %ld\n",
__func__, cal_blocks[i].cal_offset,
- acdb_data.pmem_len);
- acdb_data.vocstrm_cal[i].cal_size = 0;
+ (long)atomic64_read(&acdb_data.pmem_len));
+ atomic_set(&acdb_data.vocstrm_cal[i].cal_size, 0);
} else {
- acdb_data.vocstrm_total_cal_size +=
- cal_blocks[i].cal_size;
- acdb_data.vocstrm_cal[i].cal_size =
- cal_blocks[i].cal_size;
- acdb_data.vocstrm_cal[i].cal_paddr =
+ atomic_add(cal_blocks[i].cal_size,
+ &acdb_data.vocstrm_total_cal_size);
+ atomic_set(&acdb_data.vocstrm_cal[i].cal_size,
+ cal_blocks[i].cal_size);
+ atomic_set(&acdb_data.vocstrm_cal[i].cal_paddr,
cal_blocks[i].cal_offset +
- acdb_data.paddr;
- acdb_data.vocstrm_cal[i].cal_kvaddr =
+ atomic64_read(&acdb_data.paddr));
+ atomic_set(&acdb_data.vocstrm_cal[i].cal_kvaddr,
cal_blocks[i].cal_offset +
- acdb_data.kvaddr;
+ atomic64_read(&acdb_data.kvaddr));
}
}
- acdb_data.vocstrm_cal_size = len;
- mutex_unlock(&acdb_data.acdb_mutex);
+ atomic_set(&acdb_data.vocstrm_cal_size, len);
done:
return;
}
@@ -471,12 +516,8 @@
goto done;
}
- mutex_lock(&acdb_data.acdb_mutex);
-
- cal_data->num_cal_blocks = acdb_data.vocstrm_cal_size;
+ cal_data->num_cal_blocks = atomic_read(&acdb_data.vocstrm_cal_size);
cal_data->cal_blocks = &acdb_data.vocstrm_cal[0];
-
- mutex_unlock(&acdb_data.acdb_mutex);
done:
return;
}
@@ -492,30 +533,28 @@
goto done;
}
- mutex_lock(&acdb_data.acdb_mutex);
-
- acdb_data.vocvol_total_cal_size = 0;
+ atomic_set(&acdb_data.vocvol_total_cal_size, 0);
for (i = 0; i < len; i++) {
- if (cal_blocks[i].cal_offset > acdb_data.pmem_len) {
+ if (cal_blocks[i].cal_offset >
+ atomic64_read(&acdb_data.pmem_len)) {
pr_err("%s: offset %d is > pmem_len %ld\n",
__func__, cal_blocks[i].cal_offset,
- acdb_data.pmem_len);
- acdb_data.vocvol_cal[i].cal_size = 0;
+ (long)atomic64_read(&acdb_data.pmem_len));
+ atomic_set(&acdb_data.vocvol_cal[i].cal_size, 0);
} else {
- acdb_data.vocvol_total_cal_size +=
- cal_blocks[i].cal_size;
- acdb_data.vocvol_cal[i].cal_size =
- cal_blocks[i].cal_size;
- acdb_data.vocvol_cal[i].cal_paddr =
+ atomic_add(cal_blocks[i].cal_size,
+ &acdb_data.vocvol_total_cal_size);
+ atomic_set(&acdb_data.vocvol_cal[i].cal_size,
+ cal_blocks[i].cal_size);
+ atomic_set(&acdb_data.vocvol_cal[i].cal_paddr,
cal_blocks[i].cal_offset +
- acdb_data.paddr;
- acdb_data.vocvol_cal[i].cal_kvaddr =
+ atomic64_read(&acdb_data.paddr));
+ atomic_set(&acdb_data.vocvol_cal[i].cal_kvaddr,
cal_blocks[i].cal_offset +
- acdb_data.kvaddr;
+ atomic64_read(&acdb_data.kvaddr));
}
}
- acdb_data.vocvol_cal_size = len;
- mutex_unlock(&acdb_data.acdb_mutex);
+ atomic_set(&acdb_data.vocvol_cal_size, len);
done:
return;
}
@@ -529,12 +568,8 @@
goto done;
}
- mutex_lock(&acdb_data.acdb_mutex);
-
- cal_data->num_cal_blocks = acdb_data.vocvol_cal_size;
+ cal_data->num_cal_blocks = atomic_read(&acdb_data.vocvol_cal_size);
cal_data->cal_blocks = &acdb_data.vocvol_cal[0];
-
- mutex_unlock(&acdb_data.acdb_mutex);
done:
return;
}
@@ -543,12 +578,8 @@
{
pr_debug("%s\n", __func__);
- mutex_lock(&acdb_data.acdb_mutex);
-
- acdb_data.sidetone_cal.enable = cal_data->enable;
- acdb_data.sidetone_cal.gain = cal_data->gain;
-
- mutex_unlock(&acdb_data.acdb_mutex);
+ atomic_set(&acdb_data.sidetone_cal.enable, cal_data->enable);
+ atomic_set(&acdb_data.sidetone_cal.gain, cal_data->gain);
}
@@ -561,12 +592,8 @@
goto done;
}
- mutex_lock(&acdb_data.acdb_mutex);
-
- cal_data->enable = acdb_data.sidetone_cal.enable;
- cal_data->gain = acdb_data.sidetone_cal.gain;
-
- mutex_unlock(&acdb_data.acdb_mutex);
+ cal_data->enable = atomic_read(&acdb_data.sidetone_cal.enable);
+ cal_data->gain = atomic_read(&acdb_data.sidetone_cal.gain);
done:
return;
}
@@ -574,14 +601,12 @@
static int acdb_open(struct inode *inode, struct file *f)
{
s32 result = 0;
- pr_info("%s\n", __func__);
+ pr_debug("%s\n", __func__);
- mutex_lock(&acdb_data.acdb_mutex);
- if (acdb_data.pmem_fd) {
- pr_info("%s: ACDB opened but PMEM allocated, using existing PMEM!\n",
+ if (atomic_read(&acdb_data.pmem_fd)) {
+ pr_debug("%s: ACDB opened but PMEM allocated, using existing PMEM!\n",
__func__);
}
- mutex_unlock(&acdb_data.acdb_mutex);
atomic_inc(&usage_count);
return result;
@@ -589,9 +614,11 @@
static int deregister_pmem(void)
{
- if (acdb_data.pmem_fd) {
+ if (atomic_read(&acdb_data.pmem_fd)) {
+ mutex_lock(&acdb_data.acdb_mutex);
put_pmem_file(acdb_data.file);
- acdb_data.pmem_fd = 0;
+ mutex_unlock(&acdb_data.acdb_mutex);
+ atomic_set(&acdb_data.pmem_fd, 0);
}
return 0;
}
@@ -599,19 +626,30 @@
static int register_pmem(void)
{
int result;
+ unsigned long paddr;
+ unsigned long kvaddr;
+ unsigned long pmem_len;
- result = get_pmem_file(acdb_data.pmem_fd, &acdb_data.paddr,
- &acdb_data.kvaddr, &acdb_data.pmem_len,
+ mutex_lock(&acdb_data.acdb_mutex);
+ result = get_pmem_file(atomic_read(&acdb_data.pmem_fd),
+ &paddr, &kvaddr, &pmem_len,
&acdb_data.file);
+ mutex_unlock(&acdb_data.acdb_mutex);
if (result != 0) {
- acdb_data.pmem_fd = 0;
+ atomic_set(&acdb_data.pmem_fd, 0);
+ atomic64_set(&acdb_data.pmem_len, 0);
pr_err("%s: Could not register PMEM!!!\n", __func__);
goto done;
}
+ atomic64_set(&acdb_data.paddr, paddr);
+ atomic64_set(&acdb_data.kvaddr, kvaddr);
+ atomic64_set(&acdb_data.pmem_len, pmem_len);
pr_debug("AUDIO_REGISTER_PMEM done! paddr = 0x%lx, "
- "kvaddr = 0x%lx, len = x%lx\n", acdb_data.paddr,
- acdb_data.kvaddr, acdb_data.pmem_len);
+ "kvaddr = 0x%lx, len = x%lx\n",
+ (long)atomic64_read(&acdb_data.paddr),
+ (long)atomic64_read(&acdb_data.kvaddr),
+ (long)atomic64_read(&acdb_data.pmem_len));
done:
return result;
@@ -619,37 +657,33 @@
static long acdb_ioctl(struct file *f,
unsigned int cmd, unsigned long arg)
{
- s32 result = 0;
- s32 audproc_path;
- s32 size;
- u32 topology;
+ int32_t result = 0;
+ int32_t size;
+ int32_t pmem_fd;
+ uint32_t topology;
struct cal_block data[MAX_NETWORKS];
pr_debug("%s\n", __func__);
switch (cmd) {
case AUDIO_REGISTER_PMEM:
pr_debug("AUDIO_REGISTER_PMEM\n");
- mutex_lock(&acdb_data.acdb_mutex);
- if (acdb_data.pmem_fd) {
+ if (atomic_read(&acdb_data.pmem_fd)) {
deregister_pmem();
- pr_info("Remove the existing PMEM\n");
+ pr_debug("Remove the existing PMEM\n");
}
- if (copy_from_user(&acdb_data.pmem_fd, (void *)arg,
- sizeof(acdb_data.pmem_fd))) {
+ if (copy_from_user(&pmem_fd, (void *)arg, sizeof(pmem_fd))) {
pr_err("%s: fail to copy pmem handle!\n", __func__);
result = -EFAULT;
} else {
+ atomic_set(&acdb_data.pmem_fd, pmem_fd);
result = register_pmem();
}
- mutex_unlock(&acdb_data.acdb_mutex);
goto done;
case AUDIO_DEREGISTER_PMEM:
pr_debug("AUDIO_DEREGISTER_PMEM\n");
- mutex_lock(&acdb_data.acdb_mutex);
deregister_pmem();
- mutex_unlock(&acdb_data.acdb_mutex);
goto done;
case AUDIO_SET_VOICE_RX_TOPOLOGY:
if (copy_from_user(&topology, (void *)arg,
@@ -721,45 +755,51 @@
switch (cmd) {
case AUDIO_SET_AUDPROC_TX_CAL:
- audproc_path = TX_CAL;
if (size > sizeof(struct cal_block))
pr_err("%s: More Audproc Cal then expected, "
"size received: %d\n", __func__, size);
- store_audproc_cal(audproc_path, data);
+ store_audproc_cal(TX_CAL, data);
break;
case AUDIO_SET_AUDPROC_RX_CAL:
- audproc_path = RX_CAL;
if (size > sizeof(struct cal_block))
pr_err("%s: More Audproc Cal then expected, "
"size received: %d\n", __func__, size);
- store_audproc_cal(audproc_path, data);
+ store_audproc_cal(RX_CAL, data);
break;
case AUDIO_SET_AUDPROC_TX_STREAM_CAL:
- audproc_path = TX_CAL;
if (size > sizeof(struct cal_block))
pr_err("%s: More Audproc Cal then expected, "
"size received: %d\n", __func__, size);
- store_audstrm_cal(audproc_path, data);
+ store_audstrm_cal(TX_CAL, data);
break;
case AUDIO_SET_AUDPROC_RX_STREAM_CAL:
- audproc_path = RX_CAL;
if (size > sizeof(struct cal_block))
pr_err("%s: More Audproc Cal then expected, "
"size received: %d\n", __func__, size);
- store_audstrm_cal(audproc_path, data);
+ store_audstrm_cal(RX_CAL, data);
break;
case AUDIO_SET_AUDPROC_TX_VOL_CAL:
- audproc_path = TX_CAL;
if (size > sizeof(struct cal_block))
pr_err("%s: More Audproc Cal then expected, "
"size received: %d\n", __func__, size);
- store_audvol_cal(audproc_path, data);
+ store_audvol_cal(TX_CAL, data);
case AUDIO_SET_AUDPROC_RX_VOL_CAL:
- audproc_path = RX_CAL;
if (size > sizeof(struct cal_block))
pr_err("%s: More Audproc Cal then expected, "
"size received: %d\n", __func__, size);
- store_audvol_cal(audproc_path, data);
+ store_audvol_cal(RX_CAL, data);
+ break;
+ case AUDIO_SET_AFE_TX_CAL:
+ if (size > sizeof(struct cal_block))
+ pr_err("%s: More AFE Cal then expected, "
+ "size received: %d\n", __func__, size);
+ store_afe_cal(TX_CAL, data);
+ break;
+ case AUDIO_SET_AFE_RX_CAL:
+ if (size > sizeof(struct cal_block))
+ pr_err("%s: More AFE Cal then expected, "
+ "size received: %d\n", __func__, size);
+ store_afe_cal(RX_CAL, data);
break;
case AUDIO_SET_VOCPROC_CAL:
store_vocproc_cal(size / sizeof(struct cal_block), data);
@@ -794,14 +834,13 @@
pr_debug("%s\n", __func__);
- mutex_lock(&acdb_data.acdb_mutex);
- if (acdb_data.pmem_fd) {
- if (size <= acdb_data.pmem_len) {
+ if (atomic_read(&acdb_data.pmem_fd)) {
+ if (size <= atomic64_read(&acdb_data.pmem_len)) {
vma->vm_page_prot = pgprot_noncached(
vma->vm_page_prot);
result = remap_pfn_range(vma,
vma->vm_start,
- acdb_data.paddr >> PAGE_SHIFT,
+ atomic64_read(&acdb_data.paddr) >> PAGE_SHIFT,
size,
vma->vm_page_prot);
} else {
@@ -812,7 +851,6 @@
pr_err("%s: PMEM is not allocated, yet!\n", __func__);
result = -ENODEV;
}
- mutex_unlock(&acdb_data.acdb_mutex);
return result;
}
@@ -824,16 +862,13 @@
atomic_dec(&usage_count);
atomic_read(&usage_count);
- pr_info("%s: ref count %d!\n", __func__,
+ pr_debug("%s: ref count %d!\n", __func__,
atomic_read(&usage_count));
- if (atomic_read(&usage_count) >= 1) {
+ if (atomic_read(&usage_count) >= 1)
result = -EBUSY;
- } else {
- mutex_lock(&acdb_data.acdb_mutex);
+ else
result = deregister_pmem();
- mutex_unlock(&acdb_data.acdb_mutex);
- }
return result;
}
diff --git a/arch/arm/mach-msm/qdsp6v2/q6voice.c b/arch/arm/mach-msm/qdsp6v2/q6voice.c
index 34169c0..12a02c5 100644
--- a/arch/arm/mach-msm/qdsp6v2/q6voice.c
+++ b/arch/arm/mach-msm/qdsp6v2/q6voice.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2011, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 and
@@ -791,7 +791,7 @@
struct apr_hdr cvs_cal_cmd_hdr;
uint32_t *cmd_buf;
struct acdb_cal_data cal_data;
- struct acdb_cal_block *cal_blk;
+ struct acdb_atomic_cal_block *cal_blk;
int32_t cal_size_per_network;
uint32_t *cal_data_per_network;
int index = 0;
@@ -830,11 +830,12 @@
pr_debug("cal_blk =%x\n", (uint32_t)cal_data.cal_blocks);
for (; index < cal_data.num_cal_blocks; index++) {
- cal_size_per_network = cal_blk[index].cal_size;
+ cal_size_per_network = atomic_read(&cal_blk[index].cal_size);
pr_debug(" cal size =%d\n", cal_size_per_network);
if (cal_size_per_network >= BUFFER_PAYLOAD_SIZE)
pr_err("Cal size is too big\n");
- cal_data_per_network = (u32 *)cal_blk[index].cal_kvaddr;
+ cal_data_per_network =
+ (u32 *)atomic_read(&cal_blk[index].cal_kvaddr);
pr_debug(" cal data=%x\n", (uint32_t)cal_data_per_network);
cvs_cal_cmd_hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
cal_size_per_network);
@@ -868,7 +869,7 @@
struct apr_hdr cvp_cal_cmd_hdr;
uint32_t *cmd_buf;
struct acdb_cal_data cal_data;
- struct acdb_cal_block *cal_blk;
+ struct acdb_atomic_cal_block *cal_blk;
int32_t cal_size_per_network;
uint32_t *cal_data_per_network;
int index = 0;
@@ -907,11 +908,12 @@
pr_debug(" cal_blk =%x\n", (uint32_t)cal_data.cal_blocks);
for (; index < cal_data.num_cal_blocks; index++) {
- cal_size_per_network = cal_blk[index].cal_size;
+ cal_size_per_network = atomic_read(&cal_blk[index].cal_size);
if (cal_size_per_network >= BUFFER_PAYLOAD_SIZE)
pr_err("Cal size is too big\n");
pr_debug(" cal size =%d\n", cal_size_per_network);
- cal_data_per_network = (u32 *)cal_blk[index].cal_kvaddr;
+ cal_data_per_network =
+ (u32 *)atomic_read(&cal_blk[index].cal_kvaddr);
pr_debug(" cal data=%x\n", (uint32_t)cal_data_per_network);
cvp_cal_cmd_hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
@@ -945,11 +947,9 @@
struct apr_hdr cvp_vol_cal_cmd_hdr;
uint32_t *cmd_buf;
struct acdb_cal_data cal_data;
- struct acdb_cal_block *cal_blk;
+ struct acdb_atomic_cal_block *cal_blk;
int32_t cal_size_per_network;
uint32_t *cal_data_per_network;
- uint32_t num_volume_steps;
- int offset = 0;
int index = 0;
int ret = 0;
void *apr_cvp = voice_get_apr_cvp();
@@ -986,27 +986,18 @@
pr_debug("Cal_blk =%x\n", (uint32_t)cal_data.cal_blocks);
for (; index < cal_data.num_cal_blocks; index++) {
- cal_size_per_network = cal_blk[index].cal_size;
- cal_data_per_network = (u32 *)cal_blk[index].cal_kvaddr;
-
- /* Number of volume steps are only included in the */
- /* first block, need to be inserted into the rest */
- if (index != 0) {
- offset = sizeof(num_volume_steps);
- memcpy(cmd_buf + (APR_HDR_SIZE / sizeof(uint32_t)),
- &num_volume_steps, offset);
- } else {
- num_volume_steps = *cal_data_per_network;
- }
+ cal_size_per_network = atomic_read(&cal_blk[index].cal_size);
+ cal_data_per_network =
+ (u32 *)atomic_read(&cal_blk[index].cal_kvaddr);
pr_debug("Cal size =%d, index=%d\n", cal_size_per_network,
index);
pr_debug("Cal data=%x\n", (uint32_t)cal_data_per_network);
cvp_vol_cal_cmd_hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
- cal_size_per_network + offset);
+ cal_size_per_network);
memcpy(cmd_buf, &cvp_vol_cal_cmd_hdr, APR_HDR_SIZE);
- memcpy(cmd_buf + (APR_HDR_SIZE / sizeof(uint32_t)) +
- offset, cal_data_per_network, cal_size_per_network);
+ memcpy(cmd_buf + (APR_HDR_SIZE / sizeof(uint32_t)),
+ cal_data_per_network, cal_size_per_network);
pr_debug("Send vol table\n");
v->cvp_state = CMD_STATUS_FAIL;
diff --git a/include/linux/msm_audio_acdb.h b/include/linux/msm_audio_acdb.h
index 3d756c2..e7f06b5 100644
--- a/include/linux/msm_audio_acdb.h
+++ b/include/linux/msm_audio_acdb.h
@@ -35,6 +35,13 @@
(AUDIO_MAX_COMMON_IOCTL_NUM+14), unsigned)
#define AUDIO_SET_ASM_TOPOLOGY _IOW(AUDIO_IOCTL_MAGIC, \
(AUDIO_MAX_COMMON_IOCTL_NUM+15), unsigned)
+#define AUDIO_SET_AFE_TX_CAL _IOW(AUDIO_IOCTL_MAGIC, \
+ (AUDIO_MAX_COMMON_IOCTL_NUM+16), unsigned)
+#define AUDIO_SET_AFE_RX_CAL _IOW(AUDIO_IOCTL_MAGIC, \
+ (AUDIO_MAX_COMMON_IOCTL_NUM+17), unsigned)
+
+
+#define AUDIO_MAX_ACDB_IOCTL (AUDIO_MAX_COMMON_IOCTL_NUM+30)
/* ACDB structures */
struct cal_block {
@@ -49,25 +56,26 @@
/* For Real-Time Audio Calibration */
#define AUDIO_GET_RTAC_ADM_INFO _IOR(AUDIO_IOCTL_MAGIC, \
- (AUDIO_MAX_COMMON_IOCTL_NUM+16), unsigned)
+ (AUDIO_MAX_ACDB_IOCTL+1), unsigned)
#define AUDIO_GET_RTAC_VOICE_INFO _IOR(AUDIO_IOCTL_MAGIC, \
- (AUDIO_MAX_COMMON_IOCTL_NUM+17), unsigned)
+ (AUDIO_MAX_ACDB_IOCTL+2), unsigned)
#define AUDIO_GET_RTAC_ADM_CAL _IOWR(AUDIO_IOCTL_MAGIC, \
- (AUDIO_MAX_COMMON_IOCTL_NUM+18), unsigned)
+ (AUDIO_MAX_ACDB_IOCTL+3), unsigned)
#define AUDIO_SET_RTAC_ADM_CAL _IOWR(AUDIO_IOCTL_MAGIC, \
- (AUDIO_MAX_COMMON_IOCTL_NUM+19), unsigned)
+ (AUDIO_MAX_ACDB_IOCTL+4), unsigned)
#define AUDIO_GET_RTAC_ASM_CAL _IOWR(AUDIO_IOCTL_MAGIC, \
- (AUDIO_MAX_COMMON_IOCTL_NUM+20), unsigned)
+ (AUDIO_MAX_ACDB_IOCTL+5), unsigned)
#define AUDIO_SET_RTAC_ASM_CAL _IOWR(AUDIO_IOCTL_MAGIC, \
- (AUDIO_MAX_COMMON_IOCTL_NUM+21), unsigned)
+ (AUDIO_MAX_ACDB_IOCTL+6), unsigned)
#define AUDIO_GET_RTAC_CVS_CAL _IOWR(AUDIO_IOCTL_MAGIC, \
- (AUDIO_MAX_COMMON_IOCTL_NUM+22), unsigned)
+ (AUDIO_MAX_ACDB_IOCTL+7), unsigned)
#define AUDIO_SET_RTAC_CVS_CAL _IOWR(AUDIO_IOCTL_MAGIC, \
- (AUDIO_MAX_COMMON_IOCTL_NUM+23), unsigned)
+ (AUDIO_MAX_ACDB_IOCTL+8), unsigned)
#define AUDIO_GET_RTAC_CVP_CAL _IOWR(AUDIO_IOCTL_MAGIC, \
- (AUDIO_MAX_COMMON_IOCTL_NUM+24), unsigned)
+ (AUDIO_MAX_ACDB_IOCTL+9), unsigned)
#define AUDIO_SET_RTAC_CVP_CAL _IOWR(AUDIO_IOCTL_MAGIC, \
- (AUDIO_MAX_COMMON_IOCTL_NUM+25), unsigned)
+ (AUDIO_MAX_ACDB_IOCTL+10), unsigned)
+#define AUDIO_MAX_RTAC_IOCTL (AUDIO_MAX_ACDB_IOCTL+20)
#endif /* __MSM_AUDIO_ACDB_H */
diff --git a/include/sound/apr_audio.h b/include/sound/apr_audio.h
index 798ed89..30f1a7c 100644
--- a/include/sound/apr_audio.h
+++ b/include/sound/apr_audio.h
@@ -1,7 +1,6 @@
-
/*
*
- * Copyright (c) 2010-2011, Code Aurora Forum. All rights reserved.
+ * Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 and
@@ -353,6 +352,12 @@
struct afe_param_payload payload;
} __attribute__ ((packed));
+struct afe_port_cmd_set_param_no_payload {
+ struct apr_hdr hdr;
+ u16 port_id;
+ u16 payload_size;
+ u32 payload_address;
+} __packed;
#define AFE_EVENT_GET_ACTIVE_PORTS 0x00010100
struct afe_get_active_ports_rsp {
diff --git a/include/sound/q6afe.h b/include/sound/q6afe.h
index 6206838..2d0f53f 100644
--- a/include/sound/q6afe.h
+++ b/include/sound/q6afe.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2011, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 and
@@ -76,7 +76,9 @@
int afe_start_pseudo_port(u16 port_id);
int afe_stop_pseudo_port(u16 port_id);
int afe_cmd_memory_map(u32 dma_addr_p, u32 dma_buf_sz);
+int afe_cmd_memory_map_nowait(u32 dma_addr_p, u32 dma_buf_sz);
int afe_cmd_memory_unmap(u32 dma_addr_p);
+int afe_cmd_memory_unmap_nowait(u32 dma_addr_p);
int afe_register_get_events(u16 port_id,
void (*cb) (uint32_t opcode,
diff --git a/sound/soc/msm/qdsp6/q6adm.c b/sound/soc/msm/qdsp6/q6adm.c
index 18dfc01..d8d9c64 100644
--- a/sound/soc/msm/qdsp6/q6adm.c
+++ b/sound/soc/msm/qdsp6/q6adm.c
@@ -457,7 +457,7 @@
int i = 0;
int cmd_size = 0;
- pr_info("%s\n", __func__);
+ pr_debug("%s\n", __func__);
if (this_adm.apr == NULL) {
this_adm.apr = apr_register("ADSP", "ADM", adm_callback,
0xFFFFFFFF, &this_adm);
@@ -532,7 +532,7 @@
int i = 0;
int cmd_size = 0;
- pr_info("%s\n", __func__);
+ pr_debug("%s\n", __func__);
if (this_adm.apr == NULL) {
pr_err("%s APR handle NULL\n", __func__);
diff --git a/sound/soc/msm/qdsp6/q6afe.c b/sound/soc/msm/qdsp6/q6afe.c
index 74a66945..a214529 100644
--- a/sound/soc/msm/qdsp6/q6afe.c
+++ b/sound/soc/msm/qdsp6/q6afe.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2011, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 and
@@ -17,6 +17,7 @@
#include <linux/wait.h>
#include <linux/jiffies.h>
#include <linux/sched.h>
+#include <mach/qdsp6v2/audio_acdb.h>
#include <sound/apr_audio.h>
#include <sound/q6afe.h>
@@ -36,6 +37,8 @@
static struct afe_ctl this_afe;
+static uint32_t afe_cal_addr[MAX_AUDPROC_TYPES];
+
#define TIMEOUT_MS 1000
#define Q6AFE_MAX_VOLUME 0x3FFF
@@ -314,6 +317,63 @@
return ret;
}
+static void afe_send_cal_block(int32_t path, u16 port_id)
+{
+ int result = 0;
+ struct acdb_cal_block cal_block;
+ struct afe_port_cmd_set_param_no_payload afe_cal;
+ pr_debug("%s: path %d\n", __func__, path);
+
+ get_afe_cal(path, &cal_block);
+ if (cal_block.cal_size <= 0) {
+ pr_debug("%s: No AFE cal to send!\n", __func__);
+ goto done;
+ }
+
+ if (afe_cal_addr[path] != cal_block.cal_paddr) {
+ if (afe_cal_addr[path] != 0)
+ afe_cmd_memory_unmap_nowait(afe_cal_addr[path]);
+ afe_cmd_memory_map_nowait(cal_block.cal_paddr,
+ cal_block.cal_size);
+ afe_cal_addr[path] = cal_block.cal_paddr;
+ }
+
+ afe_cal.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
+ APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
+ afe_cal.hdr.pkt_size = sizeof(afe_cal);
+ afe_cal.hdr.src_port = 0;
+ afe_cal.hdr.dest_port = 0;
+ afe_cal.hdr.token = 0;
+ afe_cal.hdr.opcode = AFE_PORT_CMD_SET_PARAM;
+ afe_cal.port_id = port_id;
+ afe_cal.payload_size = cal_block.cal_size;
+ afe_cal.payload_address = cal_block.cal_paddr;
+
+ pr_debug("%s: AFE cal sent for device port = %d, path = %d, "
+ "cal size = %d, cal addr = 0x%x\n", __func__,
+ port_id, path, cal_block.cal_size, cal_block.cal_paddr);
+
+ result = apr_send_pkt(this_afe.apr, (uint32_t *) &afe_cal);
+ if (result < 0) {
+ pr_err("%s: AFE cal for port %d failed\n",
+ __func__, port_id);
+ }
+
+ pr_debug("%s: AFE cal sent for path %d device!\n", __func__, path);
+done:
+ return;
+}
+
+void afe_send_cal(u16 port_id)
+{
+ pr_debug("%s\n", __func__);
+
+ if (afe_get_port_type(port_id) == MSM_AFE_PORT_TYPE_TX)
+ afe_send_cal_block(TX_CAL, port_id);
+ else if (afe_get_port_type(port_id) == MSM_AFE_PORT_TYPE_RX)
+ afe_send_cal_block(RX_CAL, port_id);
+}
+
int afe_port_start_nowait(u16 port_id, union afe_port_config *afe_config,
u32 rate) /* This function is no blocking */
{
@@ -365,6 +425,10 @@
ret = -EINVAL;
goto fail_cmd;
}
+
+ /* send AFE cal */
+ afe_send_cal(port_id);
+
start.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
start.hdr.pkt_size = sizeof(start);
@@ -875,6 +939,45 @@
return 0;
}
+int afe_cmd_memory_map_nowait(u32 dma_addr_p, u32 dma_buf_sz)
+{
+ int ret = 0;
+ struct afe_cmd_memory_map mregion;
+
+ pr_debug("%s:\n", __func__);
+
+ if (this_afe.apr == NULL) {
+ this_afe.apr = apr_register("ADSP", "AFE", afe_callback,
+ 0xFFFFFFFF, &this_afe);
+ pr_debug("%s: Register AFE\n", __func__);
+ if (this_afe.apr == NULL) {
+ pr_err("%s: Unable to register AFE\n", __func__);
+ ret = -ENODEV;
+ return ret;
+ }
+ }
+
+ mregion.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
+ APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
+ mregion.hdr.pkt_size = sizeof(mregion);
+ mregion.hdr.src_port = 0;
+ mregion.hdr.dest_port = 0;
+ mregion.hdr.token = 0;
+ mregion.hdr.opcode = AFE_SERVICE_CMD_MEMORY_MAP;
+ mregion.phy_addr = dma_addr_p;
+ mregion.mem_sz = dma_buf_sz;
+ mregion.mem_id = 0;
+ mregion.rsvd = 0;
+
+ ret = apr_send_pkt(this_afe.apr, (uint32_t *) &mregion);
+ if (ret < 0) {
+ pr_err("%s: AFE memory map cmd failed %d\n",
+ __func__, ret);
+ ret = -EINVAL;
+ }
+ return 0;
+}
+
int afe_cmd_memory_unmap(u32 dma_addr_p)
{
int ret = 0;
@@ -905,7 +1008,7 @@
atomic_set(&this_afe.state, 1);
ret = apr_send_pkt(this_afe.apr, (uint32_t *) &mregion);
if (ret < 0) {
- pr_err("%s: AFE memory map cmd failed %d\n",
+ pr_err("%s: AFE memory unmap cmd failed %d\n",
__func__, ret);
ret = -EINVAL;
return ret;
@@ -919,7 +1022,42 @@
ret = -EINVAL;
return ret;
}
+ return 0;
+}
+int afe_cmd_memory_unmap_nowait(u32 dma_addr_p)
+{
+ int ret = 0;
+ struct afe_cmd_memory_unmap mregion;
+
+ pr_debug("%s:\n", __func__);
+
+ if (this_afe.apr == NULL) {
+ this_afe.apr = apr_register("ADSP", "AFE", afe_callback,
+ 0xFFFFFFFF, &this_afe);
+ pr_debug("%s: Register AFE\n", __func__);
+ if (this_afe.apr == NULL) {
+ pr_err("%s: Unable to register AFE\n", __func__);
+ ret = -ENODEV;
+ return ret;
+ }
+ }
+
+ mregion.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
+ APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
+ mregion.hdr.pkt_size = sizeof(mregion);
+ mregion.hdr.src_port = 0;
+ mregion.hdr.dest_port = 0;
+ mregion.hdr.token = 0;
+ mregion.hdr.opcode = AFE_SERVICE_CMD_MEMORY_UNMAP;
+ mregion.phy_addr = dma_addr_p;
+
+ ret = apr_send_pkt(this_afe.apr, (uint32_t *) &mregion);
+ if (ret < 0) {
+ pr_err("%s: AFE memory unmap cmd failed %d\n",
+ __func__, ret);
+ ret = -EINVAL;
+ }
return 0;
}
@@ -1389,12 +1527,17 @@
static void __exit afe_exit(void)
{
+ int i;
#ifdef CONFIG_DEBUG_FS
if (debugfs_afelb)
debugfs_remove(debugfs_afelb);
if (debugfs_afelb_gain)
debugfs_remove(debugfs_afelb_gain);
#endif
+ for (i = 0; i < MAX_AUDPROC_TYPES; i++) {
+ if (afe_cal_addr[i] != 0)
+ afe_cmd_memory_unmap_nowait(afe_cal_addr[i]);
+ }
}
device_initcall(afe_init);