Discussion:
if_flags
(too old to reply)
der Mouse
2009-01-26 21:25:33 UTC
Permalink
I'd like to add some new IFF_ flags. But if_flags is short, and all 16
bits are already in use.

How much of a pain would it be to grow it? struct ifnet is prepared
for it; if_flags is 32-bit-aligned and the next field after it is a pad
field. I know it isn't a problem for NetBSD per se, because I've
already done this to my 1.4T tree, but there are often considerations I
never think of because of the various ways my usage patterns are
unusual, hence this note.

I'm prepared to do the work (and quite likely will do it anyway for my
own use), but I'd like to get it into the tree if it wouldn't cause
trouble.

/~\ The ASCII Mouse
\ / Ribbon Campaign
X Against HTML ***@rodents-montreal.org
/ \ Email! 7D C8 61 52 5D E7 2D 39 4E F1 31 3E E8 B3 27 4B

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Joerg Sonnenberger
2009-01-26 21:38:19 UTC
Permalink
Post by der Mouse
How much of a pain would it be to grow it? struct ifnet is prepared
for it; if_flags is 32-bit-aligned and the next field after it is a pad
field.
As long as you add a second field, it should not be a problem. If you
want to make if_flags itself 32bit, you have to deal with endianess,
don't you?

Joerg

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
der Mouse
2009-01-26 21:42:55 UTC
Permalink
How much of a pain would it be to grow [if_flags]? struct ifnet is
prepared for it; if_flags is 32-bit-aligned and the next field after
it is a pad field.
As long as you add a second field, it should not be a problem. If
you want to make if_flags itself 32bit, you have to deal with
endianess, don't you?
I can't see why; if_flags doesn't appear anywhere where endianness is
relevant as far as I know (no wire protocols, for example). I didn't
have any endianness issues when just growing the field on 1.4T, and I
use hardware of each endianness regularly. And if endianness mattered,
wouldn't we have such issues today with the existing field, since it's
already more than one byte?

/~\ The ASCII Mouse
\ / Ribbon Campaign
X Against HTML ***@rodents-montreal.org
/ \ Email! 7D C8 61 52 5D E7 2D 39 4E F1 31 3E E8 B3 27 4B

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Quentin Garnier
2009-01-27 00:00:00 UTC
Permalink
Post by der Mouse
How much of a pain would it be to grow [if_flags]? struct ifnet is
prepared for it; if_flags is 32-bit-aligned and the next field after
it is a pad field.
As long as you add a second field, it should not be a problem. If
you want to make if_flags itself 32bit, you have to deal with
endianess, don't you?
I can't see why; if_flags doesn't appear anywhere where endianness is
relevant as far as I know (no wire protocols, for example). I didn't
have any endianness issues when just growing the field on 1.4T, and I
use hardware of each endianness regularly. And if endianness mattered,
wouldn't we have such issues today with the existing field, since it's
already more than one byte?
I'd say it matters for binary compatibility. However it's not that
important for ifnet anyway. Exposing the new flags to userland will be
a different issue though, given the way ifreq works.
--
Quentin Garnier - ***@cubidou.net - ***@NetBSD.org
"See the look on my face from staying too long in one place
[...] every time the morning breaks I know I'm closer to falling"
KT Tunstall, Saving My Face, Drastic Fantastic, 2007.
der Mouse
2009-01-27 00:32:01 UTC
Permalink
[cube quoting me quoting joerg]
Post by Quentin Garnier
If you want to make if_flags itself 32bit, you have to deal with
endianess, don't you?
I can't see why; [...]
I'd say it matters for binary compatibility.
Ooh, good point. (I knew there'd be something I hadn't thought of.
Binary compat often fails to occur to me because I always build from
source. It takes rare cases like running under a new OS rev before
rebuilding everything for me to run into binary compat issues.)

I guess growing if_flags (as opposed to adding if_flags2 or some such
the way gdt wrote of) would mean versioning all the ioctls, sockopts,
sysctls, whatever, that handle IFF_ bitmasks, whether in struct ifnet
or not.

