// gives this identity a trust chain to use public void AddTrustChain(byte[] trustChain) { TrustChainNode[] nodes = TrustChainUtil.SegmentChain(trustChain); bool isValid = TrustChainUtil.ValidateTrustChain(nodes); bool endsWithThis = nodes[nodes.Length - 1].ThisId.SequenceEqual(PublicIdentity); if (isValid && endsWithThis) { TrustChain = nodes; PermissionsHeld = nodes[nodes.Length - 1].HeldPermissions; PermissionsGrantable = nodes[nodes.Length - 1].GrantablePermissions; identityManager.AddIdentities(nodes); } else { throw new BadTrustChainException("Could not validate trust chain ending with this"); } }
// generates a new trust chain with this as the root node public void GenerateRootChain() { if (Name.Length > TrustChainUtil.UNASSIGNED_DATA_SIZE - 1) { throw new ArgumentException("Name too long"); } var nameBytes = new byte[TrustChainUtil.UNASSIGNED_DATA_SIZE]; using (var ms = new MemoryStream(nameBytes)) using (var writer = new BinaryWriter(ms)) { writer.Write((byte)Name.Length); writer.Write(Encoding.UTF8.GetBytes(Name)); } byte[] rootChain = TrustChainUtil.GenerateNewChain(new TrustChainNode[0], PublicIdentity, PublicIdentity, Permission.All, Permission.All, nameBytes, privateKey); PermissionsHeld = Permission.All; PermissionsGrantable = Permission.All; AddTrustChain(rootChain); }
public bool ValidateAndAdd(TrustChainNode[] trustChainNodes) { bool validChain = TrustChainUtil.ValidateTrustChain(trustChainNodes); if (!validChain) { return(false); } bool sameRoot = TrustChain[0].ParentId.SequenceEqual(trustChainNodes[0].ParentId); if (!sameRoot) { return(false); } for (int i = 0; i < trustChainNodes.Length; i++) { identityManager.AddIdentity(trustChainNodes[i], Name); } return(true); }
// generates a trust chain to pass to another client public byte[] GenerateNewChain(byte[] childId, Permission heldPermissions, Permission grantablePermissions, string name) { bool canGrant = CanGrantPermissions(heldPermissions, grantablePermissions); if (canGrant) { if (name.Length > TrustChainUtil.UNASSIGNED_DATA_SIZE - 1) { throw new ArgumentException("Name too long"); } byte[] nameBytes = new byte[TrustChainUtil.UNASSIGNED_DATA_SIZE]; nameBytes[0] = (byte)name.Length; Buffer.BlockCopy(Encoding.UTF8.GetBytes(name), 0, nameBytes, 1, name.Length); return(TrustChainUtil.GenerateNewChain(TrustChain, PublicIdentity, childId, heldPermissions, grantablePermissions, nameBytes, privateKey)); } else { throw new InvalidPermissionException($"Insufficient authorization to grant permissions"); } }
// whether the given permissions can be granted by this node public bool CanGrantPermissions(Permission heldPermissions, Permission grantablePermissions) { return(PermissionsHeld.HasFlag(Permission.Invite) && TrustChainUtil.ValidatePermissions(PermissionsGrantable, heldPermissions) && TrustChainUtil.ValidatePermissions(heldPermissions, grantablePermissions)); }
// validates the given trust chain and adds the nodes to the list of known nodes, or returns false public bool ValidateAndAdd(byte[] trustChain) { TrustChainNode[] trustChainNodes = TrustChainUtil.SegmentChain(trustChain); return(ValidateAndAdd(trustChainNodes)); }