gotorg

package
v0.1.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jan 24, 2026 License: GPL-3.0 Imports: 30 Imported by: 0

README

GotOrg

GotOrg is a permissioned namespace for marks. It manages all of the public key cryptography needed to enforce permissions for reading and writing from marks.

The branch Volumes are encrypted with AEADs, and the secret keys are stored encrypted in GotOrg.

All actions in GotOrg must be signed by a single key.

Identity

Identities are a set of public keys used for signing. Identities are either Leaves, or Groups.

Leaves

Leaves are uniquely identified by an INET256 address, derived by hashing the public key. A KEM key pair is generated and then the public key is signed with the signing key.

Groups

A group is uniquely defined by a user specified name. Names are unique within the namespace. A group contains a set of leaves, and a set of other groups.

Each Group has it's own KEM key. All members of the group have access to an encrypted version of the KEM private key. Everyone can see the KEM public key in the record for the Group.

Rules

The namespace has a set of rules, which are used to grant access to regions of the namespace. Each rule has 3 parts: a subject, a verb, and an ObjectSet. Subject refers to a Group by name. A Group cannot be deleted unless all rules referring to it are also deleted.

Verb is the action being performed, viewing or editing the branch contents or metadata.

ObjectSet is a type plus a regular exprssion. The Type can either be "group" or "branch".

Branches

The namespace for branches is regulated by the rules

Documentation

Index

Constants

View Source
const (
	KEM_MLKEM1024 = "mlkem1024"
)
View Source
const SchemaName = "got/org"

Variables

This section is empty.

Functions

func BranchVolumeSpec

func BranchVolumeSpec() blobcache.VolumeSpec

BranchVolumeSpec is the volume spec used for new marks.

func DefaultVolumeSpec

func DefaultVolumeSpec(useSchema bool) blobcache.VolumeSpec

DefaultVolumeSpec is the volume spec used for gotorg Volumes

func MarshalKEMPrivateKey

func MarshalKEMPrivateKey(out []byte, tag string, kem kem.PrivateKey) []byte

func MarshalKEMPublicKey

func MarshalKEMPublicKey(out []byte, tag string, kem kem.PublicKey) []byte

func MemberGroup

func MemberGroup(gid GroupID) gotorgop.Member

func MemberUnit

func MemberUnit(id inet256.ID) gotorgop.Member

func PKI

func PKI() inet256.PKI

func Parse

func Parse(x []byte) (statetrace.Root[Root], error)

func ParseKEMPrivateKey

func ParseKEMPrivateKey(data []byte) (kem.PrivateKey, error)

func ParseKEMPublicKey

func ParseKEMPublicKey(data []byte) (kem.PublicKey, error)

func SchemaConstructor

func SchemaConstructor(params json.RawMessage, mkSchema schema.Factory) (schema.Schema, error)

Types

type CID

type CID = blobcache.CID

type ChangeSet

type ChangeSet = gotorgop.ChangeSet

type Client

type Client struct {
	Blobcache blobcache.Service
	Machine   Machine
	ActAs     IdenPrivate
}

Client holds configuration for accessing a GotNS instance backed by a Blobcache Volume.

func (*Client) AddMember

func (c *Client) AddMember(ctx context.Context, volh blobcache.Handle, gid GroupID, mem Member) error

AddMember adds a new primitive identity to a group.

func (*Client) CreateAlias

func (c *Client) CreateAlias(ctx context.Context, nsh blobcache.Handle, name string, aux []byte) error

CreateAlias creates a new alias with a new volume at the specified name.

func (*Client) DeleteAlias

func (c *Client) DeleteAlias(ctx context.Context, volh blobcache.Handle, name string) error

func (*Client) Do

func (c *Client) Do(ctx context.Context, volh blobcache.Handle, fn func(txb *Txn) error) error

Do calls fn with a transaction for manipulating the NS.

func (*Client) EnsureInit

func (c *Client) EnsureInit(ctx context.Context, volh blobcache.Handle, admins []IdentityUnit) error