I guess I'll do it privately, then, same as I did for 1.4T, and ignore
the binary compat issue because I'll be rebuilding everything anyway.
If we can come to a consensus on a right way for the main tree, perhaps
my work can be a starting point....

[gdt]
Post by Quentin Garnier
Are you thinking of bringing this up with the FreeBSD, OpenBSD and
Dragonfly folks?
I haven't been, not yet.
Post by Quentin Garnier
It would be nice to keep the API the same among *BSD.
The API for interface flags is rather ill-defined, is my impression.
It is not clear to me whether there is a spec that defines the type of
fields that hold IFF_* interface flags; as I recall there were very few
things that needed to be grown when I did this to 1.4T, so what little
evidence I have indicates that the de-facto API wouldn't change much.
(I've never seen anything like a real API spec for this stuff; I don't
know whether this is because one doesn't exist or because I just
haven't looked in the right place.)

The ABI is another story. See above for that.
Post by Quentin Garnier
In my private work, I added a flag SEMIBROADCAST [...]
I wanted to add NOFWFROM and NOFWTO, to provide per-interface control
over packet forwarding (what net.inet.ip.forwarding and
net.inet6.ip6.forwarding control on a per-system basis, basically).
These are two of the flags whose addition prompted my growing if_flags
on 1.4T. (The others are BPFONLY and DOT1Q, the former meaning "call
bpf but don't do any further receive processing" for snooper interfaces
that should never ever receive packets except via bpf, the latter for
my vlan tagging support.)

I have looked closer, and the immediate need for them has evaporated.
But I still think if_flags should grow; having no room for expansion is
a Bad Thing. :)

/~\ The ASCII Mouse
\ / Ribbon Campaign
X Against HTML ***@rodents-montreal.org
/ \ Email! 7D C8 61 52 5D E7 2D 39 4E F1 31 3E E8 B3 27 4B

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Greg Troxel
2009-01-27 01:07:15 UTC
Permalink
Post by der Mouse
Post by Quentin Garnier
It would be nice to keep the API the same among *BSD.
The API for interface flags is rather ill-defined, is my impression.
It is not clear to me whether there is a spec that defines the type of
fields that hold IFF_* interface flags; as I recall there were very few
things that needed to be grown when I did this to 1.4T, so what little
evidence I have indicates that the de-facto API wouldn't change much.
(I've never seen anything like a real API spec for this stuff; I don't
know whether this is because one doesn't exist or because I just
haven't looked in the right place.)
The API is defined in the 4.4BSD sources :-) I'm semi-serious; there has
to my knowledge been fairly little divergence.
der Mouse
2009-01-27 04:27:03 UTC
Permalink
Post by Greg Troxel
Post by der Mouse
Post by Quentin Garnier
It would be nice to keep the API the same among *BSD.
The API for interface flags is rather ill-defined, is my impression.
The API is defined in the 4.4BSD sources :-) I'm semi-serious; there
has to my knowledge been fairly little divergence.
The 4.4BSD sources are not an API spec any more than the NetBSD sources
are.

To cite the example at readiest hand in this thread: are the API fields
bearing interface flags (eg, struct ifreq .ifr_flags) defined to be
unsigned shorts, or are they defined to be some unsigned integral type
no larger than unsigned long int, or what? If the former, converting
them to uint32_t is an API change; if the latter, it is not (note,
discussing API, not ABI, here). And this is not a question that can be
answered by inspecting sources - unless there's a comment lurking
somewhere that talks about it, and while there may be such comments for
a few such fields, I've read enough of the code to be fairly sure most
of them have none.

