Let's put the problem in place : we have the (veryveryvery) generic scheme: | | +---------+ | | Decider | | +---------+ | ^ | | (1) | V | +-------+ user space | +--| hooks |---+ | | +-------+ | App ----+-->| Syscall code | | +--------------+ The question is : what is the arrow (1) ? In other words what is the semantic behind such calls to the decider ? Your approach was to say that the decider had to answer to : "Can 'current' exec <syscall> with <parameters>" I'll prefer "Can 'current' do <type-of-action> with <object(s)>" even if it seems very MAC-oriented Do we need to intercept each file-related syscall to enforce simple rules like "Nobody write into /sbin" ? What about considering as a 1st approximation to replace every call to permission : ./fs/open.c: error = permission(inode,MAY_WRITE); ./fs/open.c: (error = permission(inode,MAY_WRITE)) != 0) ./fs/open.c: if ((error = permission(inode,MAY_WRITE)) != 0) ./fs/open.c: res = permission(nd.dentry->d_inode, mode); [...] ./fs/exec.c: error = permission(nd.dentry->d_inode, MAY_READ | MAY_EXEC); ./fs/exec.c: int err = permission(inode, MAY_EXEC); ./fs/exec.c: permission(bprm->file->f_dentry->d_inode,MAY_READ)) ./fs/super.c: if (permission(nd->dentry->d_inode, MAY_WRITE)) [...] and every call to capable() : ./fs/read_write.c: if (inode && S_ISBLK(inode->i_mode) && (!capable(CAP_SYS_RAWIO))) ./fs/read_write.c: if (inode && S_ISBLK(inode->i_mode) && (!capable(CAP_SYS_RAWIO))) { ./fs/buffer.c: if (!capable(CAP_SYS_ADMIN)) { ./fs/open.c: if (!capable(CAP_SYS_CHROOT)) { ./fs/open.c: if (capable(CAP_SYS_TTY_CONFIG)) { [...] by a call to a function with could implement the already existing scurity model : DAC and capabilities. The behaviour is quite simple : the function must have enough parameters to know what action is intended to do : ("write to this inode", "being ADMIN capable",..) and know the subject (let's keep on with the MAC terminology :)) because we are in process context. All what is needed to do is comparing some security policy data stored in the current task struct (current->uid, euid, cap_permitted...) with what is needed to be allowed to do the action. No more than what is already done. The next step would be to * transform this function is something like a hub, with a register()... * add a place for more fine grained security policy data in the task struct * add a hook for inheritage rules of security policy data. * reimplement the same security model using the new place in task struct (instead of ->uid,..), the hook of inheritage, and the hub function -- Philippe Biondi Systems administrator Webmotion Inc. http://www.webmotion.com mailto:philippe.biondiat_private Fax. (613) 260-9545 _______________________________________________ linux-security-module mailing list linux-security-moduleat_private http://mail.wirex.com/mailman/listinfo/linux-security-module
This archive was generated by hypermail 2b30 : Sat Apr 14 2001 - 01:10:04 PDT