interreality.org [VOS]
[Home][About]
[Screenshots][Download]
[News][Community]
[Documentation][Manual]
[Bugs & Requests][Wiki]

3.2. The VOS Design

3.2.1. Goals

The purpose of the VOS core is to support the following features:

  • abstract object-oriented message passing

  • polymorphic object typing and extension system

  • naming, addressing and interconnecting vobjects

  • ability to add listeners to all aspects of vobjects

  • user identities, user groups and authentication

  • fine-grained permissions system based on identities for controlling remote access to Vobjects

3.2.2. The Vobject Model

The basic unit of VOS are Vobjects, which are formally defined by the following object model:

  1. The Vobject exists with a unique name as a direct child of exactly one site.

  2. The Vobject can be a source and destination for exchanging messages with other vobjects, with sites handling intermediate transport as necessary.

  3. The Vobject has a set of type strings. These may be used to describe what interfaces this vobject supports, how to interpret the meaning of child vobjects, or tag the vobject for other special treatment by an application.

  4. The Vobject has an ordered, associative list of links to other Vobjects. Each link has a position and is tagged with an additional contextual name. This used by the application to determine how to interpret the child (linked-to vobject) in the context of the parent (linked-from vobject). The contextual name may be used more than once in a given child list, and may be blank, in which case the link is characterized only by its position.

  5. Vobject parent-child links are bidirectional. A Vobject can be a child of multiple other vobjects, and should be aware of each inbound link. The application can get a list of all parents of a particular Vobject. In the case that one side does not honor this link, the parent (vobject on which the link is outgoing) is definitive.

  6. The Vobject has a default set of access control policies, one policy for each access control domain.

  7. The Vobject has a set of Access Control Lists (ACLs), where a list consists of a complete policy (covering every relevant access control domain) and a list of identities and/or groups to which the policy shall be applied. A group or identity may not apppear in more than one ACL on the same Vobject.

Figure 3-3. An example site with five vobjects describing an simple virtual world

3.2.3. Sites

Sites are a special type of Vobject which, in addition to following the above object model, act as the connection point between vobjects which are not in the same address space. Sites encapsulate some networking medium used to transport messages to their destination; this medium could be TCP, UDP, ATM Virtual Circuts, shared memory backplanes or whatever other systems one might run VOS over.[1]

An application must create at least one local site. This site is used to manage connections to remote sites as well as host local vobjects.

A vobject may be refered to through many possible paths, making it difficult to determine if two given paths actually refer to the same vobject. Because of this, every vobject is required to be bound to exactly one site as a direct child with a unique contextual name. This restriction allows us to give every Vobject a relativly short, globally unique URI using the site's contact information and vobject's site name. Other Vobject paths are discussed in more detail below.

3.2.4. Messages

A message consists of the following information.

  1. A message type, may be one of: message, update, or messageblock. Required.

  2. To and From fields: names of the source and destination vobjects. Optional. The To field defaults to the site that receives the message, the from field defaults to the site that sent the message.

  3. A Method field: indicates the request or purpose of this message. Required

  4. A Nonce field: used to match replies with requests; should be otherwise unique. Usually required for messages that expect replies.

  5. A Time field: contains a message timestamp. Currently the format of this field is not specified by VOS (and indeed this field is not set in the current VOS implementation but is reserved for future expansion).

  6. After the above header fields there is an ordered, associative list of parameters. Each parameter has a key (which may not be blank but a key may be repeated in the same message) and a value.

Items 1-5 are headers containing message metainformation that must be treated specially, item 6 is the message "payload", which is split into user-defined fields.

Messages with the update type are a special sort. These messages indicate that a requested or listened-to bit of information has changed. It is desirable to direct these cache updates to the code handling that particular remote vobject. As a result, an "update" type messages suggests that the message be delivered to the local stub for the remote object, which contains the the code for handling request replies and cache updates.

3.2.5. Namespaces

