Skip to content

Commit 891e830

Browse files
Merge pull request #1043 from FrameworkComputer/marigold.battery_customize_batt
marigold: add customize battery cmd for GRL
2 parents d0caa52 + 2c81b87 commit 891e830

5 files changed

Lines changed: 225 additions & 5 deletions

File tree

zephyr/program/framework/Kconfig

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -96,12 +96,28 @@ config PD_CCG6_WAIT_STABLE_TIMER
9696
EC should wait X ms the PD chip run in stable mode then start to
9797
communicate.
9898

99+
config PD_CCG6_CUSTOMIZE_BATT_MESSAGE
100+
bool "Enable CCG6 Customize battery response"
101+
default n
102+
depends on PD_CHIP_CCG6
103+
help
104+
Enable customize battery response for GRL test, EC will write specific
105+
register 0x4f to PD for GET_BATTERY_CAP and GET_BATTERY_STATUS.
106+
99107
config PD_COMMON_VBUS_CONTROL
100108
bool "Enable CCG common vbus control"
101109
help
102110
Enable Cypress CCG common vbus control, if not enable please modify
103111
board_set_active_charge_port at board for customize vbus control.
104112

113+
config PD_COMMON_EXTENDED_MESSAGE
114+
bool "Enable CCG common extended message"
115+
default n
116+
help
117+
Enable Cypress CCG common extended message, if we need send message to PD
118+
please add the response for extended message.
119+
ex: get battery status or capability.
120+
105121
config PLATFORM_SIMPLE_VERSION_SHIFT_IDX
106122
int "Shift idx for return commit id to BIOS"
107123
default 18

zephyr/program/framework/include/cypress_pd_common.h

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,9 @@
2020
#define CCG_I2C_CHIP1 0x40
2121
#endif
2222

23+
#define PRODUCT_ID CONFIG_PD_USB_PID
24+
#define VENDOR_ID 0x32ac
25+
2326
#define BB_PWR_DOWN_TIMEOUT (4000*MSEC)
2427

2528
/*
@@ -57,6 +60,9 @@
5760
#define CCG_DPM_CMD_REG 0x004C
5861
#define CCG_MUX_CFG_REG 0x004D
5962
#define CCG_DEINIT_PORT_REG 0x004E
63+
#ifdef CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE
64+
#define CCG_BATTERT_STATE 0x004F
65+
#endif /* CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE */
6066
#endif
6167
#define CCG_ICL_STS_REG 0x0042
6268
#define CCG_ICL_BB_RETIMER_CMD_REG 0x0046
@@ -225,6 +231,13 @@
225231
#ifdef CONFIG_PD_CHIP_CCG6
226232
#define CCG6_AC_AT_PORT 0xC4
227233
#define CCG_ICL_CTRL_REG 0x0040
234+
235+
#ifdef CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE
236+
#define CCG6_BATT_IS_PRESENT BIT(1)
237+
#define CCG6_BATT_IS_DISCHARGING BIT(2)
238+
#define CCG6_BATT_IS_IDLE BIT(3)
239+
#endif /* CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE */
240+
228241
#endif
229242

230243
/************************************************/
@@ -526,6 +539,30 @@ struct pd_chip_ucsi_info_t {
526539
int wait_ack;
527540
};
528541

542+
#ifdef CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE
543+
544+
/**
545+
* follow CCG6 vendor Format
546+
* byte[0] - reg, 0x0 = batt_cap, 0x01 = batt_status.
547+
* ohters byte follow PD Spec format
548+
*/
549+
struct pd_battery_cap_t {
550+
uint8_t reg;
551+
uint16_t vid;
552+
uint16_t pid;
553+
uint16_t design_cap;
554+
uint16_t last_full_cap;
555+
uint8_t battery_type;
556+
} __packed;
557+
558+
struct pd_battery_status_t {
559+
uint8_t reg;
560+
uint8_t reserved;
561+
uint8_t battery_info;
562+
uint16_t batt_present_cap;
563+
} __packed;
564+
#endif /* CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE */
565+
529566
/**
530567
* extern struct for ccg6 or ccg8 use.
531568
*/
@@ -679,6 +716,19 @@ int cypd_reconnect_port_enable(int controller);
679716
void cypd_reconnect(void);
680717

681718
#endif /* CONFIG_PD_CCG6_ERROR_RECOVERY */
719+
720+
#ifdef CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE
721+
/**
722+
* Set battery_cap info to PD
723+
*/
724+
void cypd_customize_battery_cap(void);
725+
726+
/**
727+
* Set battery_status info to PD
728+
*/
729+
void cypd_customize_battery_status(void);
730+
#endif /* CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE */
731+
682732
#endif /* CONFIG_PD_CHIP_CCG6 */
683733

