Herqq
Classes | Typedefs

Device Model

HUPnP Core

This page explains the concept of HUPnP Device Model, which is the logical object hierarchy of HUPnP representing the UPnP Device Architecture. More...

Classes

class  HClientAction
 A client-side class that represents a server-side UPnP action. More...
class  HClientActionOp
 This class is used to identify a client-side action invocation and detail information of it. More...
class  HClientDevice
 This is a client-side class that represents a server-side UPnP device. More...
class  HClientService
 A client-side class that represents a server-side UPnP service. More...
class  HClientStateVariable
 A client-side class that represents a server-side UPnP state variable. More...
class  HActionArgument
 This is a class that represents an argument used in a UPnP action invocation. More...
class  HActionArguments
 A storage class for HActionArgument instances. More...
class  HActionSetup
 This class is used to specify information that can be used to setup an HServerAction or validate a UPnP action. More...
class  HActionsSetupData
 This class is used to specify information that can be used to setup HServerAction instances or generally validate the actions of a UPnP service. More...
class  HAsyncOp
 This abstract class is used as a base for identifying an asynchronous operation and detail information of it. More...
class  HDeviceModelInfoProvider
 A protocol class for providing information that is used to validate components of UPnP's device architecture and to setup components of HUPnP's device model. More...
class  HDeviceSetup
 This class is used to specify information that can be used to validate a UPnP device. More...
class  HDevicesSetupData
 This class is used to specify information that can be used to validate UPnP devices. More...
class  HExecArgs
 This class is used to specify information used to control the execution of an asynchronous operation and the notification of its completion. More...
class  HServiceSetup
 This class is used to specify information that can be used to validate a UPnP service. More...
class  HServicesSetupData
 This class is used to specify information that can be used to validate UPnP services. More...
class  HStateVariableEvent
 This is a class used to transfer state variable event information. More...
class  HStateVariablesSetupData
 This class is used to specify information that can be used to validate UPnP state variables. More...
class  HDeviceModelCreator
 A protocol class for creating HServerDevice and HServerService instances. More...
class  HServerAction
 A class that represents a server-side UPnP action. More...
class  HServerDevice
 This is an abstract base class for server-side UPnP devices hosted by HDeviceHost. More...
class  HServerService
 This is an abstract base class for server-side UPnP services. More...
class  HServerStateVariable
 This is a class that represents a server-side UPnP state variable. More...

Typedefs

typedef Functor< int,
H_TYPELIST_2(const
Herqq::Upnp::HActionArguments
&, Herqq::Upnp::HActionArguments *) 
HActionInvoke )
typedef Functor< bool,
H_TYPELIST_2(HClientAction
*, const HClientActionOp &) 
HActionInvokeCallback )
typedef QHash< QString,
HActionInvoke > 
HActionInvokes
typedef QList< HClientService * > HClientServices
typedef QList< HServerService * > HServerServices
typedef QList< HClientDevice * > HClientDevices
typedef QList< HServerDevice * > HServerDevices
typedef QHash< QString, const
HClientStateVariable * > 
HClientStateVariables
typedef QHash< QString,
HServerStateVariable * > 
HServerStateVariables
typedef QHash< QString,
HStateVariableInfo > 
HStateVariableInfos
typedef QHash< QString,
HClientAction * > 
HClientActions
typedef QHash< QString,
HServerAction * > 
HServerActions

Detailed Description

This page explains the concept of HUPnP Device Model, which is the logical object hierarchy of HUPnP representing the UPnP Device Architecture.

A few notes about the design

The main four components of the UPnP device model are a device, a service, a state variable and an action. These four components form a type of a tree in which devices and services are contained by devices, and state variables and actions are contained by services. This is called the device tree. A device tree has a root device, which is a UPnP device that has no parent, but may contain other UPnP devices. These contained devices are called embedded devices.

HUPnP's device model mimicts this design closely. At server-side the main four components are HServerDevice, HServerService, HServerStateVariable and HServerAction. At client-side the main four components are HClientDevice, HClientService, HClientStateVariable and HClientAction.

The purpose of the other classes part of the HUPnP's device model is to support the initialization and use of the four core components both at the server and client-side.

API differences between client and server sides

