From c71a6614e2c46e35d1796191c8fb04d9fb1071b0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?J=C3=A9r=C3=B4me=20Duval?= Date: Thu, 1 Jan 2009 17:13:43 +0000 Subject: [PATCH] * try to enable EAPD on capable pin widgets * added a pin capabilities attribute instead of input and output pin attributes * added ATI and nVidia vendor ids definitions * uses "mic in" and "line in" when pin colors are undefined git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@28839 a95241bf-73f2-0310-859d-f6bbb57e9c96 --- src/add-ons/kernel/drivers/audio/hda/driver.h | 3 +- .../kernel/drivers/audio/hda/hda_codec.cpp | 33 ++++++++++++++----- .../kernel/drivers/audio/hda/hda_codec_defs.h | 13 ++++++-- .../drivers/audio/hda/hda_controller.cpp | 6 ++-- .../drivers/audio/hda/hda_controller_defs.h | 5 +++ .../drivers/audio/hda/hda_multi_audio.cpp | 9 +++-- 6 files changed, 50 insertions(+), 19 deletions(-) diff --git a/src/add-ons/kernel/drivers/audio/hda/driver.h b/src/add-ons/kernel/drivers/audio/hda/driver.h index 61042a0a60..6ccb8cffb5 100644 --- a/src/add-ons/kernel/drivers/audio/hda/driver.h +++ b/src/add-ons/kernel/drivers/audio/hda/driver.h @@ -216,8 +216,7 @@ struct hda_widget { struct { } mixer; struct { - uint32 output; - uint32 input; + uint32 capabilities; uint32 config; } pin; } d; diff --git a/src/add-ons/kernel/drivers/audio/hda/hda_codec.cpp b/src/add-ons/kernel/drivers/audio/hda/hda_codec.cpp index 797d39f375..78d31f6214 100644 --- a/src/add-ons/kernel/drivers/audio/hda/hda_codec.cpp +++ b/src/add-ons/kernel/drivers/audio/hda/hda_codec.cpp @@ -168,8 +168,8 @@ dump_audiogroup_widgets(hda_audio_group* audioGroup) break; case WT_PIN_COMPLEX: - dprintf("\t%s%s\n", widget.d.pin.input ? "[Input] " : "", - widget.d.pin.output ? "[Output]" : ""); + dprintf("\t%s%s\n", PIN_CAP_IS_INPUT(widget.d.pin.capabilities) ? "[Input] " : "", + PIN_CAP_IS_OUTPUT(widget.d.pin.capabilities) ? "[Output]" : ""); break; @@ -586,11 +586,10 @@ hda_codec_parse_audio_group(hda_audio_group* audioGroup) verbs[0] = MAKE_VERB(audioGroup->codec->addr, nodeID, VID_GET_PARAMETER, PID_PIN_CAP); if (hda_send_verbs(audioGroup->codec, verbs, resp, 1) == B_OK) { - widget.d.pin.input = resp[0] & PIN_CAP_IN; - widget.d.pin.output = resp[0] & PIN_CAP_OUT; - - dprintf("\t%s%s\n", widget.d.pin.input ? "[Input] " : "", - widget.d.pin.output ? "[Output]" : ""); + widget.d.pin.capabilities = resp[0]; + + dprintf("\t%s%s\n", PIN_CAP_IS_INPUT(resp[0]) ? "[Input] " : "", + PIN_CAP_IS_OUTPUT(resp[0]) ? "[Output]" : ""); } else { dprintf("%s: Error getting Pin Complex IO\n", __func__); } @@ -689,7 +688,7 @@ hda_widget_find_input_path(hda_audio_group* audioGroup, hda_widget* widget, if (widget->flags & WIDGET_FLAG_INPUT_PATH) return false; - if (widget->d.pin.input) { + if (PIN_CAP_IS_INPUT(widget->d.pin.capabilities)) { switch (CONF_DEFAULT_DEVICE(widget->d.pin.config)) { case PIN_DEV_CD: case PIN_DEV_LINE_IN: @@ -743,7 +742,7 @@ dprintf("build output tree: %suse mixer\n", useMixer ? "" : "don't "); for (uint32 i = 0; i < audioGroup->widget_count; i++) { hda_widget& widget = audioGroup->widgets[i]; - if (widget.type != WT_PIN_COMPLEX || !widget.d.pin.output) + if (widget.type != WT_PIN_COMPLEX || !PIN_CAP_IS_OUTPUT(widget.d.pin.capabilities)) continue; int device = CONF_DEFAULT_DEVICE(widget.d.pin.config); @@ -957,6 +956,22 @@ dprintf("ENABLE pin widget %ld\n", widget.node_id); PIN_ENABLE_HEAD_PHONE | PIN_ENABLE_OUTPUT : PIN_ENABLE_INPUT); hda_send_verbs(audioGroup->codec, &verb, NULL, 1); + + if (PIN_CAP_IS_EAPD_CAP(widget.d.pin.capabilities)) { + uint32 result; + verb = MAKE_VERB(audioGroup->codec->addr, + widget.node_id, VID_GET_EAPDBTL_EN, 0); + if (hda_send_verbs(audioGroup->codec, &verb, + &result, 1) == B_OK) { + result &= 0xff; + verb = MAKE_VERB(audioGroup->codec->addr, + widget.node_id, VID_SET_EAPDBTL_EN, + result | EAPDBTL_ENABLE_EAPD); + hda_send_verbs(audioGroup->codec, + &verb, NULL, 1); +dprintf("ENABLE EAPD pin widget %ld\n", widget.node_id); + } + } } if (widget.capabilities.output_amplifier != 0) { diff --git a/src/add-ons/kernel/drivers/audio/hda/hda_codec_defs.h b/src/add-ons/kernel/drivers/audio/hda/hda_codec_defs.h index 23ce1c1cab..7fd32b1d82 100644 --- a/src/add-ons/kernel/drivers/audio/hda/hda_codec_defs.h +++ b/src/add-ons/kernel/drivers/audio/hda/hda_codec_defs.h @@ -214,8 +214,8 @@ enum pin_dev_type { #define PIN_CAP_TRIGGER_REQ (1L << 1) #define PIN_CAP_PRES_DETECT (1L << 2) #define PIN_CAP_HP_DRIVE (1L << 3) -#define PIN_CAP_OUT (1L << 4) -#define PIN_CAP_IN (1L << 5) +#define PIN_CAP_OUTPUT (1L << 4) +#define PIN_CAP_INPUT (1L << 5) #define PIN_CAP_BALANCE (1L << 6) #define PIN_CAP_VREF_CTRL_HIZ (1L << 8) #define PIN_CAP_VREF_CTRL_50 (1L << 9) @@ -224,6 +224,10 @@ enum pin_dev_type { #define PIN_CAP_VREF_CTRL_100 (1L << 13) #define PIN_CAP_EAPD_CAP (1L << 16) +#define PIN_CAP_IS_OUTPUT(c) ((c & PIN_CAP_OUTPUT) != 0) +#define PIN_CAP_IS_INPUT(c) ((c & PIN_CAP_INPUT) != 0) +#define PIN_CAP_IS_EAPD_CAP(c) ((c & PIN_CAP_EAPD_CAP) != 0) + /* PCM support */ #define PCM_8_BIT (1L << 16) #define PCM_16_BIT (1L << 17) @@ -297,6 +301,11 @@ enum pin_dev_type { #define CONF_DEFAULT_LOCATION(c) ((c & CONF_DEFAULT_LOCATION_MASK) >> CONF_DEFAULT_LOCATION_SHIFT) #define CONF_DEFAULT_CONNECTIVITY(c) ((c & CONF_DEFAULT_CONNECTIVITY_MASK) >> CONF_DEFAULT_CONNECTIVITY_SHIFT) +/* EAPD/BTL enable */ +#define EAPDBTL_ENABLE_BTL 0x1 +#define EAPDBTL_ENABLE_EAPD 0x2 +#define EAPDBTL_ENABLE_LRSWAP 0x4 + /* GP I/O count */ #define GPIO_COUNT_NUM_GPIO_MASK 0x000000ff #define GPIO_COUNT_NUM_GPIO_SHIFT 0 diff --git a/src/add-ons/kernel/drivers/audio/hda/hda_controller.cpp b/src/add-ons/kernel/drivers/audio/hda/hda_controller.cpp index 4e06050a71..6445cd81b4 100644 --- a/src/add-ons/kernel/drivers/audio/hda/hda_controller.cpp +++ b/src/add-ons/kernel/drivers/audio/hda/hda_controller.cpp @@ -744,13 +744,11 @@ hda_hw_init(hda_controller* controller) /* Enable snooping for ATI and Nvidia, right now for all their hda-devices, but only based on guessing. */ switch (controller->pci_info.vendor_id) { - /* NVIDIA */ - case 0x10de: + case NVIDIA_VENDORID: update_pci_register(controller, NVIDIA_HDA_TRANSREG, NVIDIA_HDA_TRANSREG_MASK, NVIDIA_HDA_ENABLE_COHBITS); break; - /* ATI */ - case 0x1002: + case ATI_VENDORID: update_pci_register(controller, ATI_HDA_MISC_CNTR2, ATI_HDA_MISC_CNTR2_MASK, ATI_HDA_ENABLE_SNOOP); break; diff --git a/src/add-ons/kernel/drivers/audio/hda/hda_controller_defs.h b/src/add-ons/kernel/drivers/audio/hda/hda_controller_defs.h index 84da5e397c..73bb852273 100644 --- a/src/add-ons/kernel/drivers/audio/hda/hda_controller_defs.h +++ b/src/add-ons/kernel/drivers/audio/hda/hda_controller_defs.h @@ -142,6 +142,11 @@ #define NVIDIA_HDA_TRANSREG_MASK 0xf0 #define NVIDIA_HDA_ENABLE_COHBITS 0x0f +#define ATI_VENDORID 0x1002 +#define INTEL_VENDORID 0x8086 +#define NVIDIA_VENDORID 0x10de + + typedef uint32 corb_t; typedef struct { diff --git a/src/add-ons/kernel/drivers/audio/hda/hda_multi_audio.cpp b/src/add-ons/kernel/drivers/audio/hda/hda_multi_audio.cpp index aaee5177bb..edf0ed8288 100644 --- a/src/add-ons/kernel/drivers/audio/hda/hda_multi_audio.cpp +++ b/src/add-ons/kernel/drivers/audio/hda/hda_multi_audio.cpp @@ -305,6 +305,11 @@ hda_find_multi_custom_string(hda_widget& widget) case 9: return "Mic in"; } + if (CONF_DEFAULT_DEVICE(widget.d.pin.config) == PIN_DEV_LINE_IN) + return "Line In"; + if (CONF_DEFAULT_DEVICE(widget.d.pin.config) == PIN_DEV_MIC_IN) + return "Mic In"; + return "Line Out"; break; case PIN_DEV_SPDIF_IN: return "SPDIF In"; @@ -382,7 +387,7 @@ hda_create_controls_list(hda_multi *multi) if (complex.type != WT_PIN_COMPLEX) continue; - if (!complex.d.pin.output) + if (!PIN_CAP_IS_OUTPUT(complex.d.pin.capabilities)) continue; if ((complex.flags & WIDGET_FLAG_OUTPUT_PATH) == 0) continue; @@ -412,7 +417,7 @@ hda_create_controls_list(hda_multi *multi) hda_widget *complex = hda_audio_group_get_widget(audioGroup, widget.inputs[j]); if (complex->type != WT_PIN_COMPLEX) continue; - if (!complex->d.pin.input) + if (!PIN_CAP_IS_INPUT(complex->d.pin.capabilities)) continue; if (complex->flags & WIDGET_FLAG_OUTPUT_PATH) continue;