684734
/**

zephyr/program/framework/marigold/project.conf

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@ CONFIG_THIRD_PARTY_CUSTOMIZED_DESIGN=y
3838
CONFIG_CHIPSET_INTEL=y
3939
CONFIG_PD_CHIP_CCG6=y
4040
CONFIG_PD_CCG6_WAIT_STABLE_TIMER=415
41+
CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE=y
4142

4243
# PECI
4344
CONFIG_PECI=y

zephyr/program/framework/src/cypd_ccg6.c

Lines changed: 139 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -550,3 +550,142 @@ int check_tbt_mode(int controller)
550550

551551
return data;
552552
}
553+
554+
#ifdef CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE
555+
/*****************************************************************
556+
* Customize response battery status
557+
****************************************************************/
558+
559+
static struct pd_battery_cap_t pd_battery_cap;
560+
static struct pd_battery_status_t pd_battery_status;
561+
static int pd_batt_soc;
562+
bool cypd_batt_update;
563+
564+
void cypd_customize_battery_cap(void)
565+
{
566+
int i;
567+
uint32_t c, v;
568+
bool battery_can_discharge = (battery_is_present() == BP_YES) &
569+
battery_get_disconnect_state();
570+
571+
/* only send status when PD ready */
572+
if (!(pd_chip_config[0].state == CCG_STATE_READY &&
573+
pd_chip_config[1].state == CCG_STATE_READY)) {
574+
return;
575+
}
576+
577+
if (!battery_can_discharge) {
578+
cypd_batt_update = false;
579+
pd_battery_cap.design_cap = 0x0000;
580+
pd_battery_cap.last_full_cap = 0x0000;
581+
pd_battery_cap.battery_type = 0x1;
582+
583+
} else {
584+
cypd_batt_update = true;
585+
pd_battery_cap.reg = 0;
586+
pd_battery_cap.vid = VENDOR_ID;
587+
pd_battery_cap.pid = PRODUCT_ID;
588+
pd_battery_cap.battery_type = 0x0;
589+
590+
if (battery_design_voltage(&v) == 0) {
591+
if (battery_design_capacity(&c) == 0) {
592+
/*
593+
* Wh = (c * v) / 1000000
594+
* 10th of a Wh = Wh * 10
595+
*/
596+
pd_battery_cap.design_cap = DIV_ROUND_NEAREST((c * v),
597+
100000);
598+
}
599+
if (battery_full_charge_capacity(&c) == 0) {
600+
/*
601+
* Wh = (c * v) / 1000000
602+
* 10th of a Wh = Wh * 10
603+
*/
604+
pd_battery_cap.last_full_cap = DIV_ROUND_NEAREST((c * v),
605+
100000);
606+
}
607+
}
608+
}
609+
610+
for (i = 0; i < PD_CHIP_COUNT; i++)
611+
cypd_write_reg_block(i, CCG_BATTERT_STATE,
612+
&pd_battery_cap, sizeof(pd_battery_cap));
613+
614+
}
615+
616+
void cypd_customize_battery_status(void)
617+
{
618+
int i, soc_wh;
619+
uint8_t batt_info;
620+
uint32_t c, v;
621+
struct batt_params batt;
622+
bool battery_can_discharge = (battery_is_present() == BP_YES) &
623+
battery_get_disconnect_state();
624+
625+
battery_get_params(&batt);
626+
627+
/* only send status when PD ready */
628+
if (!(pd_chip_config[0].state == CCG_STATE_READY &&
629+
pd_chip_config[1].state == CCG_STATE_READY)) {
630+
return;
631+
}
632+
633+
/* only update data when soc change */
634+
if (batt.state_of_charge == pd_batt_soc)
635+
return;
636+
637+
pd_batt_soc = batt.state_of_charge;
638+
639+
if (!battery_can_discharge) {
640+
641+
pd_battery_status.reg = 0x1;
642+
pd_battery_status.battery_info = 0;
643+
pd_battery_status.batt_present_cap = 0xFFFF;
644+
645+
} else {
646+
647+
/**
648+
* if battery didn't set cap info at first time pd init
649+
* need set again when battery ready.
650+
* ex: resume from dead battery, or ac only boot and then plug-in batt
651+
*/
652+
if (!cypd_batt_update)
653+
cypd_customize_battery_cap();
654+
655+
if (battery_design_voltage(&v) == 0) {
656+
if (battery_remaining_capacity(&c) == 0) {
657+
/*
658+
* Wh = (c * v) / 1000000
659+
* 10th of a Wh = Wh * 10
660+
*/
661+
soc_wh = DIV_ROUND_NEAREST((c * v), 100000);
662+
}
663+
}
664+
665+
if (battery_status(&c) != 0) {
666+
batt_info = 0; /* batt not present */
667+
} else {
668+
if (c & STATUS_FULLY_CHARGED)
669+
/* Fully charged */
670+
batt_info = CCG6_BATT_IS_IDLE | CCG6_BATT_IS_PRESENT;
671+
else if (c & STATUS_DISCHARGING)
672+
/* Discharging */
673+
batt_info = CCG6_BATT_IS_DISCHARGING | CCG6_BATT_IS_PRESENT;
674+
else
675+
/* else battery is charging.*/
676+
batt_info = CCG6_BATT_IS_PRESENT;
677+
}
678+
679+
pd_battery_status.reg = 0x1;
680+
pd_battery_status.battery_info = batt_info;
681+
pd_battery_status.batt_present_cap = soc_wh;
682+
}
683+
684+
for (i = 0; i < PD_CHIP_COUNT; i++)
685+
cypd_write_reg_block(i, CCG_BATTERT_STATE,
686+
&pd_battery_status, sizeof(pd_battery_status));
687+
688+
}
689+
DECLARE_HOOK(HOOK_AC_CHANGE, cypd_customize_battery_status, HOOK_PRIO_DEFAULT);
690+
DECLARE_HOOK(HOOK_BATTERY_SOC_CHANGE, cypd_customize_battery_status, HOOK_PRIO_DEFAULT);
691+
#endif /* CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE */

