From: Eric Blake <eblake@redhat.com>
To: "qemu-devel@nongnu.org" <qemu-devel@nongnu.org>
Subject: [Qemu-devel] DO_UPCAST confusion
Date: Wed, 21 Oct 2015 16:49:32 -0600 [thread overview]
Message-ID: <5628167C.9020802@redhat.com> (raw)
[-- Attachment #1: Type: text/plain, Size: 2324 bytes --]
In include/qemu/compiler.h, we have this gem:
> #ifndef container_of
> #define container_of(ptr, type, member) ({ \
> const typeof(((type *) 0)->member) *__mptr = (ptr); \
> (type *) ((char *) __mptr - offsetof(type, member));})
> #endif
>
> /* Convert from a base type to a parent type, with compile time checking. */
> #ifdef __GNUC__
> #define DO_UPCAST(type, field, dev) ( __extension__ ( { \
> char __attribute__((unused)) offset_must_be_zero[ \
> -offsetof(type, field)]; \
> container_of(dev, type, field);}))
> #else
> #define DO_UPCAST(type, field, dev) container_of(dev, type, field)
> #endif
That comment is horrible. In object-oriented programming, there are two
common sets of terminology:
base and derived classes (derived adds on to base)
parent and child classes (child inherits from parent)
Going from "base type" to "parent type" makes NO SENSE, since those two
terms are synonyms between the two terminologies.
Furthermore, according to these references:
https://programmers.stackexchange.com/questions/148615/what-is-upcasting-downcasting
http://en.wikipedia.org/wiki/Downcasting
the act of going from a base class to a derived class (or from a parent
type to a child type) is considered downcasting. Yet our definition of
DO_UPCAST is used to go from a base class to the derived class.
Example usage in blockdev.c is to declare a derived class:
> /* internal snapshot private data */
> typedef struct InternalSnapshotState {
> BlkTransactionState common;
...
> };
then to take a generic parent pointer and convert it into the derived type:
> static void internal_snapshot_prepare(BlkTransactionState *common,
> Error **errp)
> {
...
> InternalSnapshotState *state;
...
> state = DO_UPCAST(InternalSnapshotState, common, common);
I much prefer the name container_of() (which is a bit more obvious that
it is finding the container or derived type that embeds the parent
type), but if we have to keep the ugly name, could we at least clean up
the comment to make sense, and fix the name to be DO_DOWNCAST to match
what it is actually doing?
--
Eric Blake eblake redhat com +1-919-301-3266
Libvirt virtualization library http://libvirt.org
[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 604 bytes --]
next reply other threads:[~2015-10-21 22:49 UTC|newest]
Thread overview: 7+ messages / expand[flat|nested] mbox.gz Atom feed top
2015-10-21 22:49 Eric Blake [this message]
2015-10-22 7:26 ` [Qemu-devel] DO_UPCAST confusion Gerd Hoffmann
2015-10-22 9:58 ` Peter Maydell
2015-10-22 12:00 ` Markus Armbruster
2015-10-22 13:55 ` Eric Blake
2015-10-22 14:00 ` Paolo Bonzini
2015-10-22 14:48 ` Markus Armbruster
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=5628167C.9020802@redhat.com \
--to=eblake@redhat.com \
--cc=qemu-devel@nongnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).