Re: [PATCH 2/3] rbtree: update augmented data on the way down in rb_add_augmented_cached()
From: Yiwei Lin
Date: Mon Sep 28 2026 - 15:15:59 EST
On 2026/09/28 22:05, Peter Zijlstra wrote:
> > And that is *very* close to being generalizable, obviating the need for
> > RBCOMPUTE. Does your LLM see a way to make that happen?
>
> Perhaps by doing something like so?
[...]
> #define RB_DECLARE_CALLBACKS_MULTI(RBSTATIC, RBNAME, \
> - RBSTRUCT, RBFIELD, RBCOPY, RBCOMPUTE) \
> + RBSTRUCT, RBFIELD, RBCOMPUTE, RBAUG...) \
Yes, and since RBCOMPUTE is always "reset the fields to the node's own contribution,
then fold in each child". I think we can also generalize it with RBMERGE, by
adding one extra RBINIT:
static inline void min_vruntime_init(struct sched_entity *se)
{
se->min_vruntime = se->vruntime;
se->min_slice = se->slice;
se->max_slice = se->slice;
}
So the original RBCOMPUTE can be generated by the template instead, which allow us to
remove min_vruntime_update.
static inline bool RBNAME ## _compute(RBSTRUCT *node) \
{ \
typeof(node->RBAUGMENTED) aug; \
RBSTRUCT *child; \
\
RBINIT(node, &aug); \
if (node->RBFIELD.rb_left) { \
child = rb_entry(node->RBFIELD.rb_left, RBSTRUCT, RBFIELD); \
RBMERGE(&aug, &child->RBAUGMENTED); \
} \
if (node->RBFIELD.rb_right) { \
child = rb_entry(node->RBFIELD.rb_right, RBSTRUCT, RBFIELD); \
RBMERGE(&aug, &child->RBAUGMENTED); \
} \
if (!memcmp(&aug, &node->RBAUGMENTED, sizeof(aug))) \
return true; \
node->RBAUGMENTED = aug; \
return false; \
} \
Base on this I have another idea: can we let augmented data becomes one member and
init/merge just work on its type by value. Taking sched for example:
struct_group_tagged(sched_aug, aug,
u64 min_vruntime;
u64 min_slice;
u64 max_slice;
);
So fair.c's se->min_vruntime etc. can stay as they are, we don't have to rely on the
FOR_EACH machinery. Do you think this can be better or do you prefer the field-list form?
Thanks,
Yiwei Lin