Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
L
linux-davinci
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Redmine
Redmine
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Operations
Operations
Metrics
Environments
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
linux
linux-davinci
Commits
6bcdbd55
Commit
6bcdbd55
authored
Dec 20, 2008
by
Takashi Iwai
Browse files
Options
Browse Files
Download
Plain Diff
Merge branch 'topic/ca0106-resume' into topic/ca0106
parents
6a843641
72077aa3
Changes
3
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
456 additions
and
269 deletions
+456
-269
sound/pci/ca0106/ca0106.h
sound/pci/ca0106/ca0106.h
+14
-1
sound/pci/ca0106/ca0106_main.c
sound/pci/ca0106/ca0106_main.c
+312
-216
sound/pci/ca0106/ca0106_mixer.c
sound/pci/ca0106/ca0106_mixer.c
+130
-52
No files found.
sound/pci/ca0106/ca0106.h
View file @
6bcdbd55
...
...
@@ -690,7 +690,7 @@ struct snd_ca0106 {
spinlock_t
emu_lock
;
struct
snd_ac97
*
ac97
;
struct
snd_pcm
*
pcm
;
struct
snd_pcm
*
pcm
[
4
]
;
struct
snd_ca0106_channel
playback_channels
[
4
];
struct
snd_ca0106_channel
capture_channels
[
4
];
...
...
@@ -707,6 +707,11 @@ struct snd_ca0106 {
struct
snd_ca_midi
midi2
;
u16
spi_dac_reg
[
16
];
#ifdef CONFIG_PM
#define NUM_SAVED_VOLUMES 9
unsigned
int
saved_vol
[
NUM_SAVED_VOLUMES
];
#endif
};
int
snd_ca0106_mixer
(
struct
snd_ca0106
*
emu
);
...
...
@@ -725,3 +730,11 @@ int snd_ca0106_i2c_write(struct snd_ca0106 *emu, u32 reg, u32 value);
int
snd_ca0106_spi_write
(
struct
snd_ca0106
*
emu
,
unsigned
int
data
);
#ifdef CONFIG_PM
void
snd_ca0106_mixer_suspend
(
struct
snd_ca0106
*
chip
);
void
snd_ca0106_mixer_resume
(
struct
snd_ca0106
*
chip
);
#else
#define snd_ca0106_mixer_suspend(chip) do { } while (0)
#define snd_ca0106_mixer_resume(chip) do { } while (0)
#endif
sound/pci/ca0106/ca0106_main.c
View file @
6bcdbd55
This diff is collapsed.
Click to expand it.
sound/pci/ca0106/ca0106_mixer.c
View file @
6bcdbd55
...
...
@@ -75,6 +75,84 @@
#include "ca0106.h"
static
void
ca0106_spdif_enable
(
struct
snd_ca0106
*
emu
)
{
unsigned
int
val
;
if
(
emu
->
spdif_enable
)
{
/* Digital */
snd_ca0106_ptr_write
(
emu
,
SPDIF_SELECT1
,
0
,
0xf
);
snd_ca0106_ptr_write
(
emu
,
SPDIF_SELECT2
,
0
,
0x0b000000
);
val
=
snd_ca0106_ptr_read
(
emu
,
CAPTURE_CONTROL
,
0
)
&
~
0x1000
;
snd_ca0106_ptr_write
(
emu
,
CAPTURE_CONTROL
,
0
,
val
);
val
=
inl
(
emu
->
port
+
GPIO
)
&
~
0x101
;
outl
(
val
,
emu
->
port
+
GPIO
);
}
else
{
/* Analog */
snd_ca0106_ptr_write
(
emu
,
SPDIF_SELECT1
,
0
,
0xf
);
snd_ca0106_ptr_write
(
emu
,
SPDIF_SELECT2
,
0
,
0x000f0000
);
val
=
snd_ca0106_ptr_read
(
emu
,
CAPTURE_CONTROL
,
0
)
|
0x1000
;
snd_ca0106_ptr_write
(
emu
,
CAPTURE_CONTROL
,
0
,
val
);
val
=
inl
(
emu
->
port
+
GPIO
)
|
0x101
;
outl
(
val
,
emu
->
port
+
GPIO
);
}
}
static
void
ca0106_set_capture_source
(
struct
snd_ca0106
*
emu
)
{
unsigned
int
val
=
emu
->
capture_source
;
unsigned
int
source
,
mask
;
source
=
(
val
<<
28
)
|
(
val
<<
24
)
|
(
val
<<
20
)
|
(
val
<<
16
);
mask
=
snd_ca0106_ptr_read
(
emu
,
CAPTURE_SOURCE
,
0
)
&
0xffff
;
snd_ca0106_ptr_write
(
emu
,
CAPTURE_SOURCE
,
0
,
source
|
mask
);
}
static
void
ca0106_set_i2c_capture_source
(
struct
snd_ca0106
*
emu
,
unsigned
int
val
,
int
force
)
{
unsigned
int
ngain
,
ogain
;
u32
source
;
snd_ca0106_i2c_write
(
emu
,
ADC_MUX
,
0
);
/* Mute input */
ngain
=
emu
->
i2c_capture_volume
[
val
][
0
];
/* Left */
ogain
=
emu
->
i2c_capture_volume
[
emu
->
i2c_capture_source
][
0
];
/* Left */
if
(
force
||
ngain
!=
ogain
)
snd_ca0106_i2c_write
(
emu
,
ADC_ATTEN_ADCL
,
ngain
&
0xff
);
ngain
=
emu
->
i2c_capture_volume
[
val
][
1
];
/* Right */
ogain
=
emu
->
i2c_capture_volume
[
emu
->
i2c_capture_source
][
1
];
/* Right */
if
(
force
||
ngain
!=
ogain
)
snd_ca0106_i2c_write
(
emu
,
ADC_ATTEN_ADCR
,
ngain
&
0xff
);
source
=
1
<<
val
;
snd_ca0106_i2c_write
(
emu
,
ADC_MUX
,
source
);
/* Set source */
emu
->
i2c_capture_source
=
val
;
}
static
void
ca0106_set_capture_mic_line_in
(
struct
snd_ca0106
*
emu
)
{
u32
tmp
;
if
(
emu
->
capture_mic_line_in
)
{
/* snd_ca0106_i2c_write(emu, ADC_MUX, 0); */
/* Mute input */
tmp
=
inl
(
emu
->
port
+
GPIO
)
&
~
0x400
;
tmp
=
tmp
|
0x400
;
outl
(
tmp
,
emu
->
port
+
GPIO
);
/* snd_ca0106_i2c_write(emu, ADC_MUX, ADC_MUX_MIC); */
}
else
{
/* snd_ca0106_i2c_write(emu, ADC_MUX, 0); */
/* Mute input */
tmp
=
inl
(
emu
->
port
+
GPIO
)
&
~
0x400
;
outl
(
tmp
,
emu
->
port
+
GPIO
);
/* snd_ca0106_i2c_write(emu, ADC_MUX, ADC_MUX_LINEIN); */
}
}
static
void
ca0106_set_spdif_bits
(
struct
snd_ca0106
*
emu
,
int
idx
)
{
snd_ca0106_ptr_write
(
emu
,
SPCS0
+
idx
,
0
,
emu
->
spdif_bits
[
idx
]);
}
/*
*/
static
const
DECLARE_TLV_DB_SCALE
(
snd_ca0106_db_scale1
,
-
5175
,
25
,
1
);
static
const
DECLARE_TLV_DB_SCALE
(
snd_ca0106_db_scale2
,
-
10350
,
50
,
1
);
...
...
@@ -95,30 +173,12 @@ static int snd_ca0106_shared_spdif_put(struct snd_kcontrol *kcontrol,
struct
snd_ca0106
*
emu
=
snd_kcontrol_chip
(
kcontrol
);
unsigned
int
val
;
int
change
=
0
;
u32
mask
;
val
=
!!
ucontrol
->
value
.
integer
.
value
[
0
];
change
=
(
emu
->
spdif_enable
!=
val
);
if
(
change
)
{
emu
->
spdif_enable
=
val
;
if
(
val
)
{
/* Digital */
snd_ca0106_ptr_write
(
emu
,
SPDIF_SELECT1
,
0
,
0xf
);
snd_ca0106_ptr_write
(
emu
,
SPDIF_SELECT2
,
0
,
0x0b000000
);
snd_ca0106_ptr_write
(
emu
,
CAPTURE_CONTROL
,
0
,
snd_ca0106_ptr_read
(
emu
,
CAPTURE_CONTROL
,
0
)
&
~
0x1000
);
mask
=
inl
(
emu
->
port
+
GPIO
)
&
~
0x101
;
outl
(
mask
,
emu
->
port
+
GPIO
);
}
else
{
/* Analog */
snd_ca0106_ptr_write
(
emu
,
SPDIF_SELECT1
,
0
,
0xf
);
snd_ca0106_ptr_write
(
emu
,
SPDIF_SELECT2
,
0
,
0x000f0000
);
snd_ca0106_ptr_write
(
emu
,
CAPTURE_CONTROL
,
0
,
snd_ca0106_ptr_read
(
emu
,
CAPTURE_CONTROL
,
0
)
|
0x1000
);
mask
=
inl
(
emu
->
port
+
GPIO
)
|
0x101
;
outl
(
mask
,
emu
->
port
+
GPIO
);
}
ca0106_spdif_enable
(
emu
);
}
return
change
;
}
...
...
@@ -154,8 +214,6 @@ static int snd_ca0106_capture_source_put(struct snd_kcontrol *kcontrol,
struct
snd_ca0106
*
emu
=
snd_kcontrol_chip
(
kcontrol
);
unsigned
int
val
;
int
change
=
0
;
u32
mask
;
u32
source
;
val
=
ucontrol
->
value
.
enumerated
.
item
[
0
]
;
if
(
val
>=
6
)
...
...
@@ -163,9 +221,7 @@ static int snd_ca0106_capture_source_put(struct snd_kcontrol *kcontrol,
change
=
(
emu
->
capture_source
!=
val
);
if
(
change
)
{
emu
->
capture_source
=
val
;
source
=
(
val
<<
28
)
|
(
val
<<
24
)
|
(
val
<<
20
)
|
(
val
<<
16
);
mask
=
snd_ca0106_ptr_read
(
emu
,
CAPTURE_SOURCE
,
0
)
&
0xffff
;
snd_ca0106_ptr_write
(
emu
,
CAPTURE_SOURCE
,
0
,
source
|
mask
);
ca0106_set_capture_source
(
emu
);
}
return
change
;
}
...
...
@@ -200,9 +256,7 @@ static int snd_ca0106_i2c_capture_source_put(struct snd_kcontrol *kcontrol,
{
struct
snd_ca0106
*
emu
=
snd_kcontrol_chip
(
kcontrol
);
unsigned
int
source_id
;
unsigned
int
ngain
,
ogain
;
int
change
=
0
;
u32
source
;
/* If the capture source has changed,
* update the capture volume from the cached value
* for the particular source.
...
...
@@ -212,18 +266,7 @@ static int snd_ca0106_i2c_capture_source_put(struct snd_kcontrol *kcontrol,
return
-
EINVAL
;
change
=
(
emu
->
i2c_capture_source
!=
source_id
);
if
(
change
)
{
snd_ca0106_i2c_write
(
emu
,
ADC_MUX
,
0
);
/* Mute input */
ngain
=
emu
->
i2c_capture_volume
[
source_id
][
0
];
/* Left */
ogain
=
emu
->
i2c_capture_volume
[
emu
->
i2c_capture_source
][
0
];
/* Left */
if
(
ngain
!=
ogain
)
snd_ca0106_i2c_write
(
emu
,
ADC_ATTEN_ADCL
,
((
ngain
)
&
0xff
));
ngain
=
emu
->
i2c_capture_volume
[
source_id
][
1
];
/* Left */
ogain
=
emu
->
i2c_capture_volume
[
emu
->
i2c_capture_source
][
1
];
/* Left */
if
(
ngain
!=
ogain
)
snd_ca0106_i2c_write
(
emu
,
ADC_ATTEN_ADCR
,
((
ngain
)
&
0xff
));
source
=
1
<<
source_id
;
snd_ca0106_i2c_write
(
emu
,
ADC_MUX
,
source
);
/* Set source */
emu
->
i2c_capture_source
=
source_id
;
ca0106_set_i2c_capture_source
(
emu
,
source_id
,
0
);
}
return
change
;
}
...
...
@@ -271,7 +314,6 @@ static int snd_ca0106_capture_mic_line_in_put(struct snd_kcontrol *kcontrol,
struct
snd_ca0106
*
emu
=
snd_kcontrol_chip
(
kcontrol
);
unsigned
int
val
;
int
change
=
0
;
u32
tmp
;
val
=
ucontrol
->
value
.
enumerated
.
item
[
0
]
;
if
(
val
>
1
)
...
...
@@ -279,18 +321,7 @@ static int snd_ca0106_capture_mic_line_in_put(struct snd_kcontrol *kcontrol,
change
=
(
emu
->
capture_mic_line_in
!=
val
);
if
(
change
)
{
emu
->
capture_mic_line_in
=
val
;
if
(
val
)
{
//snd_ca0106_i2c_write(emu, ADC_MUX, 0); /* Mute input */
tmp
=
inl
(
emu
->
port
+
GPIO
)
&
~
0x400
;
tmp
=
tmp
|
0x400
;
outl
(
tmp
,
emu
->
port
+
GPIO
);
//snd_ca0106_i2c_write(emu, ADC_MUX, ADC_MUX_MIC);
}
else
{
//snd_ca0106_i2c_write(emu, ADC_MUX, 0); /* Mute input */
tmp
=
inl
(
emu
->
port
+
GPIO
)
&
~
0x400
;
outl
(
tmp
,
emu
->
port
+
GPIO
);
//snd_ca0106_i2c_write(emu, ADC_MUX, ADC_MUX_LINEIN);
}
ca0106_set_capture_mic_line_in
(
emu
);
}
return
change
;
}
...
...
@@ -359,8 +390,8 @@ static int snd_ca0106_spdif_put(struct snd_kcontrol *kcontrol,
(
ucontrol
->
value
.
iec958
.
status
[
3
]
<<
24
);
change
=
val
!=
emu
->
spdif_bits
[
idx
];
if
(
change
)
{
snd_ca0106_ptr_write
(
emu
,
SPCS0
+
idx
,
0
,
val
);
emu
->
spdif_bits
[
idx
]
=
val
;
ca0106_set_spdif_bits
(
emu
,
idx
);
}
return
change
;
}
...
...
@@ -773,3 +804,50 @@ int __devinit snd_ca0106_mixer(struct snd_ca0106 *emu)
return
0
;
}
#ifdef CONFIG_PM
struct
ca0106_vol_tbl
{
unsigned
int
channel_id
;
unsigned
int
reg
;
};
static
struct
ca0106_vol_tbl
saved_volumes
[
NUM_SAVED_VOLUMES
]
=
{
{
CONTROL_FRONT_CHANNEL
,
PLAYBACK_VOLUME2
},
{
CONTROL_REAR_CHANNEL
,
PLAYBACK_VOLUME2
},
{
CONTROL_CENTER_LFE_CHANNEL
,
PLAYBACK_VOLUME2
},
{
CONTROL_UNKNOWN_CHANNEL
,
PLAYBACK_VOLUME2
},
{
CONTROL_FRONT_CHANNEL
,
PLAYBACK_VOLUME1
},
{
CONTROL_REAR_CHANNEL
,
PLAYBACK_VOLUME1
},
{
CONTROL_CENTER_LFE_CHANNEL
,
PLAYBACK_VOLUME1
},
{
CONTROL_UNKNOWN_CHANNEL
,
PLAYBACK_VOLUME1
},
{
1
,
CAPTURE_CONTROL
},
};
void
snd_ca0106_mixer_suspend
(
struct
snd_ca0106
*
chip
)
{
int
i
;
/* save volumes */
for
(
i
=
0
;
i
<
NUM_SAVED_VOLUMES
;
i
++
)
chip
->
saved_vol
[
i
]
=
snd_ca0106_ptr_read
(
chip
,
saved_volumes
[
i
].
reg
,
saved_volumes
[
i
].
channel_id
);
}
void
snd_ca0106_mixer_resume
(
struct
snd_ca0106
*
chip
)
{
int
i
;
for
(
i
=
0
;
i
<
NUM_SAVED_VOLUMES
;
i
++
)
snd_ca0106_ptr_write
(
chip
,
saved_volumes
[
i
].
reg
,
saved_volumes
[
i
].
channel_id
,
chip
->
saved_vol
[
i
]);
ca0106_spdif_enable
(
chip
);
ca0106_set_capture_source
(
chip
);
ca0106_set_i2c_capture_source
(
chip
,
chip
->
i2c_capture_source
,
1
);
for
(
i
=
0
;
i
<
4
;
i
++
)
ca0106_set_spdif_bits
(
chip
,
i
);
if
(
chip
->
details
->
i2c_adc
)
ca0106_set_capture_mic_line_in
(
chip
);
}
#endif
/* CONFIG_PM */
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment