예제 #1
0
파일: btsco.c 프로젝트: goroutines/rumprun
static int
btsco_set_params(void *hdl, int setmode, int usemode,
		audio_params_t *play, audio_params_t *rec,
		stream_filter_list_t *pfil, stream_filter_list_t *rfil)
{
/*	struct btsco_softc *sc = hdl;	*/
	const struct audio_format *f;
	int rv;

	DPRINTF("setmode 0x%x usemode 0x%x\n", setmode, usemode);
	DPRINTF("rate %d, precision %d, channels %d encoding %d\n",
		play->sample_rate, play->precision, play->channels, play->encoding);

	/*
	 * If we had a list of formats, we could check the HCI_Voice_Setting
	 * and select the appropriate one to use. Currently only one is
	 * supported: 0x0060 == 8000Hz, mono, 16-bit, slinear_le
	 */
	f = &btsco_format;

	if (setmode & AUMODE_PLAY) {
		rv = auconv_set_converter(f, 1, AUMODE_PLAY, play, TRUE, pfil);
		if (rv < 0)
			return EINVAL;
	}

	if (setmode & AUMODE_RECORD) {
		rv = auconv_set_converter(f, 1, AUMODE_RECORD, rec, TRUE, rfil);
		if (rv < 0)
			return EINVAL;
	}

	return 0;
}
예제 #2
0
파일: vaudio.c 프로젝트: ryo/netbsd-src
static int
vaudio_set_params(void *opaque, int setmode, int usemode,
    audio_params_t *play, audio_params_t *rec,
    stream_filter_list_t *pfil, stream_filter_list_t *rfil)
{
	struct vaudio_softc *sc = opaque;
	audio_params_t *p;
	stream_filter_list_t *fil;
	int mode, index;

	for (mode = AUMODE_RECORD; mode != -1;
	    mode = mode == AUMODE_RECORD ? AUMODE_PLAY : -1) {
		if ((setmode & mode) == 0)
			continue;
		p = mode == AUMODE_PLAY ? play : rec;
		fil = mode == AUMODE_PLAY ? pfil : rfil;
		if (p == NULL)
			continue;

		index = auconv_set_converter(vaudio_audio_formats,
		    __arraycount(vaudio_audio_formats), mode, p, TRUE, fil);
		if (index < 0)
			return EINVAL;
		if (fil->req_size > 0)
			p = &fil->filters[0].param;

		if (mode == AUMODE_PLAY)
			sc->sc_pparam = *p;
		else
			sc->sc_rparam = *p;
	}

	return 0;
}
예제 #3
0
파일: yds.c 프로젝트: ryoon/netbsd-xhci
static int
yds_set_params(void *addr, int setmode, int usemode,
	       audio_params_t *play, audio_params_t* rec,
	       stream_filter_list_t *pfil, stream_filter_list_t *rfil)
{
	if (setmode & AUMODE_RECORD) {
		if (auconv_set_converter(yds_formats, YDS_NFORMATS,
					 AUMODE_RECORD, rec, FALSE, rfil) < 0)
			return EINVAL;
	}
	if (setmode & AUMODE_PLAY) {
		if (auconv_set_converter(yds_formats, YDS_NFORMATS,
					 AUMODE_PLAY, play, FALSE, pfil) < 0)
			return EINVAL;
	}
	return 0;
}
예제 #4
0
static int
auacer_set_params(void *v, int setmode, int usemode,
    audio_params_t *play, audio_params_t *rec, stream_filter_list_t *pfil,
    stream_filter_list_t *rfil)
{
	struct auacer_softc *sc;
	struct audio_params *p;
	stream_filter_list_t *fil;
	uint32_t control;
	int mode, index;

	DPRINTF(ALI_DEBUG_API, ("auacer_set_params\n"));
	sc = v;
	for (mode = AUMODE_RECORD; mode != -1;
	     mode = mode == AUMODE_RECORD ? AUMODE_PLAY : -1) {
		if ((setmode & mode) == 0)
			continue;

		p = mode == AUMODE_PLAY ? play : rec;
		if (p == NULL)
			continue;

		if ((p->sample_rate !=  8000) &&
		    (p->sample_rate != 11025) &&
		    (p->sample_rate != 12000) &&
		    (p->sample_rate != 16000) &&
		    (p->sample_rate != 22050) &&
		    (p->sample_rate != 24000) &&
		    (p->sample_rate != 32000) &&
		    (p->sample_rate != 44100) &&
		    (p->sample_rate != 48000))
			return (EINVAL);

		fil = mode == AUMODE_PLAY ? pfil : rfil;
		index = auconv_set_converter(sc->sc_formats, AUACER_NFORMATS,
					     mode, p, TRUE, fil);
		if (index < 0)
			return EINVAL;
		if (fil->req_size > 0)
			p = &fil->filters[0].param;
		/* p points HW encoding */
		if (sc->sc_formats[index].frequency_type != 1
		    && auacer_set_rate(sc, mode, p->sample_rate))
			return EINVAL;
		if (mode == AUMODE_PLAY) {
			control = READ4(sc, ALI_SCR);
			control &= ~ALI_SCR_PCM_246_MASK;
			if (p->channels == 4)
				control |= ALI_SCR_PCM_4;
			else if (p->channels == 6)
				control |= ALI_SCR_PCM_6;
			WRITE4(sc, ALI_SCR, control);
		}
	}

	return (0);
}
예제 #5
0
static int
fms_set_params(void *addr, int setmode, int usemode,
    audio_params_t *play, audio_params_t *rec, stream_filter_list_t *pfil,
    stream_filter_list_t *rfil)
{
	struct fms_softc *sc;
	int i, index;

	sc = addr;
	if (setmode & AUMODE_PLAY) {
		for (i = 0; i < 10 && play->sample_rate > fms_rates[i].limit;
		     i++)
			continue;
		play->sample_rate = fms_rates[i].rate;
		index = auconv_set_converter(fms_formats, FMS_NFORMATS,
					     AUMODE_PLAY, play, FALSE, pfil);
		if (index < 0)
			return EINVAL;
		sc->sc_play_reg = i << 8;
		if (fms_formats[index].channels == 2)
			sc->sc_play_reg |= FM_PLAY_STEREO;
		if (fms_formats[index].precision == 16)
			sc->sc_play_reg |= FM_PLAY_16BIT;
	}

	if (setmode & AUMODE_RECORD) {
		for (i = 0; i < 10 && rec->sample_rate > fms_rates[i].limit;
		     i++)
			continue;
		rec->sample_rate = fms_rates[i].rate;
		index = auconv_set_converter(fms_formats, FMS_NFORMATS,
					     AUMODE_RECORD, rec, FALSE, rfil);
		if (index < 0)
			return EINVAL;
		sc->sc_rec_reg = i << 8;
		if (fms_formats[index].channels == 2)
			sc->sc_rec_reg |= FM_REC_STEREO;
		if (fms_formats[index].precision == 16)
			sc->sc_rec_reg |= FM_REC_16BIT;
	}

	return 0;
}
예제 #6
0
static int
auich_set_params(void *v, int setmode, int usemode,
    audio_params_t *play, audio_params_t *rec, stream_filter_list_t *pfil,
    stream_filter_list_t *rfil)
{
	struct auich_softc *sc;
	audio_params_t *p;
	stream_filter_list_t *fil;
	int mode, index;
	uint32_t control;

	sc = v;
	for (mode = AUMODE_RECORD; mode != -1;
	     mode = mode == AUMODE_RECORD ? AUMODE_PLAY : -1) {
		if ((setmode & mode) == 0)
			continue;

		p = mode == AUMODE_PLAY ? play : rec;
		fil = mode == AUMODE_PLAY ? pfil : rfil;
		if (p == NULL)
			continue;

		if (sc->sc_codectype == AC97_CODEC_TYPE_AUDIO) {
			if (p->sample_rate <  8000 ||
			    p->sample_rate > 48000)
				return EINVAL;

			if (!sc->sc_spdif)
				index = auconv_set_converter(sc->sc_audio_formats,
				    AUICH_AUDIO_NFORMATS, mode, p, TRUE, fil);
			else
				index = auconv_set_converter(auich_spdif_formats,
				    AUICH_SPDIF_NFORMATS, mode, p, TRUE, fil);
		} else {
			if (p->sample_rate != 8000 && p->sample_rate != 16000)
				return EINVAL;
			index = auconv_set_converter(sc->sc_modem_formats,
			    AUICH_MODEM_NFORMATS, mode, p, TRUE, fil);
		}
		if (index < 0)
			return EINVAL;
		if (fil->req_size > 0)
			p = &fil->filters[0].param;
		/* p represents HW encoding */
		if (sc->sc_codectype == AC97_CODEC_TYPE_AUDIO) {
			if (sc->sc_audio_formats[index].frequency_type != 1
			    && auich_set_rate(sc, mode, p->sample_rate))
				return EINVAL;
		} else {
			if (sc->sc_modem_formats[index].frequency_type != 1
			    && auich_set_rate(sc, mode, p->sample_rate))
				return EINVAL;
			auich_write_codec(sc, AC97_REG_LINE1_RATE,
					  p->sample_rate);
			auich_write_codec(sc, AC97_REG_LINE1_LEVEL, 0);
		}
		if (mode == AUMODE_PLAY &&
		    sc->sc_codectype == AC97_CODEC_TYPE_AUDIO) {
			control = bus_space_read_4(sc->iot, sc->aud_ioh,
			    ICH_GCTRL + sc->sc_modem_offset);
				control &= ~sc->sc_pcm246_mask;
			if (p->channels == 4) {
				control |= sc->sc_pcm4;
			} else if (p->channels == 6) {
				control |= sc->sc_pcm6;
			}
			bus_space_write_4(sc->iot, sc->aud_ioh,
			    ICH_GCTRL + sc->sc_modem_offset, control);
		}
	}

	return 0;
}
예제 #7
0
static int
auvia_set_params(void *addr, int setmode, int usemode,
    audio_params_t *play, audio_params_t *rec, stream_filter_list_t *pfil,
    stream_filter_list_t *rfil)
{
	struct auvia_softc *sc;
	struct auvia_softc_chan *ch;
	struct audio_params *p;
	struct ac97_codec_if* codec;
	stream_filter_list_t *fil;
	int reg, mode;
	int index;

	sc = addr;
	codec = sc->codec_if;
	/* for mode in (RECORD, PLAY) */
	for (mode = AUMODE_RECORD; mode != -1;
	     mode = mode == AUMODE_RECORD ? AUMODE_PLAY : -1) {
		if ((setmode & mode) == 0)
			continue;

		if (mode == AUMODE_PLAY ) {
			p = play;
			ch = &sc->sc_play;
			reg = AC97_REG_PCM_FRONT_DAC_RATE;
			fil = pfil;
		} else {
			p = rec;
			ch = &sc->sc_record;
			reg = AC97_REG_PCM_LR_ADC_RATE;
			fil = rfil;
		}

		if (p->sample_rate < 4000 || p->sample_rate > 48000 ||
		    (p->precision != 8 && p->precision != 16))
			return (EINVAL);
		if (sc->sc_spdif)
			index = auconv_set_converter(auvia_spdif_formats,
			    AUVIA_SPDIF_NFORMATS, mode, p, TRUE, fil);
		else
			index = auconv_set_converter(sc->sc_formats,
			    AUVIA_NFORMATS, mode, p, TRUE, fil);
		if (index < 0)
			return EINVAL;
		if (fil->req_size > 0)
			p = &fil->filters[0].param;
		if (!AC97_IS_FIXED_RATE(codec)) {
			if (codec->vtbl->set_rate(codec, reg, &p->sample_rate))
				return EINVAL;
			reg = AC97_REG_PCM_SURR_DAC_RATE;
			if (p->channels >= 4
			    && codec->vtbl->set_rate(codec, reg,
						     &p->sample_rate))
				return EINVAL;
			reg = AC97_REG_PCM_LFE_DAC_RATE;
			if (p->channels == 6
			    && codec->vtbl->set_rate(codec, reg,
						     &p->sample_rate))
				return EINVAL;
		}
		auvia_set_params_sub(sc, ch, p);
	}

	return 0;
}