Attribute design considerations

In the current COBS design, attributes and attribute lists are perhaps the most widely-used data structure. They're to be queried to determine the behavior of almost every element of the COBS system and will likely be transmitted with every operation. This implies that attribute list operations should be fast and that their linearized representation must be small. Attributes are envisioned as name-value pairs. The are dynamic in that the set of attributes is unlikely to be determinable at compile time. Attributes and their values must also be able to be transmitted between heterogeneous machines and interpreted at remote sites.

Representation of Attribute Names and Enumerated Types

The dynamic nature and portability requirements point towards a string-based representation mechanism, but doing string operations on every attribute lookup is probably not a good way to make them fast. To avoid string operations, we borrow an idea from the X windowing system. Standard strings are represented by Atoms. Atoms are 32-bit quantities and the mapping from strings to atoms and back again is uniform across at least the entire application. This way, rather than doing string comparisons to see if an attribute is present, we can translate the attribute name into an atom and then search for a matching atom in the attribute list. (How we search is another issue, but at least direct 32-bit compares are much cheaper than strcmp().) In X, the X server is responsible to doling out Atoms and maintaining a uniform translation (on a single X display). For COBS we'll probably have to create an independent daemon which will maintain the translations. We'll provide a str_to_atom() call which would have to contact the daemon at least for the initial translation of any string. We can optimize later translations by caching results internally and perhaps loading the whole translation database at first contact. (Translations should never change after they are established, so caching isn't a big issue. The daemon getting restarted would hose things, but we just have to avoid that...)

Attribute Value Representation

Attribute values may be simple integers, addresses, enumerated types, strings or perhaps other things. Probably we don't want to represent them all as strings either, so we have to know what type they are for transmission. Currently, I imagine needing at least the following types:
  typedef enum _atom_value_type { 
	Attr_Undefined, Attr_Int4, 
	Attr_Int8, Attr_String 
} atom_value_type;
We may have to add to this. The int's can probably hold addresses as well. Things to think about:

Operations on Attribute lists

What operations we want to support on attribute lists depends upon how we plan to use them. It's clear that we must be able to construct and to query attribute lists, but beyond that things are somewhat murkier. We've mentioned having lists of attributes associated with object pointers as well as having attributes specifiable at the point of invocation. This implies at least a merger operation of some kind. As part of fancy naming services, we've also considered that name translations might be cached as attributes, presumably associated with the object pointer. This implies that we require the ability for the code layers that an invocation passes through to modify the original (pre-merge) attribute lists. Probably this means that list "mergers" don't involve copying both lists to produce a new one. So list merging probably takes place by keeping pointers to the original lists. (This is probably also faster than copying.) However, this complicates alloc()/free() somewhat as you never know who might be keeping a pointer to a list. A memory management scheme based on reference counts should help handle this as long as we can guarantee no circularities... We also need to consider that some software layers will want to add attributes to the list as the invocation passes through. For example, it's easy to imagine that the method code should be able to query its attributes to find out if it's running at the interrupt level. So we're going to need some kind of scratch area for writing such temporary values into. (And we've got to figure out how some added attributes are "temporary" while others (cached name translations) are more sticky.)

Proposed API and Implementation