zephyr/program/framework/src/cypress_pd_common.c

Lines changed: 19 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -37,10 +37,6 @@
3737
#define CPRINTS(format, args...) cprints(CC_USBCHARGE, format, ##args)
3838
#define CPRINTF(format, args...) cprintf(CC_USBCHARGE, format, ##args)
3939

40-
41-
#define PRODUCT_ID CONFIG_PD_USB_PID
42-
#define VENDOR_ID 0x32ac
43-
4440
#undef CCG_INIT_STATE
4541
#ifdef CONFIG_PD_CHIP_CCG6
4642
#define CCG_INIT_STATE CCG_STATE_WAIT_STABLE
@@ -687,6 +683,7 @@ static void cypd_ppm_port_clear(void)
687683
hook_call_deferred(&pdo_init_deferred_data, 1);
688684
}
689685

686+
#ifdef CONFIG_PD_COMMON_EXTENDED_MESSAGE
690687
/*
691688
* send a message using DM_CONTROL to port partner
692689
* pd_header is using chromium PD header with upper bits defining SOP type
@@ -745,6 +742,7 @@ void cypd_send_msg(int controller, int port, uint32_t pd_header, uint16_t ext_hd
745742
cypd_write_reg16(controller, CCG_DM_CONTROL_REG(port), dm_control_data);
746743
}
747744

745+
748746
void cypd_response_get_battery_capability(int controller, int port,
749747
uint32_t pd_header, enum tcpci_msg_type sop_type)
750748
{
@@ -942,6 +940,7 @@ int cypd_handle_extend_msg(int controller, int port, int len, enum tcpci_msg_typ
942940

943941
return rv;
944942
}
943+
#endif
945944

946945
static void clear_port_state(int controller, int port)
947946
{
@@ -1194,6 +1193,15 @@ __overridable void cypd_customize_app_setup(int controller)
11941193
*/
11951194
}
11961195

1196+
#ifdef CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE
1197+
static void pd_batt_init_deferred(void)
1198+
{
1199+
cypd_customize_battery_cap();
1200+
cypd_customize_battery_status();
1201+
}
1202+
DECLARE_DEFERRED(pd_batt_init_deferred);
1203+
#endif /* CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE */
1204+
11971205
static void cypd_handle_state(int controller)
11981206
{
11991207
int data;
@@ -1259,8 +1267,12 @@ static void cypd_handle_state(int controller)
12591267
gpio_enable_interrupt(pd_chip_config[controller].gpio);
12601268

12611269
/* Update PDO format after init complete */
1262-
if (controller)
1270+
if (controller) {
1271+
#ifdef CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE
1272+
hook_call_deferred(&pd_batt_init_deferred_data, 100 * MSEC);
1273+
#endif /* CONFIG_PD_CCG6_CUSTOMIZE_BATT_MESSAGE */
12631274
hook_call_deferred(&pdo_init_deferred_data, 25 * MSEC);
1275+
}
12641276

12651277
CPRINTS("CYPD %d Ready!", controller);
12661278
pd_chip_config[controller].state = CCG_STATE_READY;
@@ -1642,8 +1654,10 @@ void cypd_port_int(int controller, int port)
16421654
sop_type = TCPCI_MSG_SOP_PRIME;
16431655
else if (data2[0] == CCG_RESPONSE_EXT_MSG_SOP_RX)
16441656
sop_type = TCPCI_MSG_SOP_PRIME_PRIME;
1657+
#ifdef CONFIG_PD_COMMON_EXTENDED_MESSAGE
16451658
cypd_handle_extend_msg(controller, port, response_len, sop_type);
16461659
CPRINTS("CYP_RESPONSE_RX_EXT_MSG");
1660+
#endif /* CONFIG_PD_COMMON_EXTENDED_MESSAGE */
16471661
break;
16481662
case CCG_RESPONSE_OVER_CURRENT:
16491663
CPRINTS("CCG_RESPONSE_OVER_CURRENT %d", port_idx);

0 commit comments

Comments
 (0)