EnsureInit initializes a new GotNS instance in the given volume. If the volume already contains a GotNS instance, it is left unchanged.

func (*Client) GetAlias

func (c *Client) GetAlias(ctx context.Context, volh blobcache.Handle, name string) (*VolumeAlias, error)

func (*Client) GetIDUnit

func (c *Client) GetIDUnit(ctx context.Context, volh blobcache.Handle, id inet256.ID) (*IdentityUnit, error)

func (*Client) Inspect

func (c *Client) Inspect(ctx context.Context, volh blobcache.Handle, name string) (*marks.Info, error)

func (*Client) IntroduceSelf

func (c *Client) IntroduceSelf() gotorgop.ChangeSet

IntroduceSelf creates a signed change set that adds a leaf to the state. Then it returns the signed change set data. It does not contact Blobcache or perform any Volume operations.

func (*Client) ListAliases

func (c *Client) ListAliases(ctx context.Context, volh blobcache.Handle, span marks.Span, limit int) ([]string, error)

func (*Client) LookupGroup

func (c *Client) LookupGroup(ctx context.Context, volh blobcache.Handle, name string) (*gotorgop.Group, error)

func (*Client) OpenAt

func (c *Client) OpenAt(ctx context.Context, nsh blobcache.Handle, name string, actAs IdenPrivate, writeAccess bool) (marks.Volume, error)

func (*Client) PutAlias

func (c *Client) PutAlias(ctx context.Context, volh blobcache.Handle, bent VolumeAlias, secret *gotorgop.Secret) error

type Delta

type Delta gotorgop.ChangeSet

Delta can be applied to a State to produce a new State.

func (Delta) Marshal

func (d Delta) Marshal(out []byte) []byte

type Group

type Group = gotorgop.Group

type GroupID

type GroupID = gotorgop.GroupID

type IDSet

type IDSet = map[inet256.ID]struct{}

type IdenPrivate

type IdenPrivate struct {
	SigPrivateKey inet256.PrivateKey
	KEMPrivateKey kem.PrivateKey
}

func GenerateIden

func GenerateIden() IdenPrivate

func (*IdenPrivate) GetID

func (iden *IdenPrivate) GetID() inet256.ID

func (*IdenPrivate) Public

func (iden *IdenPrivate) Public() IdentityUnit

type IdentityUnit

type IdentityUnit = gotorgop.IdentityUnit

func NewIDUnit

func NewIDUnit(pubKey inet256.PublicKey, kemPub kem.PublicKey) IdentityUnit

type Machine

type Machine struct {
	// contains filtered or unexported fields
}

func New

func New() Machine

func (*Machine) AddMember

func (m *Machine) AddMember(ctx context.Context, s stores.RW, x State, gid GroupID, member Member, groupSecret *gotorgop.Secret) (*State, error)

AddMember adds a member (a unit or another Group) to a containing group.

func (*Machine) AddRule

func (m *Machine) AddRule(ctx context.Context, s stores.RW, state State, r *gotorgop.Rule) (*State, error)

AddRule adds a rule to the state if it doesn't already exist. If it does exist, it does nothing.

func (*Machine) AddVolume

func (m *Machine) AddVolume(ctx context.Context, s stores.RW, state State, entry VolumeEntry) (*State, error)

AddVolume adds a new Volume to the namespace. It's OID must be unique within the namespace or an error will be returned.

func (*Machine) CanAnyDo

func (m *Machine) CanAnyDo(ctx context.Context, s stores.Reading, state State, actors IDSet, verb Verb, objType ObjectType, objName string) (bool, error)

func (*Machine) CanDo

func (m *Machine) CanDo(ctx context.Context, s stores.Reading, state State, actor inet256.ID, verb Verb, objType ObjectType, objName string) (bool, error)

CanDo returns true if the subject can perform the action on the object.

func (*Machine) DeleteAlias

func (m *Machine) DeleteAlias(ctx context.Context, s stores.RW, State State, name string) (*State, error)

