~aleteoryx/muditaos

ref: 8fe0f2c79a1e40e133dd3026972feecd1868c85d muditaos/module-bsp/devices/power/MP2639B.cpp -rw-r--r-- 3.6 KiB
8fe0f2c7 — Paweł Joński [BH-655] SideListView - Remove dead code 4 years ago
                                                                                
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md

#include "MP2639B.hpp"

namespace bsp::devices::power
{
    MP2639B::MP2639B(const Configuration &conf) : configuration{conf}
    {
        irq_filter_timer =
            xTimerCreate("irq_charger_filter", pdMS_TO_TICKS(500), pdFALSE, this, [](TimerHandle_t xTimer) {
                MP2639B *inst = static_cast<MP2639B *>(pvTimerGetTimerID(xTimer));
                inst->configuration.notification(inst->get_charge_status());
            });

        drivers::DriverGPIOPinParams mode_pin_params{};
        mode_pin_params.dir      = drivers::DriverGPIOPinParams::Direction::Output;
        mode_pin_params.irqMode  = drivers::DriverGPIOPinParams::InterruptMode::NoIntmode;
        mode_pin_params.defLogic = 0;
        mode_pin_params.pin      = configuration.mode_pin;
        configuration.mode_gpio->ConfPin(mode_pin_params);

        /// Set the initial charging state
        enable_charging(configuration.acok_gpio->ReadPin(configuration.acok_pin) == 0u);
    }

    MP2639B::~MP2639B()
    {
        xTimerDelete(irq_filter_timer, pdMS_TO_TICKS(100));
        configuration.chgok_gpio->DisableInterrupt(1 << configuration.chgok_pin);
        configuration.acok_gpio->DisableInterrupt(1 << configuration.acok_pin);

        enable_charging(false);
    }
    MP2639B::ChargingStatus MP2639B::get_charge_status()
    {
        ChargingStatus status{};

        const auto acok  = configuration.acok_gpio->ReadPin(configuration.acok_pin);
        const auto chgok = configuration.chgok_gpio->ReadPin(configuration.chgok_pin);

        if (acok == 1 && chgok == 1) {
            status = ChargingStatus::Discharging;
        }
        else if (acok == 0 && chgok == 0) {
            status = ChargingStatus::Charging;
        }
        else if (acok == 0 && chgok == 1) {
            status = ChargingStatus::Complete;
        }
        // TODO: add error condition, i.e when chgok blinks at 1Hz
        return status;
    }
    void MP2639B::enable_charging(bool ctrl)
    {
        if (ctrl) {
            configuration.mode_gpio->WritePin(configuration.mode_pin, 0);
        }
        else {
            configuration.mode_gpio->WritePin(configuration.mode_pin, 1);
        }
    }
    void MP2639B::enable_irq()
    {
        drivers::DriverGPIOPinParams ACOKPinConfig{};
        ACOKPinConfig.dir      = drivers::DriverGPIOPinParams::Direction::Input;
        ACOKPinConfig.irqMode  = drivers::DriverGPIOPinParams::InterruptMode::IntRisingOrFallingEdge;
        ACOKPinConfig.defLogic = 0;
        ACOKPinConfig.pin      = configuration.acok_pin;
        configuration.acok_gpio->ConfPin(ACOKPinConfig);

        drivers::DriverGPIOPinParams CHGOKPinConfig{};
        CHGOKPinConfig.dir      = drivers::DriverGPIOPinParams::Direction::Input;
        CHGOKPinConfig.irqMode  = drivers::DriverGPIOPinParams::InterruptMode::IntRisingOrFallingEdge;
        CHGOKPinConfig.defLogic = 0;
        CHGOKPinConfig.pin      = configuration.chgok_pin;
        configuration.chgok_gpio->ConfPin(CHGOKPinConfig);

        /* Enable interrupts */
        configuration.chgok_gpio->EnableInterrupt(1U << configuration.chgok_pin);
        configuration.acok_gpio->EnableInterrupt(1U << configuration.acok_pin);
    }

    void MP2639B::handle_irq()
    {
        enable_charging(configuration.acok_gpio->ReadPin(configuration.acok_pin) == 0u);

        if (xTimerIsTimerActive(irq_filter_timer) == pdFALSE) {
            xTimerStart(irq_filter_timer, pdMS_TO_TICKS(100));
        }
    }

} // namespace bsp::devices::power