Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
openeuler
Kernel
提交
d807500a
K
Kernel
项目概览
openeuler
/
Kernel
大约 1 年 前同步成功
通知
5
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
K
Kernel
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
d807500a
编写于
3月 24, 2009
作者:
T
Takashi Iwai
浏览文件
操作
浏览文件
下载
差异文件
Merge branch 'topic/pcm-cleanup' into for-linus
上级
c7ccfd06
8b22d943
变更
4
隐藏空白更改
内联
并排
Showing
4 changed file
with
102 addition
and
61 deletion
+102
-61
include/sound/pcm.h
include/sound/pcm.h
+0
-1
sound/core/pcm.c
sound/core/pcm.c
+0
-1
sound/core/pcm_lib.c
sound/core/pcm_lib.c
+102
-53
sound/core/pcm_timer.c
sound/core/pcm_timer.c
+0
-6
未找到文件。
include/sound/pcm.h
浏览文件 @
d807500a
...
...
@@ -364,7 +364,6 @@ struct snd_pcm_substream {
/* -- timer section -- */
struct
snd_timer
*
timer
;
/* timer */
unsigned
timer_running
:
1
;
/* time is running */
spinlock_t
timer_lock
;
/* -- next substream -- */
struct
snd_pcm_substream
*
next
;
/* -- linked substreams -- */
...
...
sound/core/pcm.c
浏览文件 @
d807500a
...
...
@@ -667,7 +667,6 @@ int snd_pcm_new_stream(struct snd_pcm *pcm, int stream, int substream_count)
spin_lock_init
(
&
substream
->
self_group
.
lock
);
INIT_LIST_HEAD
(
&
substream
->
self_group
.
substreams
);
list_add_tail
(
&
substream
->
link_list
,
&
substream
->
self_group
.
substreams
);
spin_lock_init
(
&
substream
->
timer_lock
);
atomic_set
(
&
substream
->
mmap_count
,
0
);
prev
=
substream
;
}
...
...
sound/core/pcm_lib.c
浏览文件 @
d807500a
...
...
@@ -125,23 +125,32 @@ void snd_pcm_playback_silence(struct snd_pcm_substream *substream, snd_pcm_ufram
}
}
#ifdef CONFIG_SND_PCM_XRUN_DEBUG
#define xrun_debug(substream) ((substream)->pstr->xrun_debug)
#else
#define xrun_debug(substream) 0
#endif
#define dump_stack_on_xrun(substream) do { \
if (xrun_debug(substream) > 1) \
dump_stack(); \
} while (0)
static
void
xrun
(
struct
snd_pcm_substream
*
substream
)
{
snd_pcm_stop
(
substream
,
SNDRV_PCM_STATE_XRUN
);
#ifdef CONFIG_SND_PCM_XRUN_DEBUG
if
(
substream
->
pstr
->
xrun_debug
)
{
if
(
xrun_debug
(
substream
))
{
snd_printd
(
KERN_DEBUG
"XRUN: pcmC%dD%d%c
\n
"
,
substream
->
pcm
->
card
->
number
,
substream
->
pcm
->
device
,
substream
->
stream
?
'c'
:
'p'
);
if
(
substream
->
pstr
->
xrun_debug
>
1
)
dump_stack
();
dump_stack_on_xrun
(
substream
);
}
#endif
}
static
inline
snd_pcm_uframes_t
snd_pcm_update_hw_ptr_pos
(
struct
snd_pcm_substream
*
substream
,
struct
snd_pcm_runtime
*
runtime
)
static
snd_pcm_uframes_t
snd_pcm_update_hw_ptr_pos
(
struct
snd_pcm_substream
*
substream
,
struct
snd_pcm_runtime
*
runtime
)
{
snd_pcm_uframes_t
pos
;
...
...
@@ -150,17 +159,21 @@ static inline snd_pcm_uframes_t snd_pcm_update_hw_ptr_pos(struct snd_pcm_substre
pos
=
substream
->
ops
->
pointer
(
substream
);
if
(
pos
==
SNDRV_PCM_POS_XRUN
)
return
pos
;
/* XRUN */
#ifdef CONFIG_SND_DEBUG
if
(
pos
>=
runtime
->
buffer_size
)
{
snd_printk
(
KERN_ERR
"BUG: stream = %i, pos = 0x%lx, buffer size = 0x%lx, period size = 0x%lx
\n
"
,
substream
->
stream
,
pos
,
runtime
->
buffer_size
,
runtime
->
period_size
);
if
(
printk_ratelimit
())
{
snd_printd
(
KERN_ERR
"BUG: stream = %i, pos = 0x%lx, "
"buffer size = 0x%lx, period size = 0x%lx
\n
"
,
substream
->
stream
,
pos
,
runtime
->
buffer_size
,
runtime
->
period_size
);
}
pos
=
0
;
}
#endif
pos
-=
pos
%
runtime
->
min_align
;
return
pos
;
}
static
in
line
in
t
snd_pcm_update_hw_ptr_post
(
struct
snd_pcm_substream
*
substream
,
struct
snd_pcm_runtime
*
runtime
)
static
int
snd_pcm_update_hw_ptr_post
(
struct
snd_pcm_substream
*
substream
,
struct
snd_pcm_runtime
*
runtime
)
{
snd_pcm_uframes_t
avail
;
...
...
@@ -182,11 +195,21 @@ static inline int snd_pcm_update_hw_ptr_post(struct snd_pcm_substream *substream
return
0
;
}
static
inline
int
snd_pcm_update_hw_ptr_interrupt
(
struct
snd_pcm_substream
*
substream
)
#define hw_ptr_error(substream, fmt, args...) \
do { \
if (xrun_debug(substream)) { \
if (printk_ratelimit()) { \
snd_printd("PCM: " fmt, ##args); \
} \
dump_stack_on_xrun(substream); \
} \
} while (0)
static
int
snd_pcm_update_hw_ptr_interrupt
(
struct
snd_pcm_substream
*
substream
)
{
struct
snd_pcm_runtime
*
runtime
=
substream
->
runtime
;
snd_pcm_uframes_t
pos
;
snd_pcm_uframes_t
new_hw_ptr
,
hw_ptr_interrupt
;
snd_pcm_uframes_t
new_hw_ptr
,
hw_ptr_interrupt
,
hw_base
;
snd_pcm_sframes_t
delta
;
pos
=
snd_pcm_update_hw_ptr_pos
(
substream
,
runtime
);
...
...
@@ -194,36 +217,53 @@ static inline int snd_pcm_update_hw_ptr_interrupt(struct snd_pcm_substream *subs
xrun
(
substream
);
return
-
EPIPE
;
}
if
(
runtime
->
period_size
==
runtime
->
buffer_size
)
goto
__next_buf
;
new_hw_ptr
=
runtime
->
hw_ptr_base
+
pos
;
hw_base
=
runtime
->
hw_ptr_base
;
new_hw_ptr
=
hw_base
+
pos
;
hw_ptr_interrupt
=
runtime
->
hw_ptr_interrupt
+
runtime
->
period_size
;
delta
=
hw_ptr_interrupt
-
new_hw_ptr
;
if
(
delta
>
0
)
{
if
((
snd_pcm_uframes_t
)
delta
<
runtime
->
buffer_size
/
2
)
{
#ifdef CONFIG_SND_PCM_XRUN_DEBUG
if
(
runtime
->
periods
>
1
&&
substream
->
pstr
->
xrun_debug
)
{
snd_printd
(
KERN_ERR
"Unexpected hw_pointer value [1] (stream = %i, delta: -%ld, max jitter = %ld): wrong interrupt acknowledge?
\n
"
,
substream
->
stream
,
(
long
)
delta
,
runtime
->
buffer_size
/
2
);
if
(
substream
->
pstr
->
xrun_debug
>
1
)
dump_stack
();
}
#endif
return
0
;
delta
=
new_hw_ptr
-
hw_ptr_interrupt
;
if
(
hw_ptr_interrupt
>=
runtime
->
boundary
)
{
hw_ptr_interrupt
-=
runtime
->
boundary
;
if
(
hw_base
<
runtime
->
boundary
/
2
)
/* hw_base was already lapped; recalc delta */
delta
=
new_hw_ptr
-
hw_ptr_interrupt
;
}
if
(
delta
<
0
)
{
delta
+=
runtime
->
buffer_size
;
if
(
delta
<
0
)
{
hw_ptr_error
(
substream
,
"Unexpected hw_pointer value "
"(stream=%i, pos=%ld, intr_ptr=%ld)
\n
"
,
substream
->
stream
,
(
long
)
pos
,
(
long
)
hw_ptr_interrupt
);
/* rebase to interrupt position */
hw_base
=
new_hw_ptr
=
hw_ptr_interrupt
;
/* align hw_base to buffer_size */
hw_base
-=
hw_base
%
runtime
->
buffer_size
;
delta
=
0
;
}
else
{
hw_base
+=
runtime
->
buffer_size
;
if
(
hw_base
>=
runtime
->
boundary
)
hw_base
=
0
;
new_hw_ptr
=
hw_base
+
pos
;
}
__next_buf:
runtime
->
hw_ptr_base
+=
runtime
->
buffer_size
;
if
(
runtime
->
hw_ptr_base
==
runtime
->
boundary
)
runtime
->
hw_ptr_base
=
0
;
new_hw_ptr
=
runtime
->
hw_ptr_base
+
pos
;
}
if
(
delta
>
runtime
->
period_size
)
{
hw_ptr_error
(
substream
,
"Lost interrupts? "
"(stream=%i, delta=%ld, intr_ptr=%ld)
\n
"
,
substream
->
stream
,
(
long
)
delta
,
(
long
)
hw_ptr_interrupt
);
/* rebase hw_ptr_interrupt */
hw_ptr_interrupt
=
new_hw_ptr
-
new_hw_ptr
%
runtime
->
period_size
;
}
if
(
substream
->
stream
==
SNDRV_PCM_STREAM_PLAYBACK
&&
runtime
->
silence_size
>
0
)
snd_pcm_playback_silence
(
substream
,
new_hw_ptr
);
runtime
->
hw_ptr_base
=
hw_base
;
runtime
->
status
->
hw_ptr
=
new_hw_ptr
;
runtime
->
hw_ptr_interrupt
=
new_hw_ptr
-
new_hw_ptr
%
runtime
->
period_size
;
runtime
->
hw_ptr_interrupt
=
hw_ptr_interrupt
;
return
snd_pcm_update_hw_ptr_post
(
substream
,
runtime
);
}
...
...
@@ -233,7 +273,7 @@ int snd_pcm_update_hw_ptr(struct snd_pcm_substream *substream)
{
struct
snd_pcm_runtime
*
runtime
=
substream
->
runtime
;
snd_pcm_uframes_t
pos
;
snd_pcm_uframes_t
old_hw_ptr
,
new_hw_ptr
;
snd_pcm_uframes_t
old_hw_ptr
,
new_hw_ptr
,
hw_base
;
snd_pcm_sframes_t
delta
;
old_hw_ptr
=
runtime
->
status
->
hw_ptr
;
...
...
@@ -242,29 +282,38 @@ int snd_pcm_update_hw_ptr(struct snd_pcm_substream *substream)
xrun
(
substream
);
return
-
EPIPE
;
}
new_hw_ptr
=
runtime
->
hw_ptr_base
+
pos
;
delta
=
old_hw_ptr
-
new_hw_ptr
;
if
(
delta
>
0
)
{
if
((
snd_pcm_uframes_t
)
delta
<
runtime
->
buffer_size
/
2
)
{
#ifdef CONFIG_SND_PCM_XRUN_DEBUG
if
(
runtime
->
periods
>
2
&&
substream
->
pstr
->
xrun_debug
)
{
snd_printd
(
KERN_ERR
"Unexpected hw_pointer value [2] (stream = %i, delta: -%ld, max jitter = %ld): wrong interrupt acknowledge?
\n
"
,
substream
->
stream
,
(
long
)
delta
,
runtime
->
buffer_size
/
2
);
if
(
substream
->
pstr
->
xrun_debug
>
1
)
dump_stack
();
}
#endif
hw_base
=
runtime
->
hw_ptr_base
;
new_hw_ptr
=
hw_base
+
pos
;
delta
=
new_hw_ptr
-
old_hw_ptr
;
if
(
delta
<
0
)
{
delta
+=
runtime
->
buffer_size
;
if
(
delta
<
0
)
{
hw_ptr_error
(
substream
,
"Unexpected hw_pointer value [2] "
"(stream=%i, pos=%ld, old_ptr=%ld)
\n
"
,
substream
->
stream
,
(
long
)
pos
,
(
long
)
old_hw_ptr
);
return
0
;
}
runtime
->
hw_ptr_base
+=
runtime
->
buffer_size
;
if
(
runtime
->
hw_ptr_base
==
runtime
->
boundary
)
runtime
->
hw_ptr_base
=
0
;
new_hw_ptr
=
runtime
->
hw_ptr_base
+
pos
;
hw_base
+=
runtime
->
buffer_size
;
if
(
hw_base
>=
runtime
->
boundary
)
hw_base
=
0
;
new_hw_ptr
=
hw_base
+
pos
;
}
if
(
delta
>
runtime
->
period_size
&&
runtime
->
periods
>
1
)
{
hw_ptr_error
(
substream
,
"hw_ptr skipping! "
"(pos=%ld, delta=%ld, period=%ld)
\n
"
,
(
long
)
pos
,
(
long
)
delta
,
(
long
)
runtime
->
period_size
);
return
0
;
}
if
(
substream
->
stream
==
SNDRV_PCM_STREAM_PLAYBACK
&&
runtime
->
silence_size
>
0
)
snd_pcm_playback_silence
(
substream
,
new_hw_ptr
);
runtime
->
hw_ptr_base
=
hw_base
;
runtime
->
status
->
hw_ptr
=
new_hw_ptr
;
return
snd_pcm_update_hw_ptr_post
(
substream
,
runtime
);
...
...
sound/core/pcm_timer.c
浏览文件 @
d807500a
...
...
@@ -85,25 +85,19 @@ static unsigned long snd_pcm_timer_resolution(struct snd_timer * timer)
static
int
snd_pcm_timer_start
(
struct
snd_timer
*
timer
)
{
unsigned
long
flags
;
struct
snd_pcm_substream
*
substream
;
substream
=
snd_timer_chip
(
timer
);
spin_lock_irqsave
(
&
substream
->
timer_lock
,
flags
);
substream
->
timer_running
=
1
;
spin_unlock_irqrestore
(
&
substream
->
timer_lock
,
flags
);
return
0
;
}
static
int
snd_pcm_timer_stop
(
struct
snd_timer
*
timer
)
{
unsigned
long
flags
;
struct
snd_pcm_substream
*
substream
;
substream
=
snd_timer_chip
(
timer
);
spin_lock_irqsave
(
&
substream
->
timer_lock
,
flags
);
substream
->
timer_running
=
0
;
spin_unlock_irqrestore
(
&
substream
->
timer_lock
,
flags
);
return
0
;
}
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录