DeleteAlias deletes an alias from the namespace.

func (*Machine) DropIDUnit

func (m *Machine) DropIDUnit(ctx context.Context, s stores.RW, state State, id inet256.ID) (*State, error)

DropIDUnit drops a unit from the units table.

func (*Machine) DropRule

func (m *Machine) DropRule(ctx context.Context, s stores.RW, state State, ruleID CID) (State, error)

DropRule deletes a rule from the state if it exists. If it does not exist, it does nothing.

func (*Machine) DropVolume

func (m *Machine) DropVolume(ctx context.Context, s stores.RW, state State, volOID blobcache.OID) (*State, error)

func (*Machine) FindGroupPath

func (m *Machine) FindGroupPath(ctx context.Context, s stores.Reading, x State, id inet256.ID, target GroupID) ([]GroupID, error)

FindGroupPath finds a path of groups from priv to the target Group. FindGroupPath returns (nil, nil) when no path could be found.

func (*Machine) FindSecret

func (m *Machine) FindSecret(ctx context.Context, s stores.Reading, x State, actAs IdenPrivate, hos *[32]byte, minRatchet uint8) (*gotorgop.Secret, uint8, error)

FindSecret reveres the provied hash. The goal motivating all the complexity in this package is just to implement this function.

  1. Fnd all the obligations that hold the secret we are interested in.
  2. Find all the groups which can decrypt those secrets.
  3. Find a path from the the actor's ID to one of those groups.
  4. Use that path to perform a chain of KEM decryptions eventually resulting a secret value which reverses hash of secret.

func (*Machine) ForEachGroup

func (m *Machine) ForEachGroup(ctx context.Context, s stores.Reading, state State, fn func(group gotorgop.Group) error) error

ForEachGroup calls fn for each group in the namespace.

func (*Machine) ForEachIDUnit

func (m *Machine) ForEachIDUnit(ctx context.Context, s stores.Reading, state State, fn func(unit IdentityUnit) error) error

func (*Machine) ForEachMembership

func (m *Machine) ForEachMembership(ctx context.Context, s stores.Reading, state State, gid *GroupID, fn func(mem Membership) error) error

ForEachMembership calls fn for each membership If gid is non-nil, then it will be used to filter by the containing group.

func (*Machine) ForEachObligation

func (m *Machine) ForEachObligation(ctx context.Context, s stores.Reading, x State, hos *[32]byte, fn func(ob Obligation) error) error

ForEachObligation iterates over all Obligations If hos is non-nil, then only obligations for the corresponding secret will be emmitted.

func (*Machine) ForEachRule

func (m *Machine) ForEachRule(ctx context.Context, s stores.Reading, state State, fn func(rule Rule) error) error

ForEachRule calls fn for each rule.

func (*Machine) ForEachUnitInGroup

func (m *Machine) ForEachUnitInGroup(ctx context.Context, s stores.Reading, state State, gid GroupID, fn func(inet256.ID) error) error

ForEachInGroup calls fn recursively for each ID in the group. This is a recursive method which explores the full transitive closure of the initial Group.

func (*Machine) ForEachVolume

func (m *Machine) ForEachVolume(ctx context.Context, s stores.Reading, x State, fn func(entry VolumeEntry) error) error

func (*Machine) FulfillObligations

func (m *Machine) FulfillObligations(ctx context.Context, s stores.RW, x State, name string, secret *gotorgop.Secret) (*State, error)

FulfillObligations ensures that obligations for the entry are satisfied.

func (*Machine) GetAlias

func (m *Machine) GetAlias(ctx context.Context, s stores.Reading, state State, name string) (*gotorgop.VolumeAlias, error)

GetAlias looks up an entry in the branches table.

func (*Machine) GetGroup

func (m *Machine) GetGroup(ctx context.Context, s stores.Reading, State State, groupID GroupID) (*Group, error)

GetGroup returns a group by name.

func (*Machine) GetGroupName

