DTDL - Data Type Definition Language

The Data Type Definition Language is used to describe data types used in a schema of foster.

DTDL allows to define classes, lists and structs. Objects inside DataFS contain one or more classes. Lists and structs are used as multi value attributes.

The following sections describe the basic elements of the language.

Comments

You can write comments in the files in the C++ format.

    // Comment Type 1

    /* Command Type 2 */

class

A class has a unique global id and attributes.

If a class does not have a body, then it's called an "external" class. These classes can be used for linking.

    class Type1 [ id({DA249990-6D74-496E-B06A-C0694033665E}) ]
    {
        int32    value1;
        wstring  value2;
        double   value2 [v];   // variable attribute
    };

struct

... same as class, but the struct is packed into a single binary block and stored in one single attribute.

list

... same as struct. But the items first 16 bytes must be unique. You can use the option 'custom key' if your application can guarantee the uniqueness itself.

    list SampleList [ id({BA506E95-D20C-4E9A-8960-2210E7E46F87}), ck ] // ck for "custom key"
    {
        object  link;		// unique 16 bytes
        wstring strName;
    };

    list SampleList [ id({BA506E95-D20C-4E9A-8960-2210E7E46F88}) ]
    {
        int value;
    };

Preprocessor

The language uses to types of preprocessor commands. The #include and #use. They both load an external file. While #include imports the file and all definitions inside completely, the #use command imports all definitions as external definitions.

The difference between the </> and "/" format is how the file is searched. While " takes the current file as starting point, </> takes the input directories passed to the compiler as starting point for the search.

    #include <file.dtdl>
    #include "..\directory\file.dtdl"

Inheritance

Classes, lists and structs can inherit from one or more types. In this case the action of the compiler can be seen as copy-paste of the inherited types into the inheriting type.

Namespaces

DTDL supports namespaces. There are different possibilities to define namespaces. Either using the way known from C++, a shorter way or by simply putting the namespace name in front of the name of a new type.

    namespace a
    {
        namespace b
        {
            class q; // defines a::b::q
        }
    }

    namespace a::b
    {
        class q; // defines a::b::q
    }

    class a::b::q; // defines a::b::q

Description

You can place a description in front of a definition. This description will be stored in the schema and can be seen as documentation.

    [ this is an empty class ]
    class q
    {};

Data types

TypeDescription
int88 bit signed integer
uint88 bit unsigned integer
int1616 bit signed integer
uint1616 bit unsigned integer
int3232 bit signed integer
uint3232 bit unsigned integer
int6464 bit signed integer
uint6464 bit unsigned integer
int128128 bit signed integer
uint128128 bit unsigned integer
int256256 bit signed integer
uint256256 bit unsigned integer
float32 bit float
double64 bit float
char1 byte character
wchar2 byte character
datetimeFILETIME
string1 byte character string
wstringUTF-16 string
guidGUID
variantVARIANT
bsob[size]binary small object of size 1 to 127 bytes
blob- currently not supported -
stream- currently not supported -
objectobject (an object id or a reference)

Object Types

For values of type 'object' you can specify a set of classes you expect the objects to have when linked by this value. The system does not guarantee that object have all of those classes or restrict operations that cause a violation of these rules.

    objecttype a::b::q.val_obj(type_t); // attribute 'val_obj' of type q in namespace a::b should contain class 'type_t'
© 2020 Mobiland AG