aboutsummaryrefslogtreecommitdiffstats
path: root/sound/drivers
diff options
context:
space:
mode:
Diffstat (limited to 'sound/drivers')
-rw-r--r--sound/drivers/pcsp/pcsp.c32
-rw-r--r--sound/drivers/pcsp/pcsp.h2
-rw-r--r--sound/drivers/pcsp/pcsp_mixer.c35
3 files changed, 48 insertions, 21 deletions
diff --git a/sound/drivers/pcsp/pcsp.c b/sound/drivers/pcsp/pcsp.c
index b60cef257b58..f165c77d6273 100644
--- a/sound/drivers/pcsp/pcsp.c
+++ b/sound/drivers/pcsp/pcsp.c
@@ -26,6 +26,7 @@ MODULE_ALIAS("platform:pcspkr");
26static int index = SNDRV_DEFAULT_IDX1; /* Index 0-MAX */ 26static int index = SNDRV_DEFAULT_IDX1; /* Index 0-MAX */
27static char *id = SNDRV_DEFAULT_STR1; /* ID for this card */ 27static char *id = SNDRV_DEFAULT_STR1; /* ID for this card */
28static int enable = SNDRV_DEFAULT_ENABLE1; /* Enable this card */ 28static int enable = SNDRV_DEFAULT_ENABLE1; /* Enable this card */
29static int nopcm; /* Disable PCM capability of the driver */
29 30
30module_param(index, int, 0444); 31module_param(index, int, 0444);
31MODULE_PARM_DESC(index, "Index value for pcsp soundcard."); 32MODULE_PARM_DESC(index, "Index value for pcsp soundcard.");
@@ -33,6 +34,8 @@ module_param(id, charp, 0444);
33MODULE_PARM_DESC(id, "ID string for pcsp soundcard."); 34MODULE_PARM_DESC(id, "ID string for pcsp soundcard.");
34module_param(enable, bool, 0444); 35module_param(enable, bool, 0444);
35MODULE_PARM_DESC(enable, "Enable PC-Speaker sound."); 36MODULE_PARM_DESC(enable, "Enable PC-Speaker sound.");
37module_param(nopcm, bool, 0444);
38MODULE_PARM_DESC(nopcm, "Disable PC-Speaker PCM sound. Only beeps remain.");
36 39
37struct snd_pcsp pcsp_chip; 40struct snd_pcsp pcsp_chip;
38 41
@@ -43,13 +46,16 @@ static int __devinit snd_pcsp_create(struct snd_card *card)
43 int err; 46 int err;
44 int div, min_div, order; 47 int div, min_div, order;
45 48
46 hrtimer_get_res(CLOCK_MONOTONIC, &tp); 49 if (!nopcm) {
47 if (tp.tv_sec || tp.tv_nsec > PCSP_MAX_PERIOD_NS) { 50 hrtimer_get_res(CLOCK_MONOTONIC, &tp);
48 printk(KERN_ERR "PCSP: Timer resolution is not sufficient " 51 if (tp.tv_sec || tp.tv_nsec > PCSP_MAX_PERIOD_NS) {
49 "(%linS)\n", tp.tv_nsec); 52 printk(KERN_ERR "PCSP: Timer resolution is not sufficient "
50 printk(KERN_ERR "PCSP: Make sure you have HPET and ACPI " 53 "(%linS)\n", tp.tv_nsec);
51 "enabled.\n"); 54 printk(KERN_ERR "PCSP: Make sure you have HPET and ACPI "
52 return -EIO; 55 "enabled.\n");
56 printk(KERN_ERR "PCSP: Turned into nopcm mode.\n");
57 nopcm = 1;
58 }
53 } 59 }
54 60
55 if (loops_per_jiffy >= PCSP_MIN_LPJ && tp.tv_nsec <= PCSP_MIN_PERIOD_NS) 61 if (loops_per_jiffy >= PCSP_MIN_LPJ && tp.tv_nsec <= PCSP_MIN_PERIOD_NS)
@@ -107,12 +113,14 @@ static int __devinit snd_card_pcsp_probe(int devnum, struct device *dev)
107 snd_card_free(card); 113 snd_card_free(card);
108 return err; 114 return err;
109 } 115 }
110 err = snd_pcsp_new_pcm(&pcsp_chip); 116 if (!nopcm) {
111 if (err < 0) { 117 err = snd_pcsp_new_pcm(&pcsp_chip);
112 snd_card_free(card); 118 if (err < 0) {
113 return err; 119 snd_card_free(card);
120 return err;
121 }
114 } 122 }
115 err = snd_pcsp_new_mixer(&pcsp_chip); 123 err = snd_pcsp_new_mixer(&pcsp_chip, nopcm);
116 if (err < 0) { 124 if (err < 0) {
117 snd_card_free(card); 125 snd_card_free(card);
118 return err; 126 return err;
diff --git a/sound/drivers/pcsp/pcsp.h b/sound/drivers/pcsp/pcsp.h
index 174dd2ff0f22..1e123077923d 100644
--- a/sound/drivers/pcsp/pcsp.h
+++ b/sound/drivers/pcsp/pcsp.h
@@ -83,6 +83,6 @@ extern enum hrtimer_restart pcsp_do_timer(struct hrtimer *handle);
83extern void pcsp_sync_stop(struct snd_pcsp *chip); 83extern void pcsp_sync_stop(struct snd_pcsp *chip);
84 84
85extern int snd_pcsp_new_pcm(struct snd_pcsp *chip); 85extern int snd_pcsp_new_pcm(struct snd_pcsp *chip);
86extern int snd_pcsp_new_mixer(struct snd_pcsp *chip); 86extern int snd_pcsp_new_mixer(struct snd_pcsp *chip, int nopcm);
87 87
88#endif 88#endif
diff --git a/sound/drivers/pcsp/pcsp_mixer.c b/sound/drivers/pcsp/pcsp_mixer.c
index 903bc846763f..6f633f4f3b96 100644
--- a/sound/drivers/pcsp/pcsp_mixer.c
+++ b/sound/drivers/pcsp/pcsp_mixer.c
@@ -119,24 +119,43 @@ static int pcsp_pcspkr_put(struct snd_kcontrol *kcontrol,
119 .put = pcsp_##ctl_type##_put, \ 119 .put = pcsp_##ctl_type##_put, \
120} 120}
121 121
122static struct snd_kcontrol_new __devinitdata snd_pcsp_controls[] = { 122static struct snd_kcontrol_new __devinitdata snd_pcsp_controls_pcm[] = {
123 PCSP_MIXER_CONTROL(enable, "Master Playback Switch"), 123 PCSP_MIXER_CONTROL(enable, "Master Playback Switch"),
124 PCSP_MIXER_CONTROL(treble, "BaseFRQ Playback Volume"), 124 PCSP_MIXER_CONTROL(treble, "BaseFRQ Playback Volume"),
125 PCSP_MIXER_CONTROL(pcspkr, "PC Speaker Playback Switch"),
126}; 125};
127 126
128int __devinit snd_pcsp_new_mixer(struct snd_pcsp *chip) 127static struct snd_kcontrol_new __devinitdata snd_pcsp_controls_spkr[] = {
128 PCSP_MIXER_CONTROL(pcspkr, "Beep Playback Switch"),
129};
130
131static int __devinit snd_pcsp_ctls_add(struct snd_pcsp *chip,
132 struct snd_kcontrol_new *ctls, int num)
129{ 133{
130 struct snd_card *card = chip->card;
131 int i, err; 134 int i, err;
135 struct snd_card *card = chip->card;
136 for (i = 0; i < num; i++) {
137 err = snd_ctl_add(card, snd_ctl_new1(ctls + i, chip));
138 if (err < 0)
139 return err;
140 }
141 return 0;
142}
143
144int __devinit snd_pcsp_new_mixer(struct snd_pcsp *chip, int nopcm)
145{
146 int err;
147 struct snd_card *card = chip->card;
132 148
133 for (i = 0; i < ARRAY_SIZE(snd_pcsp_controls); i++) { 149 if (!nopcm) {
134 err = snd_ctl_add(card, 150 err = snd_pcsp_ctls_add(chip, snd_pcsp_controls_pcm,
135 snd_ctl_new1(snd_pcsp_controls + i, 151 ARRAY_SIZE(snd_pcsp_controls_pcm));
136 chip));
137 if (err < 0) 152 if (err < 0)
138 return err; 153 return err;
139 } 154 }
155 err = snd_pcsp_ctls_add(chip, snd_pcsp_controls_spkr,
156 ARRAY_SIZE(snd_pcsp_controls_spkr));
157 if (err < 0)
158 return err;
140 159
141 strcpy(card->mixername, "PC-Speaker"); 160 strcpy(card->mixername, "PC-Speaker");
142 161