Skip to content
  • Kuppuswamy Sathyanarayanan's avatar
    mfd: intel_soc_pmic_bxtwc: Use chained IRQs for second level IRQ chips · 57129044
    Kuppuswamy Sathyanarayanan authored
    
    
    Whishkey cove PMIC has support to mask/unmask interrupts at two levels.
    At first level we can mask/unmask interrupt domains like TMU, GPIO, ADC,
    CHGR, BCU THERMAL and PWRBTN and at second level, it provides facility
    to mask/unmask individual interrupts belong each of this domain. For
    example, in case of TMU, at first level we have TMU interrupt domain,
    and at second level we have two interrupts, wake alarm, system alarm that
    belong to the TMU interrupt domain.
    
    Currently, in this driver all first level IRQs are registered as part of
    IRQ chip(bxtwc_regmap_irq_chip). By default, after you register the IRQ
    chip from your driver, all IRQs in that chip will masked and can only be
    enabled if that IRQ is requested using request_irq() call. This is the
    default Linux IRQ behavior model. And whenever a dependent device that
    belongs to PMIC requests only the second level IRQ and not explicitly
    unmask the first level IRQ, then in essence the second level IRQ will
    still be disabled. For example, if TMU device driver request wake_alarm
    IRQ and not explicitly unmask TMU level 1 IRQ then according to the default
    Linux IRQ model,  wake_alarm IRQ will still be disabled. So the proper
    solution to fix this issue is to use the chained IRQ chip concept. We
    should chain all the second level chip IRQs to the corresponding first
    level IRQ. To do this, we need to create separate IRQ chips for every
    group of second level IRQs.
    
    In case of TMU, when adding second level IRQ chip, instead of using PMIC
    IRQ we should use the corresponding first level IRQ. So the following
    code will change from
    
    ret = regmap_add_irq_chip(pmic->regmap, pmic->irq, ...)
    
    to,
    
    virq = regmap_irq_get_virq(&pmic->irq_chip_data, BXTWC_TMU_LVL1_IRQ);
    
    ret = regmap_add_irq_chip(pmic->regmap, virq, ...)
    
    In case of Whiskey Cove Type-C driver, Since USBC IRQ is moved under
    charger level2 IRQ chip. We should use charger IRQ chip(irq_chip_data_chgr)
    to get the USBC virtual IRQ number.
    
    Signed-off-by: default avatarKuppuswamy Sathyanarayanan <sathyanarayanan.kuppuswamy@linux.intel.com>
    Reviewed-by: default avatarAndy Shevchenko <andy.shevchenko@gmail.com>
    Revieved-by: default avatarHeikki Krogerus <heikki.krogerus@linux.intel.com>
    Signed-off-by: default avatarLee Jones <lee.jones@linaro.org>
    57129044