当前位置: 技术问答>linux和unix
WM8976的寄存器设置问题
来源: 互联网 发布时间:2016-10-20
本文导语: 在Linux下,音频芯片WM8976的寄存器操作问题: 音频驱动中有wm8976_write函数: int wm8976_write(struct snd_soc_codec *codec, unsigned int reg,unsigned int value) 该函数为向WM8976寄存器写数据的函数,但是函数的传入参数有一个结...
在Linux下,音频芯片WM8976的寄存器操作问题:
音频驱动中有wm8976_write函数:
int wm8976_write(struct snd_soc_codec *codec, unsigned int reg,unsigned int value)
该函数为向WM8976寄存器写数据的函数,但是函数的传入参数有一个结构体,我发现程序中
凡是调用到这个函数的,都会先定义一个结构体,这样调用wm8976_write时就会有传入的结构体
参数了。如以下函数:
这些函数要么在下面的定义中:
要么就是这里定义:
我需要再添加一个函数,用于操作寄存器,通过调用wm8976_write函数实现,但是
调用它必须加入一个传入结构体,尝试定义过结构体,但是运行内核后内核直接
崩溃,请教高手我该如何添加函数?
我添加的函数如下:
生成内核映像后运行时,内核崩溃,期待高手指点。
音频驱动中有wm8976_write函数:
int wm8976_write(struct snd_soc_codec *codec, unsigned int reg,unsigned int value)
该函数为向WM8976寄存器写数据的函数,但是函数的传入参数有一个结构体,我发现程序中
凡是调用到这个函数的,都会先定义一个结构体,这样调用wm8976_write时就会有传入的结构体
参数了。如以下函数:
static int wm8976_set_dai_fmt(struct snd_soc_dai *codec_dai,unsigned int fmt)
{
struct snd_soc_codec *codec = codec_dai->codec;
...
wm8976_write(codec, WM8976_IFACE, iface);
wm8976_write(codec, WM8976_CLOCK, clk);
}
static int wm8976_set_dai_pll(struct snd_soc_dai *codec_dai,
int pll_id, unsigned int freq_in, unsigned int freq_out)
{
struct snd_soc_codec *codec = codec_dai->codec;
...
wm8976_write(codec, WM8976_PLLK1, pll_div.k >> 18);
}
static int wm8976_hw_params(struct snd_pcm_substream *substream,
struct snd_pcm_hw_params *params,
struct snd_soc_dai *dai)
{
struct snd_soc_device *socdev = rtd->socdev;
struct snd_soc_codec *codec = socdev->codec;
...
wm8976_write(codec, WM8976_ADD, adn);
}
static int wm8976_set_dai_clkdiv(struct snd_soc_dai *codec_dai,
int div_id, int div)
{
struct snd_soc_codec *codec = codec_dai->codec;
...
wm8976_write(codec, WM8976_CLOCK, reg | div);
}
这些函数要么在下面的定义中:
struct snd_soc_dai wm8976_dai = {
.name = "WM8976 HiFi",
.playback = {
.stream_name = "Playback",
.channels_min = 1,
.channels_max = 2,
.rates = WM8976_RATES,
.formats = WM8976_FORMATS,},
.capture = {
.stream_name = "Capture",
.channels_min = 1,
.channels_max = 2,
.rates = WM8976_RATES,
.formats = WM8976_FORMATS,},
.ops = {
.hw_params = wm8976_hw_params,
},
.dai_ops = {
.digital_mute = wm8976_mute,
.set_fmt = wm8976_set_dai_fmt,
.set_clkdiv = wm8976_set_dai_clkdiv,
.set_pll = wm8976_set_dai_pll,
.set_sysclk = wm8976_set_dai_sysclk,
},
};
要么就是这里定义:
struct snd_soc_codec_device soc_codec_dev_wm8976 = {
.probe = wm8976_probe,
.remove = wm8976_remove,
.suspend = wm8976_suspend,
.resume = wm8976_resume,
};
我需要再添加一个函数,用于操作寄存器,通过调用wm8976_write函数实现,但是
调用它必须加入一个传入结构体,尝试定义过结构体,但是运行内核后内核直接
崩溃,请教高手我该如何添加函数?
我添加的函数如下:
void wm8976_spk_phone_set(int mode)
{
struct snd_soc_device *socdev = wm8976_socdev;
struct snd_soc_codec *codec = socdev->codec;
if(mode)//speaker mode
{
wm8976_write(codec, WM8976_SPKVOLL, 0x3f);
wm8976_write(codec, WM8976_SPKVOLR, 0x3f);
}
else//headphone mode
{
wm8976_write(codec, WM8976_HPVOLL, 0x3f);
wm8976_write(codec, WM8976_HPVOLR, 0x40);
}
}
EXPORT_SYMBOL_GPL(wm8976_spk_phone_set);
生成内核映像后运行时,内核崩溃,期待高手指点。
|
这个问题应该不难搞啊!我也在搞wm8993,不难弄这个功能。
首先:定义一个静态全局变量:static struct snd_soc_codec *wm8976_codec;
然后:在static int wm8976_i2c_probe(struct i2c_client *i2c, const struct i2c_device_id *id)函数体的后半部分增加一行:wm8976_codec = codec;
最后就可以这样调用了,wm8976_write(wm8976_codec , WM8976_HPVOLR, 0x40);
祝你好运。
首先:定义一个静态全局变量:static struct snd_soc_codec *wm8976_codec;
然后:在static int wm8976_i2c_probe(struct i2c_client *i2c, const struct i2c_device_id *id)函数体的后半部分增加一行:wm8976_codec = codec;
最后就可以这样调用了,wm8976_write(wm8976_codec , WM8976_HPVOLR, 0x40);
祝你好运。