The HUPnP device model is largely the same at the server and client sides. That is, whether you are writing a custom UPnP device or trying to interact with a UPnP device found in the network, you will be interacting with the HUPnP device model in a similar manner. Regardless of that, there are some important differences, which is why the server and client-side define and use different types that do not share ancestors provided by HUPnP.

First and most importantly, server side contains the "businness" logic of a UPnP device and clients only invoke or use it. This logic should not be duplicated to the client-side, as it serves no purpose there. Having a design that explicitly states this separation of concerns at type level should certainly help in making the purpose of each type clear.

Second, UPnP clients are unable to modify server-side state variables directly and in a uniform manner. This is because UPnP Device Architecture does not specify a mechanism for changing the value of a state variable from client-side. Certainly the value of a state variable may be changeable, but that and the way it is done depends of the service type in which the state variable is defined. On the other hand, server-side has to have direct read-write access to the state variables. This type of difference should be explicit in the design.

Third, client-side action invocation should naturally be asynchronous to the user, as the call most often involves network access. On the server-side the action invocations are direct method calls and as such the burden of running them "asynchronously" with the help of worker threads should reside at the user code.

The lifetime and ownership of objects

Every device (HClientDevice and HServerDevice) has the ownership of all of its embedded devices, services, actions and state variables and the ownership is never released. This means that every device always manages the memory used by the objects it owns. Hence, the owner of a root device ultimately has the ownership of an entire device tree.

This is a very important point to remember: the lifetime of every object contained by the root device depends of the lifetime of the root device.

In other words, when a root device is deleted, every embedded device, service, state variable and action underneath it are deleted as well. Furthermore, every root device is always owned by HUPnP and the ownership is never released. Because of this you must never call delete to any of the components of the device model that is setup by HUPnP. Failing to follow this rule will result in undefined behavior.

Note:
There are situations where you may want to instruct HUPnP to delete a device. For instance, when a UPnP device is removed from the network you may want your HControlPoint instance to remove the device that is no longer available. This can be done through the HControlPoint interface. But note, HUPnP never deletes a device object without an explicit request from a user.

Usage

Basic use is about interacting with already created objects that comprise the device model. To get started you need to initialize either a device host or a control point and retrieve a device or a list of devices from it. See Device Hosting for more information about device hosts and control points. Once you have access to a device you can interact with any of its embedded devices, services, state variables and actions until:

See the corresponding classes for more information concerning their use.

Note:
By default, HControlPoint keeps the state of the state variables up-to-date. That is, using default configuration an HControlPoint automatically subscribes to events the UPnP services expose. In such a case the state of a device tree the control point maintains reflects the state of the corresponding device tree at server-side as accurately as the server keeps sending events.

If you wish to implement and host your own UPnP device things get more involved. See Tutorial for Building a UPnP Device to get started on building your own UPnP devices using HUPnP.


Typedef Documentation

typedef Functor<int, H_TYPELIST_2( const Herqq::Upnp::HActionArguments&, Herqq::Upnp::HActionArguments*) HActionInvoke)

This is a type definition for a callable entity that is used for HServerAction invocation.

You can create HActionInvoke objects using normal functions, functors and member functions that follow the signature of

qint32 function(const Herqq::Upnp::HActionArguments& inArgs, Herqq::Upnp::HActionArguments* outArgs = 0);

The following example demonstrates how you can instantiate the HActionInvoke for a normal function, functor and a member function.

 #include <HActionInvoke>
 #include <HUpnpCore/HActionArguments>

 #include "myclass.h" // your code that contains declaration for MyClass

 namespace
 {
 qint32 freefun(
      const Herqq::Upnp::HActionArguments& inArgs,
      Herqq::Upnp::HActionArguments* outArgs)
 {
     return 0;
 }

 class MyFunctor
 {
 public:
     qint32 operator()(
         const Herqq::Upnp::HActionArguments& inArgs,
         Herqq::Upnp::HActionArguments* outArgs)
     {
         return 0;
     }
 };
 }

 qint32 MyClass::memfun(
      const Herqq::Upnp::HActionArguments& inArgs,
      Herqq::Upnp::HActionArguments* outArgs = 0)
 {
 }

 void MyClass::example()
 {
     Herqq::Upnp::HActionInvoke usingFreeFunction(freefun);

     MyFunctor myfunc;
     Herqq::Upnp::HActionInvoke usingFunctor(myfunc);

     Herqq::Upnp::HActionInvoke usingMemberFunction(this, &MyClass::memfun);
 }

