Merge d2a6844be5
("ASoC: meson: spdifin: start hw on dai probe") into android11-5.4-lts
Steps on the way to 5.4.258 Change-Id: I85f1c8953f850461246d7be38934a6c11e7137fa Signed-off-by: Greg Kroah-Hartman <gregkh@google.com>
This commit is contained in:
commit
d8ca210978
@ -1199,6 +1199,26 @@ static ssize_t ahci_activity_show(struct ata_device *dev, char *buf)
|
|||||||
return sprintf(buf, "%d\n", emp->blink_policy);
|
return sprintf(buf, "%d\n", emp->blink_policy);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void ahci_port_clear_pending_irq(struct ata_port *ap)
|
||||||
|
{
|
||||||
|
struct ahci_host_priv *hpriv = ap->host->private_data;
|
||||||
|
void __iomem *port_mmio = ahci_port_base(ap);
|
||||||
|
u32 tmp;
|
||||||
|
|
||||||
|
/* clear SError */
|
||||||
|
tmp = readl(port_mmio + PORT_SCR_ERR);
|
||||||
|
dev_dbg(ap->host->dev, "PORT_SCR_ERR 0x%x\n", tmp);
|
||||||
|
writel(tmp, port_mmio + PORT_SCR_ERR);
|
||||||
|
|
||||||
|
/* clear port IRQ */
|
||||||
|
tmp = readl(port_mmio + PORT_IRQ_STAT);
|
||||||
|
dev_dbg(ap->host->dev, "PORT_IRQ_STAT 0x%x\n", tmp);
|
||||||
|
if (tmp)
|
||||||
|
writel(tmp, port_mmio + PORT_IRQ_STAT);
|
||||||
|
|
||||||
|
writel(1 << ap->port_no, hpriv->mmio + HOST_IRQ_STAT);
|
||||||
|
}
|
||||||
|
|
||||||
static void ahci_port_init(struct device *dev, struct ata_port *ap,
|
static void ahci_port_init(struct device *dev, struct ata_port *ap,
|
||||||
int port_no, void __iomem *mmio,
|
int port_no, void __iomem *mmio,
|
||||||
void __iomem *port_mmio)
|
void __iomem *port_mmio)
|
||||||
@ -1213,18 +1233,7 @@ static void ahci_port_init(struct device *dev, struct ata_port *ap,
|
|||||||
if (rc)
|
if (rc)
|
||||||
dev_warn(dev, "%s (%d)\n", emsg, rc);
|
dev_warn(dev, "%s (%d)\n", emsg, rc);
|
||||||
|
|
||||||
/* clear SError */
|
ahci_port_clear_pending_irq(ap);
|
||||||
tmp = readl(port_mmio + PORT_SCR_ERR);
|
|
||||||
VPRINTK("PORT_SCR_ERR 0x%x\n", tmp);
|
|
||||||
writel(tmp, port_mmio + PORT_SCR_ERR);
|
|
||||||
|
|
||||||
/* clear port IRQ */
|
|
||||||
tmp = readl(port_mmio + PORT_IRQ_STAT);
|
|
||||||
VPRINTK("PORT_IRQ_STAT 0x%x\n", tmp);
|
|
||||||
if (tmp)
|
|
||||||
writel(tmp, port_mmio + PORT_IRQ_STAT);
|
|
||||||
|
|
||||||
writel(1 << port_no, mmio + HOST_IRQ_STAT);
|
|
||||||
|
|
||||||
/* mark esata ports */
|
/* mark esata ports */
|
||||||
tmp = readl(port_mmio + PORT_CMD);
|
tmp = readl(port_mmio + PORT_CMD);
|
||||||
@ -1554,6 +1563,8 @@ int ahci_do_hardreset(struct ata_link *link, unsigned int *class,
|
|||||||
tf.command = ATA_BUSY;
|
tf.command = ATA_BUSY;
|
||||||
ata_tf_to_fis(&tf, 0, 0, d2h_fis);
|
ata_tf_to_fis(&tf, 0, 0, d2h_fis);
|
||||||
|
|
||||||
|
ahci_port_clear_pending_irq(ap);
|
||||||
|
|
||||||
rc = sata_link_hardreset(link, timing, deadline, online,
|
rc = sata_link_hardreset(link, timing, deadline, online,
|
||||||
ahci_check_ready);
|
ahci_check_ready);
|
||||||
|
|
||||||
|
@ -1517,7 +1517,7 @@ struct ext4_sb_info {
|
|||||||
struct task_struct *s_mmp_tsk;
|
struct task_struct *s_mmp_tsk;
|
||||||
|
|
||||||
/* record the last minlen when FITRIM is called. */
|
/* record the last minlen when FITRIM is called. */
|
||||||
atomic_t s_last_trim_minblks;
|
unsigned long s_last_trim_minblks;
|
||||||
|
|
||||||
/* Reference to checksum algorithm driver via cryptoapi */
|
/* Reference to checksum algorithm driver via cryptoapi */
|
||||||
struct crypto_shash *s_chksum_driver;
|
struct crypto_shash *s_chksum_driver;
|
||||||
|
@ -16,6 +16,7 @@
|
|||||||
#include <linux/slab.h>
|
#include <linux/slab.h>
|
||||||
#include <linux/nospec.h>
|
#include <linux/nospec.h>
|
||||||
#include <linux/backing-dev.h>
|
#include <linux/backing-dev.h>
|
||||||
|
#include <linux/freezer.h>
|
||||||
#include <trace/events/ext4.h>
|
#include <trace/events/ext4.h>
|
||||||
|
|
||||||
#ifdef CONFIG_EXT4_DEBUG
|
#ifdef CONFIG_EXT4_DEBUG
|
||||||
@ -5159,19 +5160,19 @@ error_return:
|
|||||||
* @sb: super block for the file system
|
* @sb: super block for the file system
|
||||||
* @start: starting block of the free extent in the alloc. group
|
* @start: starting block of the free extent in the alloc. group
|
||||||
* @count: number of blocks to TRIM
|
* @count: number of blocks to TRIM
|
||||||
* @group: alloc. group we are working with
|
|
||||||
* @e4b: ext4 buddy for the group
|
* @e4b: ext4 buddy for the group
|
||||||
*
|
*
|
||||||
* Trim "count" blocks starting at "start" in the "group". To assure that no
|
* Trim "count" blocks starting at "start" in the "group". To assure that no
|
||||||
* one will allocate those blocks, mark it as used in buddy bitmap. This must
|
* one will allocate those blocks, mark it as used in buddy bitmap. This must
|
||||||
* be called with under the group lock.
|
* be called with under the group lock.
|
||||||
*/
|
*/
|
||||||
static int ext4_trim_extent(struct super_block *sb, int start, int count,
|
static int ext4_trim_extent(struct super_block *sb,
|
||||||
ext4_group_t group, struct ext4_buddy *e4b)
|
int start, int count, struct ext4_buddy *e4b)
|
||||||
__releases(bitlock)
|
__releases(bitlock)
|
||||||
__acquires(bitlock)
|
__acquires(bitlock)
|
||||||
{
|
{
|
||||||
struct ext4_free_extent ex;
|
struct ext4_free_extent ex;
|
||||||
|
ext4_group_t group = e4b->bd_group;
|
||||||
int ret = 0;
|
int ret = 0;
|
||||||
|
|
||||||
trace_ext4_trim_extent(sb, group, start, count);
|
trace_ext4_trim_extent(sb, group, start, count);
|
||||||
@ -5194,6 +5195,71 @@ __acquires(bitlock)
|
|||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static ext4_grpblk_t ext4_last_grp_cluster(struct super_block *sb,
|
||||||
|
ext4_group_t grp)
|
||||||
|
{
|
||||||
|
if (grp < ext4_get_groups_count(sb))
|
||||||
|
return EXT4_CLUSTERS_PER_GROUP(sb) - 1;
|
||||||
|
return (ext4_blocks_count(EXT4_SB(sb)->s_es) -
|
||||||
|
ext4_group_first_block_no(sb, grp) - 1) >>
|
||||||
|
EXT4_CLUSTER_BITS(sb);
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool ext4_trim_interrupted(void)
|
||||||
|
{
|
||||||
|
return fatal_signal_pending(current) || freezing(current);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int ext4_try_to_trim_range(struct super_block *sb,
|
||||||
|
struct ext4_buddy *e4b, ext4_grpblk_t start,
|
||||||
|
ext4_grpblk_t max, ext4_grpblk_t minblocks)
|
||||||
|
{
|
||||||
|
ext4_grpblk_t next, count, free_count;
|
||||||
|
bool set_trimmed = false;
|
||||||
|
void *bitmap;
|
||||||
|
|
||||||
|
bitmap = e4b->bd_bitmap;
|
||||||
|
if (start == 0 && max >= ext4_last_grp_cluster(sb, e4b->bd_group))
|
||||||
|
set_trimmed = true;
|
||||||
|
start = max(e4b->bd_info->bb_first_free, start);
|
||||||
|
count = 0;
|
||||||
|
free_count = 0;
|
||||||
|
|
||||||
|
while (start <= max) {
|
||||||
|
start = mb_find_next_zero_bit(bitmap, max + 1, start);
|
||||||
|
if (start > max)
|
||||||
|
break;
|
||||||
|
next = mb_find_next_bit(bitmap, max + 1, start);
|
||||||
|
|
||||||
|
if ((next - start) >= minblocks) {
|
||||||
|
int ret = ext4_trim_extent(sb, start, next - start, e4b);
|
||||||
|
|
||||||
|
if (ret && ret != -EOPNOTSUPP)
|
||||||
|
return count;
|
||||||
|
count += next - start;
|
||||||
|
}
|
||||||
|
free_count += next - start;
|
||||||
|
start = next + 1;
|
||||||
|
|
||||||
|
if (ext4_trim_interrupted())
|
||||||
|
return count;
|
||||||
|
|
||||||
|
if (need_resched()) {
|
||||||
|
ext4_unlock_group(sb, e4b->bd_group);
|
||||||
|
cond_resched();
|
||||||
|
ext4_lock_group(sb, e4b->bd_group);
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((e4b->bd_info->bb_free - free_count) < minblocks)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (set_trimmed)
|
||||||
|
EXT4_MB_GRP_SET_TRIMMED(e4b->bd_info);
|
||||||
|
|
||||||
|
return count;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* ext4_trim_all_free -- function to trim all free space in alloc. group
|
* ext4_trim_all_free -- function to trim all free space in alloc. group
|
||||||
* @sb: super block for file system
|
* @sb: super block for file system
|
||||||
@ -5217,10 +5283,8 @@ ext4_trim_all_free(struct super_block *sb, ext4_group_t group,
|
|||||||
ext4_grpblk_t start, ext4_grpblk_t max,
|
ext4_grpblk_t start, ext4_grpblk_t max,
|
||||||
ext4_grpblk_t minblocks)
|
ext4_grpblk_t minblocks)
|
||||||
{
|
{
|
||||||
void *bitmap;
|
|
||||||
ext4_grpblk_t next, count = 0, free_count = 0;
|
|
||||||
struct ext4_buddy e4b;
|
struct ext4_buddy e4b;
|
||||||
int ret = 0;
|
int ret;
|
||||||
|
|
||||||
trace_ext4_trim_all_free(sb, group, start, max);
|
trace_ext4_trim_all_free(sb, group, start, max);
|
||||||
|
|
||||||
@ -5230,58 +5294,20 @@ ext4_trim_all_free(struct super_block *sb, ext4_group_t group,
|
|||||||
ret, group);
|
ret, group);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
bitmap = e4b.bd_bitmap;
|
|
||||||
|
|
||||||
ext4_lock_group(sb, group);
|
ext4_lock_group(sb, group);
|
||||||
if (EXT4_MB_GRP_WAS_TRIMMED(e4b.bd_info) &&
|
|
||||||
minblocks >= atomic_read(&EXT4_SB(sb)->s_last_trim_minblks))
|
|
||||||
goto out;
|
|
||||||
|
|
||||||
start = (e4b.bd_info->bb_first_free > start) ?
|
if (!EXT4_MB_GRP_WAS_TRIMMED(e4b.bd_info) ||
|
||||||
e4b.bd_info->bb_first_free : start;
|
minblocks < EXT4_SB(sb)->s_last_trim_minblks)
|
||||||
|
ret = ext4_try_to_trim_range(sb, &e4b, start, max, minblocks);
|
||||||
|
else
|
||||||
|
ret = 0;
|
||||||
|
|
||||||
while (start <= max) {
|
|
||||||
start = mb_find_next_zero_bit(bitmap, max + 1, start);
|
|
||||||
if (start > max)
|
|
||||||
break;
|
|
||||||
next = mb_find_next_bit(bitmap, max + 1, start);
|
|
||||||
|
|
||||||
if ((next - start) >= minblocks) {
|
|
||||||
ret = ext4_trim_extent(sb, start,
|
|
||||||
next - start, group, &e4b);
|
|
||||||
if (ret && ret != -EOPNOTSUPP)
|
|
||||||
break;
|
|
||||||
ret = 0;
|
|
||||||
count += next - start;
|
|
||||||
}
|
|
||||||
free_count += next - start;
|
|
||||||
start = next + 1;
|
|
||||||
|
|
||||||
if (fatal_signal_pending(current)) {
|
|
||||||
count = -ERESTARTSYS;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (need_resched()) {
|
|
||||||
ext4_unlock_group(sb, group);
|
|
||||||
cond_resched();
|
|
||||||
ext4_lock_group(sb, group);
|
|
||||||
}
|
|
||||||
|
|
||||||
if ((e4b.bd_info->bb_free - free_count) < minblocks)
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!ret) {
|
|
||||||
ret = count;
|
|
||||||
EXT4_MB_GRP_SET_TRIMMED(e4b.bd_info);
|
|
||||||
}
|
|
||||||
out:
|
|
||||||
ext4_unlock_group(sb, group);
|
ext4_unlock_group(sb, group);
|
||||||
ext4_mb_unload_buddy(&e4b);
|
ext4_mb_unload_buddy(&e4b);
|
||||||
|
|
||||||
ext4_debug("trimmed %d blocks in the group %d\n",
|
ext4_debug("trimmed %d blocks in the group %d\n",
|
||||||
count, group);
|
ret, group);
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
@ -5326,7 +5352,7 @@ int ext4_trim_fs(struct super_block *sb, struct fstrim_range *range)
|
|||||||
if (minlen > EXT4_CLUSTERS_PER_GROUP(sb))
|
if (minlen > EXT4_CLUSTERS_PER_GROUP(sb))
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
if (end >= max_blks)
|
if (end >= max_blks - 1)
|
||||||
end = max_blks - 1;
|
end = max_blks - 1;
|
||||||
if (end <= first_data_blk)
|
if (end <= first_data_blk)
|
||||||
goto out;
|
goto out;
|
||||||
@ -5343,6 +5369,8 @@ int ext4_trim_fs(struct super_block *sb, struct fstrim_range *range)
|
|||||||
end = EXT4_CLUSTERS_PER_GROUP(sb) - 1;
|
end = EXT4_CLUSTERS_PER_GROUP(sb) - 1;
|
||||||
|
|
||||||
for (group = first_group; group <= last_group; group++) {
|
for (group = first_group; group <= last_group; group++) {
|
||||||
|
if (ext4_trim_interrupted())
|
||||||
|
break;
|
||||||
grp = ext4_get_group_info(sb, group);
|
grp = ext4_get_group_info(sb, group);
|
||||||
/* We only do this if the grp has never been initialized */
|
/* We only do this if the grp has never been initialized */
|
||||||
if (unlikely(EXT4_MB_GRP_NEED_INIT(grp))) {
|
if (unlikely(EXT4_MB_GRP_NEED_INIT(grp))) {
|
||||||
@ -5359,10 +5387,9 @@ int ext4_trim_fs(struct super_block *sb, struct fstrim_range *range)
|
|||||||
*/
|
*/
|
||||||
if (group == last_group)
|
if (group == last_group)
|
||||||
end = last_cluster;
|
end = last_cluster;
|
||||||
|
|
||||||
if (grp->bb_free >= minlen) {
|
if (grp->bb_free >= minlen) {
|
||||||
cnt = ext4_trim_all_free(sb, group, first_cluster,
|
cnt = ext4_trim_all_free(sb, group, first_cluster,
|
||||||
end, minlen);
|
end, minlen);
|
||||||
if (cnt < 0) {
|
if (cnt < 0) {
|
||||||
ret = cnt;
|
ret = cnt;
|
||||||
break;
|
break;
|
||||||
@ -5378,7 +5405,7 @@ int ext4_trim_fs(struct super_block *sb, struct fstrim_range *range)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!ret)
|
if (!ret)
|
||||||
atomic_set(&EXT4_SB(sb)->s_last_trim_minblks, minlen);
|
EXT4_SB(sb)->s_last_trim_minblks = minlen;
|
||||||
|
|
||||||
out:
|
out:
|
||||||
range->len = EXT4_C2B(EXT4_SB(sb), trimmed) << sb->s_blocksize_bits;
|
range->len = EXT4_C2B(EXT4_SB(sb), trimmed) << sb->s_blocksize_bits;
|
||||||
@ -5407,8 +5434,7 @@ ext4_mballoc_query_range(
|
|||||||
|
|
||||||
ext4_lock_group(sb, group);
|
ext4_lock_group(sb, group);
|
||||||
|
|
||||||
start = (e4b.bd_info->bb_first_free > start) ?
|
start = max(e4b.bd_info->bb_first_free, start);
|
||||||
e4b.bd_info->bb_first_free : start;
|
|
||||||
if (end >= EXT4_CLUSTERS_PER_GROUP(sb))
|
if (end >= EXT4_CLUSTERS_PER_GROUP(sb))
|
||||||
end = EXT4_CLUSTERS_PER_GROUP(sb) - 1;
|
end = EXT4_CLUSTERS_PER_GROUP(sb) - 1;
|
||||||
|
|
||||||
|
@ -1280,6 +1280,7 @@ static void ff_layout_io_track_ds_error(struct pnfs_layout_segment *lseg,
|
|||||||
case -EPFNOSUPPORT:
|
case -EPFNOSUPPORT:
|
||||||
case -EPROTONOSUPPORT:
|
case -EPROTONOSUPPORT:
|
||||||
case -EOPNOTSUPP:
|
case -EOPNOTSUPP:
|
||||||
|
case -EINVAL:
|
||||||
case -ECONNREFUSED:
|
case -ECONNREFUSED:
|
||||||
case -ECONNRESET:
|
case -ECONNRESET:
|
||||||
case -EHOSTDOWN:
|
case -EHOSTDOWN:
|
||||||
|
@ -4244,6 +4244,33 @@ int tracing_open_generic_tr(struct inode *inode, struct file *filp)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* The private pointer of the inode is the trace_event_file.
|
||||||
|
* Update the tr ref count associated to it.
|
||||||
|
*/
|
||||||
|
int tracing_open_file_tr(struct inode *inode, struct file *filp)
|
||||||
|
{
|
||||||
|
struct trace_event_file *file = inode->i_private;
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
ret = tracing_check_open_get_tr(file->tr);
|
||||||
|
if (ret)
|
||||||
|
return ret;
|
||||||
|
|
||||||
|
filp->private_data = inode->i_private;
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int tracing_release_file_tr(struct inode *inode, struct file *filp)
|
||||||
|
{
|
||||||
|
struct trace_event_file *file = inode->i_private;
|
||||||
|
|
||||||
|
trace_array_put(file->tr);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
static int tracing_release(struct inode *inode, struct file *file)
|
static int tracing_release(struct inode *inode, struct file *file)
|
||||||
{
|
{
|
||||||
struct trace_array *tr = inode->i_private;
|
struct trace_array *tr = inode->i_private;
|
||||||
|
@ -680,6 +680,8 @@ void tracing_reset_all_online_cpus(void);
|
|||||||
void tracing_reset_all_online_cpus_unlocked(void);
|
void tracing_reset_all_online_cpus_unlocked(void);
|
||||||
int tracing_open_generic(struct inode *inode, struct file *filp);
|
int tracing_open_generic(struct inode *inode, struct file *filp);
|
||||||
int tracing_open_generic_tr(struct inode *inode, struct file *filp);
|
int tracing_open_generic_tr(struct inode *inode, struct file *filp);
|
||||||
|
int tracing_open_file_tr(struct inode *inode, struct file *filp);
|
||||||
|
int tracing_release_file_tr(struct inode *inode, struct file *filp);
|
||||||
bool tracing_is_disabled(void);
|
bool tracing_is_disabled(void);
|
||||||
bool tracer_tracing_is_on(struct trace_array *tr);
|
bool tracer_tracing_is_on(struct trace_array *tr);
|
||||||
void tracer_tracing_on(struct trace_array *tr);
|
void tracer_tracing_on(struct trace_array *tr);
|
||||||
|
@ -1699,9 +1699,10 @@ static const struct file_operations ftrace_set_event_pid_fops = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
static const struct file_operations ftrace_enable_fops = {
|
static const struct file_operations ftrace_enable_fops = {
|
||||||
.open = tracing_open_generic,
|
.open = tracing_open_file_tr,
|
||||||
.read = event_enable_read,
|
.read = event_enable_read,
|
||||||
.write = event_enable_write,
|
.write = event_enable_write,
|
||||||
|
.release = tracing_release_file_tr,
|
||||||
.llseek = default_llseek,
|
.llseek = default_llseek,
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1718,9 +1719,10 @@ static const struct file_operations ftrace_event_id_fops = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
static const struct file_operations ftrace_event_filter_fops = {
|
static const struct file_operations ftrace_event_filter_fops = {
|
||||||
.open = tracing_open_generic,
|
.open = tracing_open_file_tr,
|
||||||
.read = event_filter_read,
|
.read = event_filter_read,
|
||||||
.write = event_filter_write,
|
.write = event_filter_write,
|
||||||
|
.release = tracing_release_file_tr,
|
||||||
.llseek = default_llseek,
|
.llseek = default_llseek,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -2684,6 +2684,7 @@ out_msg_denied:
|
|||||||
case rpc_autherr_rejectedverf:
|
case rpc_autherr_rejectedverf:
|
||||||
case rpcsec_gsserr_credproblem:
|
case rpcsec_gsserr_credproblem:
|
||||||
case rpcsec_gsserr_ctxproblem:
|
case rpcsec_gsserr_ctxproblem:
|
||||||
|
rpcauth_invalcred(task);
|
||||||
if (!task->tk_cred_retry)
|
if (!task->tk_cred_retry)
|
||||||
break;
|
break;
|
||||||
task->tk_cred_retry--;
|
task->tk_cred_retry--;
|
||||||
|
@ -112,34 +112,6 @@ static int axg_spdifin_prepare(struct snd_pcm_substream *substream,
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int axg_spdifin_startup(struct snd_pcm_substream *substream,
|
|
||||||
struct snd_soc_dai *dai)
|
|
||||||
{
|
|
||||||
struct axg_spdifin *priv = snd_soc_dai_get_drvdata(dai);
|
|
||||||
int ret;
|
|
||||||
|
|
||||||
ret = clk_prepare_enable(priv->refclk);
|
|
||||||
if (ret) {
|
|
||||||
dev_err(dai->dev,
|
|
||||||
"failed to enable spdifin reference clock\n");
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
regmap_update_bits(priv->map, SPDIFIN_CTRL0, SPDIFIN_CTRL0_EN,
|
|
||||||
SPDIFIN_CTRL0_EN);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void axg_spdifin_shutdown(struct snd_pcm_substream *substream,
|
|
||||||
struct snd_soc_dai *dai)
|
|
||||||
{
|
|
||||||
struct axg_spdifin *priv = snd_soc_dai_get_drvdata(dai);
|
|
||||||
|
|
||||||
regmap_update_bits(priv->map, SPDIFIN_CTRL0, SPDIFIN_CTRL0_EN, 0);
|
|
||||||
clk_disable_unprepare(priv->refclk);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void axg_spdifin_write_mode_param(struct regmap *map, int mode,
|
static void axg_spdifin_write_mode_param(struct regmap *map, int mode,
|
||||||
unsigned int val,
|
unsigned int val,
|
||||||
unsigned int num_per_reg,
|
unsigned int num_per_reg,
|
||||||
@ -251,25 +223,38 @@ static int axg_spdifin_dai_probe(struct snd_soc_dai *dai)
|
|||||||
ret = axg_spdifin_sample_mode_config(dai, priv);
|
ret = axg_spdifin_sample_mode_config(dai, priv);
|
||||||
if (ret) {
|
if (ret) {
|
||||||
dev_err(dai->dev, "mode configuration failed\n");
|
dev_err(dai->dev, "mode configuration failed\n");
|
||||||
clk_disable_unprepare(priv->pclk);
|
goto pclk_err;
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ret = clk_prepare_enable(priv->refclk);
|
||||||
|
if (ret) {
|
||||||
|
dev_err(dai->dev,
|
||||||
|
"failed to enable spdifin reference clock\n");
|
||||||
|
goto pclk_err;
|
||||||
|
}
|
||||||
|
|
||||||
|
regmap_update_bits(priv->map, SPDIFIN_CTRL0, SPDIFIN_CTRL0_EN,
|
||||||
|
SPDIFIN_CTRL0_EN);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
pclk_err:
|
||||||
|
clk_disable_unprepare(priv->pclk);
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int axg_spdifin_dai_remove(struct snd_soc_dai *dai)
|
static int axg_spdifin_dai_remove(struct snd_soc_dai *dai)
|
||||||
{
|
{
|
||||||
struct axg_spdifin *priv = snd_soc_dai_get_drvdata(dai);
|
struct axg_spdifin *priv = snd_soc_dai_get_drvdata(dai);
|
||||||
|
|
||||||
|
regmap_update_bits(priv->map, SPDIFIN_CTRL0, SPDIFIN_CTRL0_EN, 0);
|
||||||
|
clk_disable_unprepare(priv->refclk);
|
||||||
clk_disable_unprepare(priv->pclk);
|
clk_disable_unprepare(priv->pclk);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static const struct snd_soc_dai_ops axg_spdifin_ops = {
|
static const struct snd_soc_dai_ops axg_spdifin_ops = {
|
||||||
.prepare = axg_spdifin_prepare,
|
.prepare = axg_spdifin_prepare,
|
||||||
.startup = axg_spdifin_startup,
|
|
||||||
.shutdown = axg_spdifin_shutdown,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
static int axg_spdifin_iec958_info(struct snd_kcontrol *kcontrol,
|
static int axg_spdifin_iec958_info(struct snd_kcontrol *kcontrol,
|
||||||
|
Loading…
Reference in New Issue
Block a user