Esempio n. 1
0
    def auth(self, client_cert, credentials, slice_urn=None, privileges=()):
        """
        This method authenticates and authorizes.
        It returns the client's urn, uuid, email (extracted from the {client_cert}). Example call: "urn, uuid, email = self.auth(...)"
        Be aware, the email is not required in the certificate, hence it might be empty.
        If the validation fails, an GENIv3ForbiddenError is thrown.
        
        The credentials are checked so the user has all the required privileges (success if any credential fits all privileges).
        The client certificate is not checked: this is usually done via the webserver configuration.
        This method only treats certificates of type 'geni_sfa'.
        
        Here a list of possible privileges (format: right_in_credential: [privilege1, privilege2, ...]):
            "authority" : ["register", "remove", "update", "resolve", "list", "getcredential", "*"],
            "refresh"   : ["remove", "update"],
            "resolve"   : ["resolve", "list", "getcredential"],
            "sa"        : ["getticket", "redeemslice", "redeemticket", "createslice", "createsliver", "deleteslice", "deletesliver", "updateslice",
                           "getsliceresources", "getticket", "loanresources", "stopslice", "startslice", "renewsliver",
                            "deleteslice", "deletesliver", "resetslice", "listslices", "listnodes", "getpolicy", "sliverstatus"],
            "embed"     : ["getticket", "redeemslice", "redeemticket", "createslice", "createsliver", "renewsliver", "deleteslice", 
                           "deletesliver", "updateslice", "sliverstatus", "getsliceresources", "shutdown"],
            "bind"      : ["getticket", "loanresources", "redeemticket"],
            "control"   : ["updateslice", "createslice", "createsliver", "renewsliver", "sliverstatus", "stopslice", "startslice", 
                           "deleteslice", "deletesliver", "resetslice", "getsliceresources", "getgids"],
            "info"      : ["listslices", "listnodes", "getpolicy"],
            "ma"        : ["setbootstate", "getbootstate", "reboot", "getgids", "gettrustedcerts"],
            "operator"  : ["gettrustedcerts", "getgids"],                   
            "*"         : ["createsliver", "deletesliver", "sliverstatus", "renewsliver", "shutdown"]
            
        When using the gcf clearinghouse implementation the credentials will have the rights:
        - user: "******", "resolve", "info" (which resolves to the privileges: "remove", "update", "resolve", "list", "getcredential", "listslices", "listnodes", "getpolicy").
        - slice: "refresh", "embed", "bind", "control", "info" (well, do the resolving yourself...)        
        """
        # check variables
        if not isinstance(privileges, tuple):
            raise TypeError("Privileges need to be a tuple.")
        # collect credentials (only GENI certs, version ignored)
        geni_credentials = []
        for c in credentials:
            if c['geni_type'] == 'geni_sfa':
                geni_credentials.append(c['geni_value'])

        # get the cert_root
        config = pm.getService("config")
        cert_root = expand_amsoil_path(config.get("geniv3rpc.cert_root"))

        # test the credential
        try:
            cred_verifier = ext.geni.CredentialVerifier(cert_root)
            cred_verifier.verify_from_strings(client_cert, geni_credentials,
                                              slice_urn, privileges)
        except Exception as e:
            raise GENIv3ForbiddenError(str(e))

        user_gid = gid.GID(string=client_cert)
        user_urn = user_gid.get_urn()
        user_uuid = user_gid.get_uuid()
        user_email = user_gid.get_email()
        return user_urn, user_uuid, user_email  # TODO document return
Esempio n. 2
0
    def verify_from_strings(self, gid_string, cred_strings, target_urn,
                            privileges):
        '''Create Credential and GID objects from the given strings,
        and then verify the GID has the right privileges according 
        to the given credentials on the given target.'''
        def make_cred(cred_string):
            return cred.Credential(string=cred_string)

        return self.verify(gid.GID(string=gid_string),
                           map(make_cred, cred_strings), target_urn,
                           privileges)
Esempio n. 3
0
def create_credential(caller_gid,
                      object_gid,
                      expiration,
                      typename,
                      issuer_keyfile,
                      issuer_certfile,
                      trusted_roots,
                      delegatable=False):
    '''Create and Return a Credential object issued by given key/cert for the given caller
    and object GID objects, given life in seconds, and given type.
    Privileges are determined by type per sfa/trust/rights.py
    Privileges are delegatable if requested.'''
    # FIXME: Validate args: my gids, >0 life,
    # type of cred one I can issue
    # and readable key and cert files
    if caller_gid is None:
        raise ValueError("Missing Caller GID")
    if object_gid is None:
        raise ValueError("Missing Object GID")
    if expiration is None:
        raise ValueError("Missing expiration")
    naive_expiration = naiveUTC(expiration)
    duration = naive_expiration - datetime.datetime.utcnow()
    life_secs = duration.seconds + duration.days * 24 * 3600
    if life_secs < 1:
        raise ValueError("Credential expiration is in the past")
    if trusted_roots is None:
        raise ValueError("Missing list of trusted roots")

    if typename is None or typename.strip() == '':
        raise ValueError("Missing credential type")
    typename = typename.strip().lower()
    if typename not in ("user", "sa", "ma", "authority", "slice", "component"):
        raise ValueError("Unknown credential type %s" % typename)

    if not os.path.isfile(issuer_keyfile):
        raise ValueError("Cant read issuer key file %s" % issuer_keyfile)

    if not os.path.isfile(issuer_certfile):
        raise ValueError("Cant read issuer cert file %s" % issuer_certfile)

    issuer_gid = gid.GID(filename=issuer_certfile)

    if not (object_gid.get_urn() == issuer_gid.get_urn() or
            (issuer_gid.get_type().find('authority') == 0
             and hrn_authfor_hrn(issuer_gid.get_hrn(), object_gid.get_hrn()))):
        raise ValueError(
            "Issuer not authorized to issue credential: Issuer=%s  Target=%s" %
            (issuer_gid.get_urn(), object_gid.get_urn()))

    ucred = cred.Credential()
    # FIXME: Validate the caller_gid and object_gid
    # are my user and slice
    # Do get_issuer and compare to the issuer cert?
    # Or do gid.is_signed_by_cert(issuer_certfile)?
    ucred.set_gid_caller(caller_gid)
    ucred.set_gid_object(object_gid)
    ucred.set_expiration(expiration)
    # Use sfa/trust/rights.py to figure out what privileges
    # the credential should have.
    # user means refresh, resolve, info
    # per the privilege_table that lets users do
    # remove, update, resolve, list, getcredential,
    # listslices, listnodes, getpolicy
    # Note that it does not allow manipulating slivers

    # And every right is delegatable if any are delegatable (default False)
    privileges = rights.determine_rights(typename, None)
    privileges.delegate_all_privileges(delegatable)
    ucred.set_privileges(privileges)
    ucred.encode()
    ucred.set_issuer_keys(issuer_keyfile, issuer_certfile)
    ucred.sign()

    try:
        ucred.verify(trusted_roots)
    except Exception, exc:
        raise Exception(
            "Create Credential failed to verify new credential from trusted roots: %s"
            % exc)