[Apparmor-dev] Network definitions in profile

John Johansen jjohansen at suse.de
Mon Dec 3 14:46:27 MST 2007


On Mon, Dec 03, 2007 at 01:54:51PM +0200, Markku Savela wrote:
> ext John Johansen wrote:
> > On Fri, Nov 30, 2007 at 02:40:11PM +0200, Markku Savela wrote:
> 
> >> socket_recvmsg
> >>
> >>   Socket recvmsg is useless -- it only indicates application is
> >>   ready to receive data (datagram).
> >>
> > hmm, not useless but not important to what you propose.
> 
> As far as I can see from the code, "socket_recvmsg" is direct result
> of application issuing a receive request (read, recv, recvmsg). The
> LSM call does not have any information of the received/pending data,
> there may not even be any data queued for the socket at this
> point. Thus, it cannot be used to check anything against profile,
> except perphaps "is application allowed to read the socket".
> 
yep, it can be used to do a revalidation of socket access, which has
some merit especially when combined with the revocation patches.

> > Hrmm, I am not fond of using the bind keyword (though I am more than
> > willing to be convinced otherwise).  In the older design the binding
> > information is there it is just implicit.  What I would like to see
> > change from the older design is from, to becoming "local" and
> > "remote" so it is easy to determine what is meant.  And then a
> > subset of the full proposal could be used to obtain the binding
> > information.
> 
> I leaned towards using the explicit "bind" keyword to avoid the
> following "fuzzy" problem: using your connect/accept, you can end up
> with following
> 
>   1) network tcp connect to #80 from #1025-65k,
>   2) network tcp accept local #6660-6699
> 
> At the time of "bind", the call does not know whether the socket is
> going to be used for accepting incoming connection or outgoing
> connections. Which of the above lines will bind to port 6667 match
> against?
> 
This little problem is one of the reasons I don't like the idea of
introducing the bind syntax.  It is pushing this fuzzy problem into
the language syntax and in the end making the user care about
binding instead of connections.

> If (1) is chosen, it is incorrect, if socket is actually used for
> incoming connections (no port 80), and if (2) is chosen, it is
> incorrect, if later connect to port 80 follows. Of course, some
> correction might be done at later "connect" or even "listen".
> 
> We could say that "bind" LSM only checks the "accept" lines to solve
> this, but then in the future extension, you might have
> 
>    1) network udp accept local #53 remote 10.0.0/8
>    2) network udp accept #50-100
> 
> Should "bind to port 53" match first or second? It really does not
> have information to accept (1) and if it does, it seems to give wrong
> "assurance" (especially if profile lines include some flow labeling
> tags in future).
> 
This comes back to in order vs. declarative syntax.  One of the
reasons AppArmor treats rules in a declarative fashion is order
doesn't matter and it makes problems like this go away.

What needs to be done for sockets is the partition set needs to be
computed (user side) and a type with read and write permissions
attached to each partition.  The "type" and rw permission mask can
then be used to solve the direction problem.

For the first iteration which approximates bind only (accept rules are
only allowed a local address) the partition set is easy to compute.
The partition set for the next iteration allowing accept rules to specify
remote address is harder to compute but the kernel side only needs
minor extension.

> If the "remote"-clause is not allowed in "accept", above can be
> expressed as
> 
>    1) network udp connect remote 10.0.0/8 from #53
>    2) network udp accept #50-100
> 
> And assume "bind" only checks (2). But, then accept would be a synonym
> of my "bind" keyword, with no other functionality.
> 
correct, for a first implementation this would be functionaly the
same as your "bind" keyword proposal but it doesn't introduce
the extra bind syntax, and has the potential to be extended using
the partition set type/permissions.

> In conclusion, because I felt that "bind LSM hook" can only check
> against very specific lines in profile, I leaned towards explicit
> "bind" instead of generic "accept", which seemed give impression that
> it can express more, but when you try to use is more generally, you
> run into issues presented above.
> 
> I don't say that those issues are not solvable, but it was easier to
> cop out with "bind", rather than try to lay out the rules for generic
> "accept" lines...
> 
understood, and appreciated, and I also think quibbling about the
syntax isn't actually all that important at this stage.  Since
the "bind" syntax version and the limited accept version are
functionally equivalent, I would far rather focus on getting
a working prototype and then playing with the syntax.

> 
> ---------------
> Some minor notes on remaining texts..
> 
> > This makes the bind information implicit as part of the rules still
> > leaves us open to do rules like,
> > 
> >   network tcp connect to #80 from #1025-65k,
> > 
> > for connections we can figure out the bind source allowed and have
> > the pairing without relying on netfilter.
> 
> Just a note: this would seem to cover the automatic source port
> assignment. However, in such case the connect LSM does not know the
> source port (without explicit bind, the source port is still undefined
> at that point). With above rule the connect LSM hook would have to
> reject all outgoing HTTP connections (because they usually don't use
> bind and the unspecified port would not match 1024-65k)
> 
unfortunately yes, the ability to limit like this has to come as a
later step.  Think of it as an eventual goal.  This specific limitation
may have to be done in the netfilter postroute hook.

> >> - could the algorithms used in file path matching utilized somehow
> >>   (e.g. can the network profiles be turned into file path like
> >>   constructs that can be processed and matched with existing
> >>   functions within apparmor kernel module).
> >>
> > yes.  It requires some user side work, a lot of which I have been
> > doing anyways to make the dfa code more general.  The data could be
> > represented as an ordered string but it would be even better to
> > treat it in a binary fashion so that the kernel doesn't need to
> > build up a string to match against.
> 
> For the "string match" approach, the port range expression might be a
> challenge (unless your DFA matching can include binary in range
> operation for integers in the "match string"). Similarly, the network
> prefix match could be problematic, if the prefix length is not
> multiple of 8 bits.
> 
well I am still unsure whether the dfa is the best approach but neither
of these are a real problem.  Range matching is done as a multilevel state
byte match.  So for example if the range is being done on a 16 bite number
(ports).  It is a two level match first against the msb then the lsb.

Conceptually for every number in the msb that is in range transitions to
the lsb match state every other number is a transition to a none match state.
The lsb match is similar with number that are in range going to a match state
and non-matches going to a none match state.

Of course in practice it will seldom collapse to 2 states as the msb may
need to transition to several different lsb accept states, dependant on
overlaps, and lsb ranges not being the same (think the start of a range
and end of a range are probably different than the middle where the
lsb match will be all 256 states).  Thankfully the dfa code already
handles computing the overlaps and properly splitting states.  It would
just require a function to add the proper important states per rule.

The prefix length problem is similar and not really any harder, instead
of basing the accept state transition based on a range you do it based on
whether the byte segment in the number matches the byte mask.
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 194 bytes
Desc: not available
Url : http://forge.novell.com/pipermail/apparmor-dev/attachments/20071203/3c538ff1/attachment.pgp


More information about the Apparmor-dev mailing list