/~\ The ASCII Mouse
\ / Ribbon Campaign
X Against HTML ***@rodents-montreal.org
/ \ Email! 7D C8 61 52 5D E7 2D 39 4E F1 31 3E E8 B3 27 4B

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Robert Elz
2009-01-27 06:35:17 UTC
Permalink
Date: Mon, 26 Jan 2009 23:27:03 -0500 (EST)
From: der Mouse <***@Rodents-Montreal.ORG>
Message-ID: <***@Sparkle.Rodents-Montreal.ORG>

| The 4.4BSD sources are not an API spec any more than the NetBSD sources
| are.

They are, both of them. They may not be in the form you'd like,
or as accessible or precise as you'd like, but they are a specification,
and they are defining an API (and an ABI).

| To cite the example at readiest hand in this thread: are the API fields
| bearing interface flags (eg, struct ifreq .ifr_flags) defined to be
| unsigned shorts, or are they defined to be some unsigned integral type
| no larger than unsigned long int, or what?

They are exactly whatever the 4.4 if.h file says they are. That's the
spec. Not some other type that might be kind of similar to the one
actually used in the struct definition. But that exact one. Change
from short to unsigned short and you've altered the API.

| And this is not a question that can be
| answered by inspecting sources - unless there's a comment lurking
| somewhere that talks about it,

You're assuming that a specification must be written in English.
It doesn't. Would you be claiming there is no spec if the only
document you could find was written in French? Or Chinese?
If those languages are acceptable, then why not C? If anything
it is likely to be more precise, as it has to be interpreted by
compilers, not just the (we hope) more intelligent humans.

Or it may be that you're assuming that it wasn't necessarily intended
to be,a nd perhapd doesn't need to be, as precise as it is, and that may
be true - but once it became the spec, its precision (needed or not)
came along with it - we don't get to ignore bits and just claim that part
doesn't really matter. Or not unless we're also willing to simply
decide we're going to break conformance.

Now, given all that, this is an area where some API change is
probably acceptable. We need to care about binary compat via the
syscall interface, but internally I think this is fair game.

We badly need a simple, well defined "interface works" flag,
the way that has been described for FreeBSD and Linux (the
link status NetBSD currently has is better for humans, but much
harder to interpret for software that just wants a working/not-working
status). Whether that should be IFF_RUNNING or not I don't know,
but if other people have done it that way... (It is interesting that
nat-snmp did, and I think still does, treat IFF_RUNNING as "admin up"
(ie: what is really IFF_UP) and treats IFF_UP as "working" - then given
that lo0 has no need for IFF_RUNNING we end up with an interface that
net-snmp thinks is administrativey down, but working anyway...)

I have always hoped that there are a few flags that have no logical use
outside the kernel (perhaps IFF_OACTIVE, IFF_RUNNING with its original
meaning, maybe some of the other internal flags that communicate little
useful information to the outside world) that could be moved to a different
flags word without upsetting anyone at all (to keep the API they could
remain defined with value 0 (outside the kernel), so they'd just never appear
to be set to anything that tests them) then those 2 (or more) bits could get
used for more flags where application/kernel interface is needed. That way
we avoid significant API and ABI changes, but get to add a few extra
essential flags.

I had understood that this kind of decision was made in some kind of
mysterious way as a co-operation between all the BSD's (and perhaps
linux too) which was always beyond my comprehension, so I've never
bothered suggesting it. But if we're seriously considering playing
around (in even a small way) with ifnet data, then, this would be the
time...

kre


--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
der Mouse
2009-01-27 08:27:52 UTC
Permalink
Post by der Mouse
To cite the example at readiest hand in this thread: are the API
fields bearing interface flags (eg, struct ifreq .ifr_flags) defined
to be unsigned shorts, or are they defined to be some unsigned
integral type no larger than unsigned long int, or what?
They are exactly whatever the 4.4 if.h file says they are. That's
the spec. Not some other type that might be kind of similar to the
one actually used in the struct definition. But that exact one.
Change from short to unsigned short and you've altered the API.
Then the API consists of the source code *with that specification*.

