Hi Matthias, Matthias Behr wrote: > Hi Greg, > > I got a few review comments/questions. Pls see below. > > Best Regards, > Matthias > > P.S. I'm a kernel newbie so don't hesitate to tell me if I'm wrong ;-) > > >> +/** >> + * pi_sink_init - initialize a pi_sink before use >> + * @sink: a sink context >> + * @ops: pointer to an pi_sink_ops structure >> + */ >> +static inline void >> +pi_sink_init(struct pi_sink *sink, struct pi_sink_ops *ops) >> +{ >> + atomic_set(&sink->refs, 0); >> + sink->ops = ops; >> +} >> > > Shouldn't ops be tested for 0 here? (ASSERT/BUG_ON/...) (get's dereferenced later quite often in the form "if (sink->ops->...)". > This is a good idea. I will add this. > >> +/** >> + * pi_sink_put - down the reference count, freeing the sink if 0 >> + * @node: the node context >> + * @flags: optional flags to modify behavior. Reserved, must be 0. >> + * >> + * Returns: none >> + */ >> +static inline void >> +pi_sink_put(struct pi_sink *sink, unsigned int flags) >> +{ >> + if (atomic_dec_and_test(&sink->refs)) { >> + if (sink->ops->free) >> + sink->ops->free(sink, flags); >> + } >> +} >> > > Shouldn't the atomic/locked part cover the ...->free(...) as well? Actually, it already does. The free can only be called by the last reference dropping the ref-count. > A pi_get right after the atomic_dec_and_test but before the free() could lead to a free() with refs>0? > A pi_get() after the ref could have already dropped to zero is broken at a higher layer. E.g. the caller of pi_get() has to ensure that there are no races against the reference dropping to begin with. This is the same as any reference-counted object (for instance, see get_task_struct()). Thanks for the review, Matthias! Regards, -Greg