VOS has a simple namespace system for avoid the confusion of the same identifier being used in different situations and to indicate to the user the context of a given identifier. One simply prefixes the identifier with the namespace and a colon. Namespace prefixes are generally used on type names, method names, child link names and access control policies. Common examples include "core:" for the core VOS API, "property:" for property metaobjects and "a3dl:" for identifiers dealing with the Abstract 3D Layer metaobjects.

3.2.6. Types

The core of the VOS extension mechanism is the flexible vobject type system. Each Vobject has a set of type strings; the elements of this set are used to advise the application on how to handle this Vobject. This may include what messages the Vobject accepts or produces, the names, types and interpretation of expected child objects, or other domain-specific metainformation about the vobject. Vobjects may have any number of type strings, allowing for polymorphic objects. If no types are specified, the object only supports the basic vobject API.

Type strings are almost free form, with only one notable exception. If a type contains one or more period characters ('.', ASCII 46), it means that the type is a subclass of each type string that would be produced if the portion of the type string following each period were removed in turn. For example, a vobject with the type "object3D.cylinder" inherits all the aspects of "a3dl:object3D". Were there to be another subclass "a3dl:object3D.cylinder.foo" (not a real type) it would be expected to inherit all aspects from "a3dl:object3D" as well as "a3dl:object3D.cylinder". A corollary from this is that if an application encounters a type it does not understand (such as the example "a3dl:object3D.cylinder.foo") it may work its way up the inheritance until it finds a type that it does understand (perhaps "a3dl:object3D.cylinder" in this case.)

3.2.7. Linking and Naming

One of the main uses of vobject links are to group vobjects in "contains" or "describes" relationships. These typically take the form of a trees or Directed Acyclic Graph (DAG), but Vobject links can form any directed graph. Every vobject has an ordered, associative list of outgoing child links as well as a set of incoming parent links .

Links are graph edges and have several attributes. They list the parent (source) and child (destination) vobjects, as well as the contextual name and position in the parent's child list. Each link in the child list is characterized by its position; the name (which may be repeated or blank) is used to determine the context in which to interpret the particular child vobject. For example, in figure 2-3 the vobject with site name "cube" has three child links. These links are named "a3dl:position", "a3dl:orientation", and "a3dl:material". Each linked-to vobject has the "property:property" type, which means they store some data. Because the parent vobject is of type "a3dl:object3D.cube", this indicates to the application that the information stored in the vobject linked through as "a3dl:orientation" should be used to affect the presentation of the vobject, in this case by changing its rotation.

Vobjects are addressed using URLs in the format vop://hostname[:port]/objname Consider the following examples, all of which could be used to refer to the same vobject .

  • vop://interreality.org/world/ball/position

This refers to the vobject storing the position of a ball, which is contained in a virtual world at the site interreality.org. Note that this path is not the only way of referring to this object. Here are a couple more ways:

  • vop://interreality.org/1264095060

  • vop://interreality.org/1474612399/position

The former is the unique name of the Vobject on its site. The latter directly addresses the "position" object via the "ball" Vobject, instead of indirecting through the "world" Vobject first.

Note that the fact that "vop://interreality.org/1264095060" happens to denote the position of some thing is entirely contextual, and determined by the parent-child linking. Another Vobject could easily link to this with a different name, in which case the same vobject could take on an entirely different meaning—because a single vobject may have multiple types such a situation is quite reasonable.

Because the basic Vobject linking model is standard across all vobjects, the same tools to access and inspect the Vobject structure can be used for a variety of applications. For example, one tool is the command line shell mesh (described in chapter 3) which allows one to browse vobject structures using familiar commands like "cd" and "ls" as well as send and receive messages interactively.

If the port is omitted in a URL, the default port 4231 is assumed.

3.2.8. Listeners

An important feature of VOS is the ability to set up listeners to receive notification whenever the state of a Vobject changes. Notifications are sent out on child add/replace/remove, parent add/remove and type add/remove. The listener pattern is also used in various metaobject extensions including the property:property and a3dl:actor.

