Main Page | Namespace List | Class Hierarchy | Class List | Directories | File List | Namespace Members | Class Members | File Members

AccessControl.H

Go to the documentation of this file.
00001 // Copyright (C) 2001, Compaq Computer Corporation
00002 // 
00003 // This file is part of Vesta.
00004 // 
00005 // Vesta is free software; you can redistribute it and/or
00006 // modify it under the terms of the GNU Lesser General Public
00007 // License as published by the Free Software Foundation; either
00008 // version 2.1 of the License, or (at your option) any later version.
00009 // 
00010 // Vesta is distributed in the hope that it will be useful,
00011 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00012 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00013 // Lesser General Public License for more details.
00014 // 
00015 // You should have received a copy of the GNU Lesser General Public
00016 // License along with Vesta; if not, write to the Free Software
00017 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00018 
00019 //
00020 // AccessControl.H
00021 //
00022 
00023 #ifndef _AccessControl
00024 #define _AccessControl 1
00025 
00026 #include "Basics.H"
00027 #include "VestaAttribs.H"
00028 #include "VestaConfig.H"
00029 #include "CharsSeq.H"
00030 #include <PwGrp.H>
00031 #include <chars_seq.H>
00032 #include <sys/types.h>
00033 #include <rpc/types.h>
00034 #include <rpc/xdr.h>
00035 #include <rpc/auth.h>
00036 #include <rpc/auth_unix.h>
00037 
00038 // Forward declaration of functions uder with pthread_once (which must
00039 // have C linkage).
00040 extern "C"
00041 {
00042   void AccessControl_commonInit_inner() throw();
00043   void AccessControl_selfInit_inner() throw();
00044 }
00045 
00046 //
00047 // Access control list for a Vesta source
00048 //
00049 class AccessControl {
00050  public:
00051   //
00052   // Nested class for the identity of a principal
00053   //
00054   class IdentityRep {
00055   protected:
00056     CharsSeq *users_cache, *groups_cache;
00057     virtual void fill_caches()  throw() = 0;
00058 
00059     IdentityRep() : users_cache(0), groups_cache(0) { }
00060   public:
00061     // Flavor of credentials used.  "unspecified" is not a valid
00062     // flavor; it is used as a special flag in various places.
00063 
00064     // (Just "unix" is often a pre-defined macro, so we use
00065     // "unix_flavor instead.)
00066     enum Flavor { unix_flavor, global, gssapi,
00067                   nflavors=3, unspecified=255 };
00068     Flavor flavor;
00069     
00070     // Host of origin
00071     sockaddr_in origin;
00072 
00073     // Global user names.  Primary name is 0th.
00074     // Returns NULL after users are exhausted.
00075     virtual const char* user(int n = 0) throw (); // shared, do not free
00076 
00077     // Global group names.  Primary name is 0th.
00078     // Returns NULL after groups are exhausted.
00079     virtual const char* group(int n = 0) throw (); // shared, do not free
00080 
00081     // Forbid write-like operations to this user
00082     bool readOnly;
00083 
00084     // For use by NFS glue
00085     virtual uid_t toUnixUser() throw () = 0;
00086     virtual gid_t toUnixGroup() throw () = 0;
00087 
00088     //
00089     // Convenience methods for use by check()
00090     //
00091 
00092     // Would user(i) for some i return name?
00093     bool userMatch(const char* name) throw ();
00094 
00095     // Would group(i) for some i return name?
00096     bool groupMatch(const char* name) throw ();
00097 
00098     // Would userMatch(v) return true for some value v of the aname attribute?
00099     bool userMatch(const char* aname, VestaAttribs attribs) throw ();
00100 
00101     // Would groupMatch(v) return true for some value v of the aname attribute?
00102     bool groupMatch(const char* aname, VestaAttribs attribs) throw ();
00103 
00104     virtual bool operator==(const IdentityRep &other) const throw() = 0;
00105     bool operator !=(const IdentityRep &other) const throw()
00106     {
00107       return !(*this == other);
00108     }
00109 
00110     virtual void send(SRPC *srpc) const throw(SRPC::failure) = 0;
00111     virtual ~IdentityRep();
00112   };
00113   typedef IdentityRep* Identity;
00114 
00115   class GlobalIdentityRep : public IdentityRep {
00116   protected:
00117     const char* user_;
00118     void fill_caches()  throw();
00119   public:
00120     // Note: the constructor retains the supplied char*.  If u is
00121     // NULL, the effective uid of the current process is translated to
00122     // a global name and used.
00123     GlobalIdentityRep(const char* u =NULL, const sockaddr_in* o =NULL) throw();
00124     const char* user(int n = 0) throw (); // shared, do not free
00125     const char* group(int n = 0) throw (); // shared, do not free
00126     uid_t toUnixUser() throw () { return globalToUnixUser(user(0)); };
00127     gid_t toUnixGroup() throw () { return globalToUnixGroup(group(0)); };
00128 
00129     bool operator==(const IdentityRep &other) const throw();
00130     void send(SRPC *srpc) const throw(SRPC::failure);
00131     ~GlobalIdentityRep();
00132   };
00133 
00134 #if 0
00135   // !!Unfinished
00136   class GssapiIdentityRep : public GlobalIdentityRep {
00137   private:
00138     gss_cred_id_t* creds_;  // NULL if not owned by this process
00139   public:
00140     // The first form imports a plain character string name.
00141     // If u is NULL, the default principal for the current process is
00142     // used, i.e., whoever the user logged in to Kerberos as with kinit.
00143     GssapiIdentityRep(const char* u =NULL, const sockaddr_in* o =NULL)
00144       throw(failure);
00145     GssapiIdentityRep(const gss_name_t u, const sockaddr_in* o =NULL)
00146       throw(failure);
00147     GssapiIdentityRep(const gss_cred_id_t c, const sockaddr_in* o =NULL)
00148       throw(failure);
00149 
00150     ~GssapiIdentityRep();  // may need base type to have a virtual destructor
00151 
00152     class failure {
00153     public:
00154       Bit32 generic, minor;
00155       Text where;
00156       failure(Bit32 g, Bit32 m, Text w) : generic(g), minor(m), where(w) {};
00157     };
00158   };
00159 #endif
00160 
00161   class UnixIdentityRep : public IdentityRep {
00162   protected:
00163     virtual void fill_caches()  throw();
00164   private:
00165     authunix_parms* aup_;
00166     bool free_aup_;  // Should we free aup_ when this object is destroyed?
00167   public:
00168     // Note: the constructor retains the supplied aup pointer
00169     UnixIdentityRep(authunix_parms* aup =NULL, const sockaddr_in* o =NULL, bool own_aup=true)
00170       throw ();
00171     const char* user(int n = 0) throw (); // shared, do not free
00172     const char* group(int n = 0) throw (); // shared, do not free
00173     uid_t toUnixUser() throw () { return aup_->aup_uid; };
00174     gid_t toUnixGroup() throw () { return aup_->aup_gid; };
00175 
00176     // Server-side only call to make sure that the unig user/group ids
00177     // have mappings to global user/group names, possibly updating the
00178     // repository's internal tables.
00179     void validate() throw();
00180 
00181     bool operator==(const IdentityRep &other) const throw();
00182     void send(SRPC *srpc) const throw(SRPC::failure);
00183     ~UnixIdentityRep();
00184   };
00185 
00186   // Used to represent a user's information for the "whoami" call.
00187   class IdInfo {
00188   public:
00189     chars_seq names;  // Global usersnames (includes aliases)
00190     chars_seq groups; // Global group names
00191 
00192     uid_t unix_uid;   // The Unix UID of this user (used by the
00193                       // repository's NFS interface).
00194     uid_t unix_gid;   // The user's primary Unix GID (used by the
00195                       // repository's NFS interface).
00196 
00197     bool is_root;     // Does this user have root access?
00198     bool is_admin;    // Does this user have admin access?
00199     bool is_wizard;   // Does this user have wizard access?
00200     bool is_runtool;  // Is this user the runtool user (or aliased to
00201                       // it)?
00202 
00203     IdInfo() : names(), groups(), unix_uid(0), unix_gid(0),
00204                is_root(false), is_admin(false),
00205                is_wizard(false), is_runtool(false)
00206     { }
00207   };
00208 
00209   class ParseError {
00210   public:
00211     ParseError(Text m) : message(m) { };
00212     Text message;
00213 
00214     // The file in which the parsing error occurred.
00215     Text fname;
00216 
00217     // The type of file in which the parsing error occurred.
00218     Text fkind;
00219   };
00220 
00221   //
00222   // Conversions between local Unix uid/gid and global name
00223   // Fields are constant after initialization
00224   //
00225   static const char* realm;     // [Repository]realm (or 
00226   static unsigned int realmlen; // length of the realm string
00227   static IdentityRep::Flavor defaultFlavor;
00228   static uid_t globalToUnixUser(const char* user) throw ();
00229   static gid_t globalToUnixGroup(const char* group) throw ();
00230   static const char* unixToGlobalUser(uid_t uid) throw ();  // do not free
00231   static const char* unixToGlobalGroup(gid_t gid) throw (); // do not free
00232   static void refreshAccessTables() throw(ParseError); // server-side only
00233 
00234   uid_t toUnixUser() throw ();
00235   gid_t toUnixGroup() throw ();
00236 
00237   //
00238   // Parameters and methods for access checking
00239   //
00240 
00241   // AccessControl::del access is the same as administrative access
00242   // if restrictDelete is true; the same as write access otherwise.
00243   // That is, only an administrator can delete from an appendable
00244   // directory (creating a ghost) if restrictDelete is true;
00245   // otherwise anyone with write access to the directory can do so.
00246   // Available only within the repository address space.
00247   static bool restrictDelete;
00248 
00249   //
00250   // Special local and global users
00251   //
00252   static uid_t vforeignUser;       // globalToUnixUser if user is not local
00253   static gid_t vforeignGroup;      // globalToUnixGroup if group is not local
00254   static const char* vadminUser;   // privileged user
00255   static const char* vadminGroup;  // default group for /vesta
00256   static const char* rootUser;     // additional privileged user (root@realm)
00257   static const char* runtoolUser;  // owner of the volatile tree
00258   static const char* vwizardUser;  // can fix (or break) replication invariant
00259 
00260   // Operation types.  Note: VestaSource does not keep execute
00261   // permission bits for files, and AccessControl does not support
00262   // execute permission checking.  The NFS glue layer handles execute
00263   // permission by clearing the execute bits for a file if the
00264   // underlying shortid file is not executable or setting them to be
00265   // the same as the read bits if it is.
00266   //
00267   enum Class { unrestricted, administrative, ownership, read, write,
00268                search, del, setuid, setgid, agreement };
00269 
00270   // Check whether someone with the given identity is permitted to
00271   // make an access of the given class under this access control.
00272   // If who is NULL, the identity is that of the caller: the Vesta
00273   // administrator if the call is from the Vesta server address
00274   // space, the current process's effective user and groups
00275   // otherwise.  Assumes that admit() is true.  The value argument
00276   // is used with the setuid and setgid classes, to say what the
00277   // object is being made setuid or setgid to.
00278   //
00279   bool check(Identity who, Class cls, const char* value =NULL) throw ();
00280 
00281   // Check whether the given identity is allowed any access at
00282   // all to the local repository.
00283   static bool admit(Identity who) throw ();
00284 
00285   //
00286   // Get this process's default identity.
00287   // Uses a cached value unless flush is true, in which case
00288   // the cache is updated.
00289   //
00290   static Identity self()
00291     throw (/*GssapiIdentityRep::failure*/);
00292 
00293   //
00294   // Specific fields and methods of an AccessControl object
00295   //
00296   typedef Bit32 ModeBits;
00297   static ModeBits parseModeBits(const char* char_mode) throw ();
00298   static const char* formatModeBits(ModeBits mode) throw (); // caller frees
00299 
00300   ModeBits mode;
00301   VestaAttribs owner; // inherit nonempty #owner attrib from here
00302   VestaAttribs group; // inherit nonempty #group attrib from here
00303 
00304   //
00305   // One-time module initialization.
00306   //
00307  public:
00308   // server side of VestaSourceSRPC
00309   static void serverInit()
00310     throw (VestaConfig::failure /*, gssapi::failure*/);
00311   // client side of VestaSourceSRPC and common bits used by both
00312   // client and server.
00313   static void commonInit() throw ();
00314  private:
00315 
00316   friend void AccessControl_commonInit_inner() throw();
00317 
00318   static void selfInit() throw ();
00319   friend void AccessControl_selfInit_inner() throw();
00320 
00321   static Identity self_;
00322 };
00323 
00324 #endif // _AccessControl

Generated on Mon May 8 00:48:43 2006 for Vesta by  doxygen 1.4.2