You can test if the object can be invoked simply by issuing if (actionInvokeObject) { ... }

typedef Functor<bool, H_TYPELIST_2( HClientAction*, const HClientActionOp&) HActionInvokeCallback)

This is a type definition for a callable entity that is used as a callback for signaling the completion of an HClientAction invocation.

You can create HActionInvokeCallback objects using normal functions, functors and member functions that follow the signature of

bool function(Herqq::Upnp::HClientAction*, const Herqq::Upnp::HClientActionOp&);

Parameters

  • The first parameter is a type of an "ID" of the asynchronous action invocation.
  • The second parameter specifies the output arguments of the action invocation, which may be empty.

Return value

The return value indicates if the invoked HClientAction should emit an HClientAction::invokeComplete() after the callback has returned.

  • true indicates that the HClientAction should sent the corresponding event.

The following example demonstrates how you can instantiate the HActionInvokeCallback for a normal function, functor and a member function.

 #include <HUpnpCore/HClientAction>

 #include "myclass.h" // your code that contains declaration for MyClass

 namespace
 {
 bool freefun(Herqq::Upnp::HClientAction*, const Herqq::Upnp::HClientActionOp&)
 {
     return true;
 }

 class MyFunctor
 {
 public:
     bool operator()(Herqq::Upnp::HClientAction*, const Herqq::Upnp::HClientActionOp&)
     {
         return true;
     }
 };
 }

 bool MyClass::memfun(Herqq::Upnp::HClientAction*, const Herqq::Upnp::HClientActionOp&)
 {
     return true;
 }

 void MyClass::example()
 {
     Herqq::Upnp::HActionInvokeCallback usingFreeFunction(freefun);

     MyFunctor myfunc;
     Herqq::Upnp::HActionInvokeCallback usingFunctor(myfunc);

     Herqq::Upnp::HActionInvokeCallback usingMemberFunction(this, &MyClass::memfun);
 }

You can test if the object can be invoked simply by issuing if (actionInvokeCallbackObject) { ... }

typedef QHash<QString, HActionInvoke> HActionInvokes [protected, inherited]

This is a type definition for a hash table containing HActionInvoke objects keyed with strings representing the names of the actions.

See also:
HActionInvoke
typedef QList<HClientService*> HClientServices

This is a type definition to a list of pointers to Herqq::Upnp::HClientService instances.

See also:
HClientService
typedef QList<HServerService*> HServerServices

This is a type definition to a list of pointers to Herqq::Upnp::HServerService instances.

See also:
HServerService
typedef QList<HClientDevice*> HClientDevices

This is a type definition to a list of pointers to Herqq::Upnp::HClientDevice instances.

See also:
HClientDevice
typedef QList<HServerDevice*> HServerDevices

This is a type definition to a list of pointers to Herqq::Upnp::HServerDevice instances.

See also:
HServerDevice
typedef QHash<QString, const HClientStateVariable*> HClientStateVariables

This is a type definition to a hash table of pointers to const Herqq::Upnp::HServerStateVariable instances keyed with the state variable names.

See also:
HClientStateVariable
typedef QHash<QString, HServerStateVariable*> HServerStateVariables

This is a type definition to a hash table of pointers to Herqq::Upnp::HServerStateVariable instances keyed with the state variable names.

See also:
HServerStateVariable
typedef QHash<QString, HStateVariableInfo> HStateVariableInfos

This is a type definition to a hash table of Herqq::Upnp::HStateVariableInfo instances keyed with the state variable names.

See also:
HStateVariableInfo
typedef QHash<QString, HClientAction*> HClientActions

This is a type definition to a hash table of pointers to Herqq::Upnp::HClientAction instances keyed with the action names.

See also:
HClientAction
typedef QHash<QString, HServerAction*> HServerActions

This is a type definition to a hash table of pointers to Herqq::Upnp::HServerAction instances keyed with the action names.

See also:
HServerAction