예제 #1
0
func (g *granter) Grant(ctx *context.T, call security.Call) (security.Blessings, error) {
	// Verify that the remote end's blessings encapsulates the
	// same user identity as g.user.
	remoteBlessingNames, _ := security.RemoteBlessingNames(ctx, call)
	authorized := false
	for _, b := range remoteBlessingNames {
		if vUser(b) == g.user {
			authorized = true
		}
	}
	if !authorized {
		return security.Blessings{}, fmt.Errorf("remote end presented blessings %v, want a blessing for user %v", remoteBlessingNames, g.user)
	}

	peerPattern := security.BlessingPattern(g.lockName)
	onlyThisLockCav, err := security.NewCaveat(security.PeerBlessingsCaveat, []security.BlessingPattern{peerPattern})
	if err != nil {
		return security.Blessings{}, fmt.Errorf("failed to create peer blessings caveat for key: %v", err)
	}

	caveats := []security.Caveat{onlyThisLockCav}
	if g.expiry != 0 {
		expiryCav, err := security.NewExpiryCaveat(time.Now().Add(g.expiry))
		if err != nil {
			return security.Blessings{}, fmt.Errorf("failed to create expiration caveat for key: %v", err)
		}
		caveats = append(caveats, expiryCav)
	}
	return call.LocalPrincipal().Bless(call.RemoteBlessings().PublicKey(), g.key, g.category, caveats[0], caveats[1:]...)
}
예제 #2
0
func runClaim(ctx *context.T, env *cmdline.Env, args []string) error {
	if numargs := len(args); numargs != 2 {
		return fmt.Errorf("requires exactly two arguments <lock>, <name>, provided %d", numargs)
	}
	lockName, name := args[0], args[1]

	ctx, stop, err := withLocalNamespace(ctx, "", lockUserNhName(ctx))
	if err != nil {
		return err
	}
	defer stop()

	ctx, cancel := context.WithTimeout(ctx, time.Minute)
	defer cancel()
	// TODO(ataly): We should not skip server endpoint authorization while
	// claiming locks but instead fetch the blessing root of the lock manufacturer
	// from an authoritative source and then appropriately authenticate the server.
	b, err := lock.UnclaimedLockClient(lockObjName(lockName)).Claim(
		ctx,
		name,
		options.ServerAuthorizer{security.AllowEveryone()})
	if err != nil {
		return err
	}

	p := v23.GetPrincipal(ctx)
	if err := security.AddToRoots(p, b); err != nil {
		return fmt.Errorf("failed to add (key) blessing (%v) to roots: %v", b, err)
	}
	if _, err := p.BlessingStore().Set(b, security.BlessingPattern(name)); err != nil {
		return fmt.Errorf("failed to set (key) blessing (%v) for peer %v: %v", b, name, err)
	}
	fmt.Printf("Claimed lock: %v as %v and received key: %v\n", lockName, name, b)
	return nil
}
예제 #3
0
func (ul *unclaimedLock) makeKey(principal security.Principal, name string, remoteKey security.PublicKey) (security.Blessings, error) {
	lockBlessing, err := principal.BlessSelf(name)
	if err != nil {
		return security.Blessings{}, err
	}

	if err := principal.BlessingStore().SetDefault(lockBlessing); err != nil {
		return security.Blessings{}, err
	}
	if err := security.AddToRoots(principal, lockBlessing); err != nil {
		return security.Blessings{}, err
	}

	// Add a caveat to the "key" blessing so that it can only be used to talking
	// to this lock object.
	// TODO(ataly): Add a client-only caveat as well so that someone who obtains
	// this blessing or an extension of it cannot maliciously (or accidentally)
	// start a server with this blessing (such a server could impersonate this
	// lock object).
	peerPattern := security.BlessingPattern(name)
	onlyThisLockCav, err := security.NewCaveat(security.PeerBlessingsCaveat, []security.BlessingPattern{peerPattern})
	if err != nil {
		return security.Blessings{}, err
	}
	keyBlessing, err := principal.Bless(remoteKey, lockBlessing, keyBlessingExtension, onlyThisLockCav)
	if err != nil {
		return security.Blessings{}, err
	}
	return keyBlessing, nil
}
예제 #4
0
func isKeyValidForLock(ctx *context.T, key security.Blessings, lockName string) bool {
	bp := security.BlessingPattern(lockName + security.ChainSeparator + "key")
	for _, b := range security.BlessingNames(v23.GetPrincipal(ctx), key) {
		if bp.MatchedBy(b) {
			return true
		}
	}
	return false
}
예제 #5
0
func m2vVisibility(visibility *[]string) []security.BlessingPattern {
	if visibility == nil {
		return nil
	}
	vVisibility := make([]security.BlessingPattern, len(*visibility))
	for i, p := range *visibility {
		vVisibility[i] = security.BlessingPattern(p)
	}
	return vVisibility
}
예제 #6
0
func saveKeyForLock(ctx *context.T, key security.Blessings, lockName string) error {
	if isKeyValidForLock(ctx, key, lockName) {
		return fmt.Errorf("key %v is not valid for lock %v", key, lockName)
	}
	p := v23.GetPrincipal(ctx)
	if _, err := p.BlessingStore().Set(key, security.BlessingPattern(lockName)); err != nil {
		return fmt.Errorf("failed to save key %v for lock %v", key, lockName)
	}
	if err := security.AddToRoots(p, key); err != nil {
		return fmt.Errorf("failed to save key %v for lock %v", key, lockName)
	}
	return nil
}
예제 #7
0
// vUser returns a comma-separated string of user identities obtained
// from the provided blessing names.
//
// For each blessing name, vUser checks if it matches the pattern
// 'vanadiumBlessingPrefix' and if so constructs the user identity by
// stripping off 'vanadiumBlessingPrefix' from the blessing name.
// Otherwise the user identity is simply the blessing name.
//
// In all case, the user identity is converted into a valid neighborhood-name
// by replacing slahes with "@@".
// TODO(ataly): Try to use conventions.GetClientUserIds instead.
func vUser(bNames ...string) string {
	nhFriendly := func(b string) string {
		return strings.Replace(b, security.ChainSeparator, "@@", -1)
	}
	users := make([]string, len(bNames))
	for i, b := range bNames {
		if !security.BlessingPattern(vanadiumBlessingPrefix).MatchedBy(b) {
			users[i] = nhFriendly(b)
			continue
		}
		users[i] = nhFriendly(strings.TrimPrefix(b, vanadiumBlessingPrefix+security.ChainSeparator))
	}
	return strings.Join(users, ",")
}
예제 #8
0
파일: swift.go 프로젝트: vanadium/go.swift
// Exports the discovery advertise API to CGO using JSON to marshal ads
//export swift_io_v_v23_discovery_advertise
func swift_io_v_v23_discovery_advertise(ctxHandle C.GoContextHandle, discoveryHandle C.GoDiscoveryHandle, adJson C.SwiftByteArray, visibilityArray C.SwiftCStringArray, asyncId C.AsyncCallbackIdentifier, doneCallback C.SwiftAsyncSuccessCallback, errOut *C.SwiftVError) bool {
	ctx := scontext.GoContext(uint64(ctxHandle))
	d := GoDiscoveryT(uint64(discoveryHandle))
	ad := discovery.Advertisement{}
	if err := json.Unmarshal(sutil.GoBytesNoCopy(unsafe.Pointer(&adJson)), &ad); err != nil {
		sutil.ThrowSwiftError(ctx, err, unsafe.Pointer(errOut))
		return false
	}
	var visibility []security.BlessingPattern
	for _, v := range visibilityArray.toStrings() {
		visibility = append(visibility, security.BlessingPattern(v))
	}
	doneChan, err := d.Advertise(ctx, &ad, visibility)
	if err != nil {
		sutil.ThrowSwiftError(ctx, err, unsafe.Pointer(errOut))
		return false
	}
	go func() {
		<-doneChan
		C.CallAdvertisingCallback(doneCallback, asyncId)
	}()
	return true
}
예제 #9
0
파일: jni.go 프로젝트: vanadium/go.jni
//export Java_io_v_v23_security_BlessingPattern_nativeCreate
func Java_io_v_v23_security_BlessingPattern_nativeCreate(jenv *C.JNIEnv, jBlessingPatternClass C.jclass, jValue C.jstring) C.jlong {
	env := jutil.Env(uintptr(unsafe.Pointer(jenv)))
	pattern := security.BlessingPattern(jutil.GoString(env, jutil.Object(uintptr(unsafe.Pointer(jValue)))))
	ref := jutil.GoNewRef(&pattern) // Un-refed when the BlessingPattern object is finalized.
	return C.jlong(ref)
}