func (m *Machine) GetGroupName(ctx context.Context, s stores.Reading, x State, name string) (*gotorgop.GroupID, error)

func (*Machine) GetGroupSecret

func (m *Machine) GetGroupSecret(ctx context.Context, s stores.Reading, state State, priv IdenPrivate, groupPath []GroupID) (*gotorgop.Secret, error)

GetGroupSecret returns a KEM seed used to derive the key pair for a given group. id is the ID of the leaf that is requesting the KEM private key. kemPriv is the KEM private key for the leaf to decrypt messages sent to it by group operations. groupPath should go from the largest group to the smallest group. If you need a groupPath, try `FindGroupPath` first.

func (*Machine) GetIDUnit

func (m *Machine) GetIDUnit(ctx context.Context, s stores.Reading, state State, id inet256.ID) (*IdentityUnit, error)

GetIDUnit retuns an identity unit by ID.

func (*Machine) GetMembership

func (m *Machine) GetMembership(ctx context.Context, s stores.Reading, state State, group GroupID, mem Member) (*Membership, error)

func (*Machine) GetRule

func (m *Machine) GetRule(ctx context.Context, s stores.Reading, state State, cid CID) (Rule, error)

func (*Machine) GetVolume

func (m *Machine) GetVolume(ctx context.Context, s stores.Reading, state State, volOID blobcache.OID) (*VolumeEntry, error)

GetVolume looks up a volume in the volumes table. If the volume is not found, nil is returned.

func (*Machine) GroupContains

func (m *Machine) GroupContains(ctx context.Context, s stores.Reading, state State, group GroupID, actor inet256.ID) (bool, error)

GroupContains returns true if the actor is a member of the group. This method answers the `contains?` query for the full transitive closure for the group. For immediate memberhsip call GetMembership directly and check for (nil, nil); that means the memberhip does not exist.

func (*Machine) ListBranches

func (m *Machine) ListBranches(ctx context.Context, s stores.Reading, state State, span marks.Span, limit int) ([]gotorgop.VolumeAlias, error)

func (*Machine) LookupGroup

func (m *Machine) LookupGroup(ctx context.Context, s stores.Reading, state State, name string) (*Group, error)

func (*Machine) New

func (m *Machine) New(ctx context.Context, s stores.RW, admins []IdentityUnit) (*statetrace.Root[Root], error)

New creates a new root.

func (*Machine) NewTxn

func (m *Machine) NewTxn(prev statetrace.Root[Root], s schema.RW, actAs []IdenPrivate) *Txn

NewBuilder creates a new delta builder. privateKey is the private key of the actor performing the transaction. It will be used to produce a signature at the end of the transaction.

func (*Machine) Open

func (m *Machine) Open(ctx context.Context, s stores.Reading, x State, actAs IdenPrivate, volid blobcache.OID, writeAccess bool) (*blobcache.LinkToken, VolumeConstructor, error)

func (*Machine) OpenAt

func (m *Machine) OpenAt(ctx context.Context, s stores.Reading, x State, actAs IdenPrivate, name string, writeAccess bool) (*blobcache.LinkToken, VolumeConstructor, error)

func (*Machine) PutAlias

func (m *Machine) PutAlias(ctx context.Context, s stores.RW, state State, entry gotorgop.VolumeAlias, secret *gotorgop.Secret) (*State, error)

PutAlias inserts or overwrites an entry in the branches table.

func (*Machine) PutGroup

func (m *Machine) PutGroup(ctx context.Context, s stores.RW, state State, group Group) (*State, error)

PutGroup adds or replaces a group by name.

func (*Machine) PutGroupName

func (m *Machine) PutGroupName(ctx context.Context, s stores.RW, state State, name string, groupID gotorgop.GroupID) (*State, error)

func (*Machine) PutIDUnit

func (m *Machine) PutIDUnit(ctx context.Context, s stores.Writing, state State, leaf IdentityUnit) (*State, error)

