Skip to content

Commit b07f7c0

Browse files
jannaumarcan
authored andcommitted
drm: apple: epic: systemep: Parse "mNits" log events
The 13.5 firmware has stopped updating the NITS property on backlight brightness changes. Parse system log events instead which report backlight's brightness in millinits. Fixes the backlight device's "actual_brightness" property used by the systemd backlight service to save and restore brightness. Signed-off-by: Janne Grunau <[email protected]>
1 parent b8904df commit b07f7c0

3 files changed

Lines changed: 94 additions & 0 deletions

File tree

drivers/gpu/drm/apple/parser.c

Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -997,3 +997,51 @@ int parse_sound_mode(struct dcp_parse_ctx *handle,
997997
return 0;
998998
}
999999
EXPORT_SYMBOL_GPL(parse_sound_mode);
1000+
1001+
int parse_system_log_mnits(struct dcp_parse_ctx *handle, struct dcp_system_ev_mnits *entry)
1002+
{
1003+
struct iterator it;
1004+
int ret;
1005+
s64 mnits = -1;
1006+
s64 idac = -1;
1007+
s64 timestamp = -1;
1008+
bool type_match = false;
1009+
1010+
dcp_parse_foreach_in_dict(handle, it) {
1011+
char *key = parse_string(it.handle);
1012+
if (IS_ERR(key)) {
1013+
ret = PTR_ERR(key);
1014+
} else if (!strcmp(key, "mNits")) {
1015+
ret = parse_int(it.handle, &mnits);
1016+
} else if (!strcmp(key, "iDAC")) {
1017+
ret = parse_int(it.handle, &idac);
1018+
} else if (!strcmp(key, "logEvent")) {
1019+
const char * value = parse_string(it.handle);
1020+
if (!IS_ERR_OR_NULL(value)) {
1021+
type_match = strcmp(value, "Display (Event Forward)") == 0;
1022+
kfree(value);
1023+
}
1024+
} else if (!strcmp(key, "timestamp")) {
1025+
ret = parse_int(it.handle, &timestamp);
1026+
} else {
1027+
skip(it.handle);
1028+
}
1029+
1030+
if (!IS_ERR_OR_NULL(key))
1031+
kfree(key);
1032+
1033+
if (ret) {
1034+
pr_err("dcp parser: failed to parse mNits sys event\n");
1035+
return ret;
1036+
}
1037+
}
1038+
1039+
if (!type_match || mnits < 0 || idac < 0 || timestamp < 0)
1040+
return -EINVAL;
1041+
1042+
entry->millinits = mnits;
1043+
entry->idac = idac;
1044+
entry->timestamp = timestamp;
1045+
1046+
return 0;
1047+
}

drivers/gpu/drm/apple/parser.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -126,4 +126,13 @@ int parse_sound_mode(struct dcp_parse_ctx *handle,
126126
struct snd_pcm_chmap_elem *chmap,
127127
struct dcp_sound_cookie *cookie);
128128

129+
struct dcp_system_ev_mnits {
130+
u32 timestamp;
131+
u32 millinits;
132+
u32 idac;
133+
};
134+
135+
int parse_system_log_mnits(struct dcp_parse_ctx *handle,
136+
struct dcp_system_ev_mnits *entry);
137+
129138
#endif

drivers/gpu/drm/apple/systemep.c

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55

66
#include "afk.h"
77
#include "dcp.h"
8+
#include "parser.h"
89

910
static bool enable_verbose_logging;
1011
module_param(enable_verbose_logging, bool, 0644);
@@ -66,6 +67,41 @@ static void powerlog_init(struct apple_epic_service *service, const char *name,
6667
{
6768
}
6869

70+
static int powerlog_report(struct apple_epic_service *service, enum epic_subtype type,
71+
const void *data, size_t data_size)
72+
{
73+
struct dcp_system_ev_mnits mnits;
74+
struct dcp_parse_ctx parse_ctx;
75+
struct apple_dcp *dcp = service->ep->dcp;
76+
int ret;
77+
78+
dev_dbg(dcp->dev, "systemep[ch:%u]: report type:%02x len:%zu\n",
79+
service->channel, type, data_size);
80+
81+
if (type != EPIC_SUBTYPE_STD_SERVICE)
82+
return 0;
83+
84+
ret = parse(data, data_size, &parse_ctx);
85+
if (ret) {
86+
dev_warn(service->ep->dcp->dev, "systemep: failed to parse report: %d\n", ret);
87+
return ret;
88+
}
89+
90+
ret = parse_system_log_mnits(&parse_ctx, &mnits);
91+
if (ret) {
92+
/* ignore parse errors in the case dcp sends unknown log events */
93+
dev_dbg(dcp->dev, "systemep: failed to parse mNits event: %d\n", ret);
94+
return 0;
95+
}
96+
97+
dev_dbg(dcp->dev, "systemep: mNits event: Nits: %u.%03u, iDAC: %u\n",
98+
mnits.millinits / 1000, mnits.millinits % 1000, mnits.idac);
99+
100+
dcp->brightness.nits = mnits.millinits / 1000;
101+
102+
return 0;
103+
}
104+
69105
static const struct apple_epic_service_ops systemep_ops[] = {
70106
{
71107
.name = "system",
@@ -74,6 +110,7 @@ static const struct apple_epic_service_ops systemep_ops[] = {
74110
{
75111
.name = "powerlog-service",
76112
.init = powerlog_init,
113+
.report = powerlog_report,
77114
},
78115
{}
79116
};

0 commit comments

Comments
 (0)