全志TYPE-C使用介绍

有无TYPE-C方案,主从识别和耳机的插拔检测不同;有TYPE-C情况下,主要为TYPE-C逻辑进行侦测;而没有TYPE-C的方案;主从区分需要USB-ID detect管脚进行判断,耳机则靠HP-DET进行区分;

传统侦测方式

主从侦测

usb_id_detect

在没有TYPE-C的硬件上,主要靠USB-ID管脚的上下拉来区分主从;

耳机侦测

耳机结构

3.5mm耳机插头有三段(TRS,Tip-Ring-Sleeve)和四段(TRRS,Tip-Ring-Sleeve)之分,其中三段的不带麦克风,尾段(Sleeve)是公共地;中间环(Ring)是右声道,尖部(Tip)是左声道,四节的分两种,一种是CTIA,一种是OMTP;

耳机结构

HP-L耳机左声道,HP-R耳机右声道,GND接地,V-Mic语音麦克风

耳机座以及传统耳机侦测介绍

耳机座分为支持欧标设计的耳机座和支持美标的耳机座。另外从耳机座左声道的检测方式来又可以分为”Normal-closed type”(常闭型)和“Normal -type”(常开型)两种。设计图如下:

耳机座子

. 在常闭型中,不接耳机时,耳机座左声道和检测端HS-DET接触,接入耳机时,HS-DET与HPH-L不导通

. 在常开型中,不接耳机时,耳机座左声道和检测端HS-DET不接触,插入耳机时,HS-DET与HPH-L导通

耳机侦测电路

如图为常开型结构,HP-DET上拉,当插入耳机后HP-DET和HP-OUTL导通,DET下拉引起软件中断。软件上通过debounce后,检测到持续的低电平,于是认为耳机插入;这时候需要判断,插入的还是三段还是四段,平台上打开mic_bias,当插入的是三段耳机,MIC被拉低,于是判断为三段耳机;若为四段耳机,MIC接近于MIC_BIAS,软件判断该处的直流电压为四段耳机;当按键按下时,MIC的电压发生变化,触发了系统中断,之后软件通过采样该处的电压值确定按下了哪一个按键;

TYPE-C方案侦测方式讲解

TYPE-C主要电路如下

TYPE-C关键电路

Type-C连接并没有在物理结构上区分DFP(Host)和UFP(Device),无连接时DFP未给VBUS供电,连接后通过CC信号线配置,确认连接有效,VBUS供电打开并确认使用哪一个端口传输数据;
状态说明

cc_logic

如图所示

DFP的CC1/CC2会接上拉电阻Rp或电流源,UFP的CC1/CC2会接下拉电阻Rd,AUDIO设备则会接两个下拉电阻

如何确认当前TYPE_C接入设备类型:

echo 1 > /sys/class/axp/axp_num
echo 0x37 > /sys/class/axp_reg && cat /sys/class/axp/axp_reg

若读出状态为ATTACH_SNK 说明接入的是适配器或pc
若读出的状态为ATTACH_SOURCE 说明此时作为host
如读出为AUDIO_ACSY,说明此时为音频设备

type_c_detect

TS5USBA224RSWR

用于将D-,D+在(USB0-DM,USB0-DP),(HPOUTL,HPOUTR)两种模式之间切换;由于VBUS默认低后,无法满足通过SEL切换状态,故VBUS一般设置为高;通过ASEL来设置高低实现切换

TS3A226AE:

可以用于区分三四节耳机,并且可以将MIC和GROUND区分出来,降低软件设计复杂度;

使用TYPE-C方案时,TYPE-C 中断服务程序负责将D-,D+选择为USB模式的Dp,Dm或者为耳机模式HP-OUTL,HP-OUTR;并通知音频驱动耳机接入;

软件流程为:

一:bmu驱动产生中断:

irqreturn_t axp_tc_in_isr(int irq, void *data)
{
    struct axp_charger_dev *chg_dev = data;
    #ifdef CONFIG_TYPE_C_AUDIO
    struct axp_usb_info *usb = chg_dev->spy_info->usb;
    u8 cc_mode = 0; 
    /*axp_usbac_in(chg_dev);*/
    cc_mode = usb->get_cc_mode(chg_dev); //获取cc 侦测结果
    if (cc_mode == AUDIO_ACSY) {    //如果为音频设备
            usb->set_sel_mode(chg_dev, 1);  //D+ D- 连接到耳机的左右声道
            call_notifier_call_chain(1);    //通知耳机驱动耳机接入
    } else {
            usb->set_sel_mode(chg_dev, 0); //D+ D- 连接到 USB的 Dp,Dm口
            call_notifier_call_chain(0);   //通知耳机驱动拔出
    }    
    #endif
    axp_change(chg_dev);
    return IRQ_HANDLED;
}

二:耳机接受到通知:

static int type_c_chain_notify(struct notifier_block *nb, unsigned long mode, void *_unused)
{
    struct mc_private *ctx = container_of(nb, struct mc_private, type_c_chain_nb);

    if (mode) {
            ctx->detect_state = PLUG_IN; //切换接入状态
            printk("%s PLUG_IN", __func__);
    } else {
            ctx->detect_state = PLUG_OUT;
            printk("%s PLUG_OUT", __func__);
    }

    schedule_delayed_work(&ctx->hs_detect_work,
                            msecs_to_jiffies(10)); //执行音频相关的处理函数
    return 0;
}

软件配置demo

使能TYPE-C SINK与SOURCE 检测功能:

一:sys_config.fex中:

usb_id_gpio = "axp_ctrl"

二:deconfig中

CONFIG_TYPE_C=y

使能TYPE-C耳机功能

一:如原理图所示,使用的是PH10作为选通管脚,故对pmu_typc_c_sel进行配置

[charger0]
 compatible                 = "bmu1760-charger"
pmu_type_c_sel             = port:PH10<1><default><default><0>
 pmu_chg_ic_temp            = 0
pmu_battery_rdc            = 100
 pmu_battery_cap            = 4200

二:deconfig中

CONFIG_TYPE_C_AUDIO=y