3.2.9. Identities and Groups

An Identity is a local Vobject with type "core:identity". It is used by the access control system to represent the permissions granted to a remote site when accessing resources on the local site. When a remote site first connects, it has an anonymous identity. By logging in (performing an authentication protocol) the remote site gains whatever permissions are associated with that identity for the duration of the session. A connected remote site can only have one identity at a time. If the remote site authenticates itself as a different Identity then it loses the old identity and gains the new one.

Another way of thinking about it is that an identity is like a user account on VOS site. By logging in you "become" that identity, with whatever permissions and restrictions to access the system that user account entails.

A Group is a local Vobject of type "core:group" which represents a group of Identity Vobjects. Each child link of the Group Vobject named "core:member" is considered a member of the group. Groups are used by the access control system to apply a policies to a group of identities rather than having to name every identity specifically. Groups cannot contain other groups.

3.2.10. Access Control

Since VOS is designed for use in a multiuser environment, there is an obvious need to be able to apply different levels of access to to different users. For example, for some Vobject one may want to completely deny access by default, but grant read-only access to certain a group of users and give a specific user full read-write access. VOS has a flexible system for describing which access control policy to apply based on the identity and group membership of the requester and on the operation in question.

Formally speaking, a "policy" is a decision process that determines whether to allow or deny a requested operation. A policy may have complicated logic that takes into account the details of operation or it may just be a blanket "yes" or "no" for some operation. Policies are divided into domains, where a domain is a specific set of access control checks against a specific set of actions. For example, the "core" domain contains policies that apply to the core API: reading and writing the types, parents, children, and access control of a Vobject. The "property" domain has policies for reading and writing properties, and so forth. The use of domains allows the access control system to be extended to cover new actions as new Metaobject types are developed.

So, the process of applying access control to a request has two steps: determining which policy to use, and actually applying the policy. Applying the policy involves mapping the policy name to a concrete implementation in code, and then calling the appropriate method to perform the actual access check. The return value—true or false—determines whether the request is accepted to rejected.

Access control lookups are done using the identity of the requesting site. If the identity is anonymous, then the default policy is applied, otherwise VOS uses Access Control Lists (ACLs) to determine which policy to apply to the given identity. An ACL is characterized by a list of identities and groups, and a set of policies, one for each relevant domain that applies to its members. ACLs are named by concatenating their policies together, separated by commas. For example, an ACL "core:read-only,property:accept-all" means that for "core" access control checks (such as the ability to read the child list and insert new children) apply the "read-only" policy (which, as it suggests, allows reading the vobject state but not changing it). For the "property" access control checks, apply the "accept-all" policy which means that all requests are accepted (full read/write access in other words). Note that an ACL named just "core:read-only" would be distinct from the previous example, because it does NOT specify any policy in the property domain. If no policy is supplied for the desired domain then the operation must fail (to do otherwise would be quite insecure!)

Access control lookup works by searching first for the identity, and then any groups the identity belongs to using the follow algorithm:

  1. Check each ACL to see if it lists this Identity. If so, use that ACL's policy and terminate.

  2. Otherwise, check each ACL for groups that this Identity belongs to. If the Identity is a member of several Groups that are in different ACLs, then return the policy for each relevant ACL. The caller should check every policy to determine pass or fail—this is up to the caller, but commonly in VOS code if any policy grants permission then permission is given. This means that groups can be used to add permissions, but not take them away! Design your access control scheme accordingly (and make the default permissions as restrictive as possible).

  3. Otherwise, because neither the Identity nor any of its Groups appear in any ACL, return the default access control.

Notes

[1]

As of this writing ($Date: 2005/03/12 17:42:47 $) VOS supports two transport protocols, VOP which passes serialized messages over TCP, and the more flexible VIP which uses UDP to pass messages, with programmer-configurable priorities and resend policies useful for various kinds and purposes of messages.