The source code alone is not enough; it does not define whether that
"short" is "this field is defined to have this type" or "this field is
defined to have certain characteristics, and this type is one of the
possibilities". The example I gave was an instance of this: if I see
"unsigned short if_flags;", that could have resulted from either of the
specs I cited (amogn others), and without additional information I, the
person reading the code to deduce the API, have no way to tell which.

A well-designed API often has things which are _not_ specified (with,
of course, clearly defined boundaries). The "unsigned integral type
not larger than unsigned long" example is the kind of thing I mean.
Post by der Mouse
And this is not a question that can be answered by inspecting
sources - unless there's a comment lurking somewhere that talks
about it,
You're assuming that a specification must be written in English.
Actually, I'm not. I'm just pointing out that C code, by itself, is
not a good spec; it needs some additional other language (probably a
natural language) to supplement it, for reasons outlined above. An
English spec that provided no more information than the C code ("the
ifr_flags is implemented as unsigned short") would be as bad a spec as
the code itself ("unsigned short ifr_flags") is.
If anything [the code] is likely to be more precise [than a
natural-language spec],
Yes, except that it's an implementation, not a spec. Good specs
constrain the implementation in some respects and leave it latitude in
others, but looking at just an implementation does not give any
indication of how much latitude is permitted. (Looking at multiple
disparate implementations can, under the assumption that they all
conform, but that's not what's under discussion here.)
Or it may be that you're assuming that it wasn't necessarily intended
to be,a nd perhapd doesn't need to be, as precise as it is,
Well, of course. If the spec were as precise as you're making it out
to be, there would be exactly one possible implementation - the spec
one - and never any change (for example, all implementations would
forever be required to reject anything the reference implementation
rejects, in the same way; this would make it impossible to, for
example, add new socket options).

/~\ The ASCII Mouse
\ / Ribbon Campaign
X Against HTML ***@rodents-montreal.org
/ \ Email! 7D C8 61 52 5D E7 2D 39 4E F1 31 3E E8 B3 27 4B

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Robert Elz
2009-01-27 12:22:40 UTC
Permalink
Date: Tue, 27 Jan 2009 03:27:52 -0500 (EST)
From: der Mouse <***@Rodents-Montreal.ORG>
Message-ID: <***@Sparkle.Rodents-Montreal.ORG>

| A well-designed API ...

| Actually, I'm not. I'm just pointing out that C code, by itself, is
| not a good spec; ...

(etc). Who said anything about a good spec, or a well designed API.
I doubt anyone would claim the ifnet struct, and its flags, are anything
even close to that.

Not well designed, not good, but still an API, and in fact, the API
that is currently used.

| Yes, except that it's an implementation, not a spec.

It is both. Having one thing be both is not all that uncommon.
It might not be desirable, but it happens a lot.

kre


--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Christos Zoulas
2009-01-27 17:00:43 UTC
Permalink
Post by Joerg Sonnenberger
Post by der Mouse
How much of a pain would it be to grow it? struct ifnet is prepared
for it; if_flags is 32-bit-aligned and the next field after it is a pad
field.
As long as you add a second field, it should not be a problem. If you
want to make if_flags itself 32bit, you have to deal with endianess,
don't you?
I don't think that there is a binary compatibility issue since ifnet
is not used in ioctls from what I can see.

christos


--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
der Mouse
2009-01-27 17:27:47 UTC
Permalink
Post by Christos Zoulas
How much of a pain would it be to grow [ifnet.if_flags]?
I don't think that there is a binary compatibility issue since ifnet
is not used in ioctls from what I can see.
Strictly, true, but this is not for internal flags but for flags
userland needs to be able to manipulate, which means that it really
applies not just to if_flags but other places that carry IFF_* flags,
such as ifreq.ifr_flags. Done simplistically, it would indeed be an
ABI change.

/~\ The ASCII Mouse
\ / Ribbon Campaign
X Against HTML ***@rodents-montreal.org
/ \ Email! 7D C8 61 52 5D E7 2D 39 4E F1 31 3E E8 B3 27 4B

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Joerg Sonnenberger
2009-01-27 17:19:55 UTC
Permalink
Post by Christos Zoulas
Post by Joerg Sonnenberger
Post by der Mouse
How much of a pain would it be to grow it? struct ifnet is prepared
for it; if_flags is 32-bit-aligned and the next field after it is a pad
field.
As long as you add a second field, it should not be a problem. If you
want to make if_flags itself 32bit, you have to deal with endianess,
don't you?
I don't think that there is a binary compatibility issue since ifnet
is not used in ioctls from what I can see.
Seems to be, so only some of the usual kvm users are involved.

Joerg

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
der Mouse
2009-01-27 21:49:00 UTC
Permalink
Post by Robert Elz
Not well designed, not good, but still an API, and in fact, the API
that is currently used.
Well, speaking of "the spec" or "the API" is a bit fuzzy. There are
many specs the current code is an implementation of, and I see no
particular reason to pick the one "everything is exactly as in this
reference implementation" as "the" API. On the benefit side, it's
well-specified; on the detriment side, it's over-specified, to the
point of stagnation.

Indeed, typedefs like bpf_int32 (<net/bpf.h>), n_short
(<netinet/in_systm.h>), and tcp_seq (<netinet/tcp.h>) argue that the
"this reference implementation _is_ the spec" stance is wrong, that
code that knows what the underlying type is and uses it is broken, even
though it conforms to the kind of reference-implementation API
pseudo-spec you seem to be arguing for here.

Anyway, this appears to be a tempest-in-a-teapot, in that what I intend
to do is a ABI change and thus is unlikely to go into the tree in the
simplistic form I, at least, have been discussing here. (It's probably
what I'll implement, and might even serve as the basis for some in-tree
work someday, but that's far from the same thing.)

/~\ The ASCII Mouse
\ / Ribbon Campaign
X Against HTML ***@rodents-montreal.org
/ \ Email! 7D C8 61 52 5D E7 2D 39 4E F1 31 3E E8 B3 27 4B

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Greg Troxel
2009-01-27 00:07:20 UTC
Permalink
I'd like to add some new IFF_ flags. But if_flags is short, and all 16
bits are already in use.

Many others have the same sorts of feelings.

I did this once, hackishly, in private code by adding if_flags2 to
ifreq, stealing the pad, and thus maintaining compatibility sort of.

Two thoughts:

how to do binary compat for the field becoming 32 bits. I am not sure
how much needs to be versioned.

Are you thinking of bringing this up with the FreeBSD, OpenBSD and
Dragonfly folks? It would be nice to keep the API the same among
*BSD. I have no idea if there is a Darwin community any more, but
perhaps someone from Apple is listening.

In quagga the issue has come up that Linux and maybe Solaris treat
IFF_RUNNING differently. The historical BSD usage is that it's an
internal "resources have been allocated" flag, and not useful to user
space. So they have repurposed it for link detect, but can only
represent down and [up|can't-tell], rather than the BSD link detect
interface's ability to have all three.

In my private work, I added a flag SEMIBROADCAST that was set on
BROADCAST interfaces that didn't have the semantics of a full
connectivity matrix. An example is 802.11 IBSS mode, but BSS mode is
not SEMIBROADCAST.
Christos Zoulas
2009-01-27 17:00:06 UTC
Permalink
Post by der Mouse
I'd like to add some new IFF_ flags. But if_flags is short, and all 16
bits are already in use.
How much of a pain would it be to grow it? struct ifnet is prepared
for it; if_flags is 32-bit-aligned and the next field after it is a pad
field. I know it isn't a problem for NetBSD per se, because I've
already done this to my 1.4T tree, but there are often considerations I
never think of because of the various ways my usage patterns are
unusual, hence this note.
I'm prepared to do the work (and quite likely will do it anyway for my
own use), but I'd like to get it into the tree if it wouldn't cause
trouble.
Does not look like a problem to me.

christos


--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Loading...