PutLeaf adds a leaf to the leaves table, overwriting whatever was there. Any unreferenced leaves will be deleted.

func (*Machine) PutObligation

func (m *Machine) PutObligation(ctx context.Context, s stores.RW, state State, o *Obligation) (*State, error)

func (*Machine) RekeyGroup

func (m *Machine) RekeyGroup(ctx context.Context, s stores.RW, state State, gid GroupID, secret *gotorgop.Secret) (*State, error)

RekeyGroup creates a new KEM key pair for a group and - changes the group's KEM public key - re-encrypts the KEM private key for all leaves, using the leaves' KEM public key - re-encrypts the KEM private key for all member groups, using those groups' KEM public keys

func (*Machine) RemoveMember

func (m *Machine) RemoveMember(ctx context.Context, s stores.RW, state State, gid GroupID, mem Member) (*State, error)

RemoveMember removes a member group from a containing group.

func (*Machine) ValidateChange

func (m *Machine) ValidateChange(ctx context.Context, src stores.Reading, prev, next State, delta Delta) error

ValidateChange checks the change between two states. Prev is assumed to be a known good, valid state.

func (*Machine) ValidateState

func (m *Machine) ValidateState(ctx context.Context, src stores.Reading, x State) error

ValidateState checks the state in isolation.

type Member

type Member = gotorgop.Member

type Membership

type Membership struct {
	Group  GroupID
	Member Member

	// EncryptedKEM contains a KEM ciphertext, and a symmetric ciphertext.
	// The symmetric ciphertext contains the KEM seed for the Group's KEM private key.
	EncryptedKEM []byte
}

Membership contains the Group's KEM seed encrypted for the target member.

func ParseMembership

func ParseMembership(k, v []byte) (*Membership, error)

func (*Membership) Key

func (m *Membership) Key(out []byte) []byte

func (*Membership) Value

func (m *Membership) Value(out []byte) []byte

type ObjectType

type ObjectType = gotorgop.ObjectType

type Obligation

type Obligation struct {
	// HashOfSecret is the hash of the secret that the obligation is for.
	HashOfSecret [32]byte
	// Ratchet is the number of times that the secret is hashed to produce HashOfSecret
	// This value must always be >= 0, usually 1 for readers and 2 for writers.
	Ratchet uint8
	// GroupID is the id of the Group that is entitled to the secret.
	GroupID GroupID

	// The seed can be decrypted with the corresponding private key for the KEMHash.
	// The seed will decrypt to a 64 byte seed, which is used for the volume's Signing Key.
	// The hash of the seed will be used for the symmetric cipher.
	EncryptedSecret []byte
}

Obligation associates encrypted secret keys with Volumes, according to rules.

func ParseObligation

func ParseObligation(key []byte, value []byte) (*Obligation, error)

func (*Obligation) Key

func (o *Obligation) Key(out []byte) []byte

func (*Obligation) Value

func (o *Obligation) Value(out []byte) []byte

type Op

type Op = gotorgop.Op

type Root

type Root struct {
	Version uint8
	// Current is the state of the world.
	Current State
	// Recent is the Delta that was applied most recently
	// to get to the Current state, from the immediately previous state.
	Recent Delta
}

func ParseRoot

func ParseRoot(data []byte) (Root, error)

func (Root) Marshal

func (r Root) Marshal(out []byte) []byte

func (*Root) Unmarshal

func (r *Root) Unmarshal(data []byte) error

type Rule

type Rule = gotorgop.Rule

type RuleID

type RuleID = gotorgop.RuleID

type Schema

type Schema struct{}

Schema implements a blobcache Schema for Got Namespaces.

func (Schema) ValidateChange

func (s Schema) ValidateChange(ctx context.Context, change schema.Change) error

type Space

type Space struct {
	// contains filtered or unexported fields
}

Space implements marks.Space

func NewSpace

func NewSpace(client *Client, volh blobcache.Handle) *Space

func (*Space) Create

func (bs *Space) Create(ctx context.Context, name string, md marks.Metadata) (*marks.Info, error)

func (*Space) Delete

func (bs *Space) Delete(ctx context.Context, name string) error

func (*Space) Inspect

func (bs *Space) Inspect(ctx context.Context, name string) (*marks.Info, error)

func (*Space) List

func (bs *Space) List(ctx context.Context, span marks.Span, limit int) ([]string, error)

func (*Space) Open

func (bs *Space) Open(ctx context.Context, name string) (*marks.Mark, error)

func (*Space) Set

func (bs *Space) Set(ctx context.Context, name string, config marks.Metadata) error

type State

type State struct {

	// IDUnits hold primitive identity elements.
	// The key is the INET256 ID, derived by hashing the public signing key.
	// The value is the public signing key for the unit, and a signed KEM key for the leaf to recieve messages
	// The unit KEM private keys are not store anywhere in the state.
	IDUnits gotkv.Root
	// Groups maps group IDs to group information.
	// Group information holds group's Owner list, and shared KEM key for the group
	// to receive messages.
	Groups gotkv.Root
	// GroupNames maps names to group IDs.
	GroupNames gotkv.Root

	// Memberships holds relationships between groups and other groups.
	// The value is a KEM ciphertext sent by the containing group owners to the member.
	// The ciphertext contains the containing group's KEM private key encrypted with the member's KEM public key.
	Memberships gotkv.Root

	// Rules holds rules for the namespace, granting look or touch access to marks.
	Rules gotkv.Root
	// Obligations holds obligations for the namespace, granting access to volumes.
	Obligations gotkv.Root

	// Volumes holds the volume entries themselves.
	Volumes gotkv.Root
	// VolumeNames maps names to Volume OIDs
	VolumeNames gotkv.Root
}

State represents the current state of a namespace.

func (State) Marshal

func (s State) Marshal(out []byte) []byte

func (*State) Unmarshal

func (s *State) Unmarshal(data []byte) error

type Txn

type Txn struct {
	// contains filtered or unexported fields
}

Txn allows a transction to be built up incrementally And then turned into a single slot change to the ledger.

func (*Txn) AddMember

func (tx *Txn) AddMember(ctx context.Context, gid gotorgop.GroupID, member gotorgop.Member) error

func (*Txn) AddVolume

func (tx *Txn) AddVolume(ctx context.Context, vent gotorgop.VolumeEntry) error

func (*Txn) ChangeSet

func (tx *Txn) ChangeSet(ctx context.Context, cs gotorgop.ChangeSet) error

func (*Txn) CreateIDUnit

func (tx *Txn) CreateIDUnit(ctx context.Context, unit IdentityUnit) error

CreateIDUnit creates a new unit.

func (*Txn) DeleteAlias

func (tx *Txn) DeleteAlias(ctx context.Context, name string) error

func (*Txn) DropVolume

func (tx *Txn) DropVolume(ctx context.Context, volid blobcache.OID) error

func (*Txn) Finish

func (tx *Txn) Finish(ctx context.Context) (statetrace.Root[Root], error)

Finish applies the changes to the previous root, and returns the new root.

func (*Txn) LookupGroup

func (tx *Txn) LookupGroup(ctx context.Context, gname string) (*Group, error)

func (*Txn) PutAlias

func (tx *Txn) PutAlias(ctx context.Context, entry VolumeAlias, secret *gotorgop.Secret) error

type Verb

type Verb = gotorgop.Verb

type Volume

type Volume struct {
	// contains filtered or unexported fields
}

func (*Volume) BeginTx

func (v *Volume) BeginTx(ctx context.Context, txp blobcache.TxParams) (volumes.Tx, error)

type VolumeAlias

type VolumeAlias = gotorgop.VolumeAlias

type VolumeConstructor

type VolumeConstructor = func(nsVol, innerVol marks.Volume) *Volume

type VolumeEntry

type VolumeEntry = gotorgop.VolumeEntry

Directories

Path Synopsis
internal

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL