Page Menu
Home
Phorge
Search
Configure Global Search
Log In
Files
F375348
AgentHandle.hpp
No One
Temporary
Actions
Download File
Edit File
Delete File
View Transforms
Subscribe
Size
8 KB
Referenced Files
None
Subscribers
None
AgentHandle.hpp
View Options
//===-- rosa/core/AgentHandle.hpp -------------------------------*- C++ -*-===//
//
// The RoSA Framework
//
//===----------------------------------------------------------------------===//
///
/// \file rosa/core/AgentHandle.hpp
///
/// \author David Juhasz (david.juhasz@tuwien.ac.at)
///
/// \date 2017
///
/// \brief Declaration of a handle for \c rosa::Agent.
///
//===----------------------------------------------------------------------===//
#ifndef ROSA_CORE_AGENTHANDLE_HPP
#define ROSA_CORE_AGENTHANDLE_HPP
#include
"rosa/core/AbstractAgent.hpp"
namespace
rosa
{
/// Wraps an actual \c rosa::Agent to decouple its public interface.
/// \note Such decoupling might be necessary when operating with remote
/// *systems*, sometime in the future.
class
AgentHandle
:
public
AbstractAgent
<
AgentHandle
>
{
/// \c rosa::Agent and \c rosa::MessagingSystem are our friends, they may
/// inspect the private member fields of the class.
///@{
friend
class
Agent
;
friend
class
MessagingSystem
;
///@}
/// The wrapped \c rosa::Agent instance.
Agent
&
A
;
/// The \c rosa::MessagingSystem owning \c A.
MessagingSystem
&
S
;
/// Creates a new instance without validating the state of the wrapped
/// \c rosa::Agent.
///
/// \note Used by a \c rosa::Agent instance to create a reference to itself
/// during construction, when its state is not valid yet.
///
/// \param A \c rosa::Agent to wrap
///
/// \note There a second argument, which is ignored, that is only present to
/// separate this constructor from the public constructor taking only a
/// \c rosa::Agent to wrap.
AgentHandle
(
Agent
&
A
,
bool
)
noexcept
;
public
:
/// Creates a new instance validating the state of the wrapped \p rosa::Agent.
///
/// \note The wrapped \c rosa::Agent must be in a valid state to instantiate
/// \c rosa::AgentHandle with this constructor.
///
/// \param A \c rosa::Agent to wrap
///
/// \pre \p A is registered in its owning *system*:\code
/// A.system().isUnitRegistered(A)
/// \endcode
AgentHandle
(
Agent
&
A
);
/// Destroys \p this object.
///
/// The destructor has nothing to take care of.
~
AgentHandle
(
void
)
=
default
;
/// Tells if the wrapped \c rosa::Agent is in a valid state.
///
/// \note A \c rosa::AgentHandler belongs to a \c rosa::MessagingSystem.
/// Working with a \c rosa::AgentHandler whose originating
/// \c rosa::MessagingSystem has already been destroyed results in *undefined*
/// behavior.
///
/// \return if the wrapped \c rosa::Agent is in a valid state
operator
bool
(
void
)
const
noexcept
override
;
/// Tells if another \c rosa::AgentHandle wraps the same \c rosa::Agent as
/// \p this object.
///
/// \param H \c rosa::AgentHandle whose wrapped \c rosa::Agent to check
///
/// \return if \p H wraps \c A like \p this object
bool
operator
==
(
const
AgentHandle
&
H
)
const
noexcept
override
;
/// Compares \p this object to another \c rosa::AgentHandle instance.
///
/// The comparison is based on the memory addresses of the wrapped
/// \c rosa::Agent instances.
///
/// \param H \c rosa::AgentHandle to compare to
///
/// \return if \p this object a \c rosa::Agent instance whose address is less
/// than that of \p H
bool
operator
<
(
const
AgentHandle
&
H
)
const
noexcept
override
;
/// Returns a reference to the wrapped \c rosa::Agent.
///
/// \return a reference to \c A
AgentHandle
self
(
void
)
noexcept
override
;
/// Sends a given \c rosa::message_t instance to the wrapped \c rosa::Agent.
///
/// \param M message to send
///
/// \pre The wrapped \c rosa::Agent instance is in a valid state:\code
/// bool(*this)
/// \endcode
void
sendMessage
(
message_t
&&
M
)
noexcept
override
;
};
/// Template specialization for optionally storing \c rosa::AgentHandle
/// instances.
///
/// \ingroup Optional
///
/// Due to \c rosa::AgentHandle not supporting copying and moving of instances,
/// the member functions in this class fall back to destroying the old stored
/// object and creating a new one whenever the stored value is to be changed.
template
<>
class
Optional
<
AgentHandle
>
{
public
:
using
Type
=
AgentHandle
;
/// Creates an instance without value.
///
/// \note Use it with its default parameter.
Optional
(
const
none_t
&
=
none
)
:
Valid
(
false
)
{}
/// Creates a valid instance with value.
///
/// \param X value to store in the object
Optional
(
AgentHandle
X
)
:
Valid
(
false
)
{
cr
(
std
::
move
(
X
));
}
/// Creates an instance as a copy of another one.
///
/// \param Other the instance whose state to copy
Optional
(
const
Optional
&
Other
)
:
Valid
(
false
)
{
if
(
Other
.
Valid
)
{
cr
(
Other
.
Value
);
}
}
/// Creates an instance as a copy of another one.
///
/// \param Other the instance whose state to obtain
Optional
(
Optional
&&
Other
)
noexcept
:
Valid
(
false
)
{
if
(
Other
.
Valid
)
{
cr
(
std
::
move
(
Other
.
Value
));
}
}
/// Destroys \p this object.
~
Optional
(
void
)
{
destroy
();
}
/// Updates \p this object by copying the state of another one.
///
/// \param Other the instance whose state to copy
///
/// \return reference of the updated instance
Optional
&
operator
=
(
const
Optional
&
Other
)
{
if
(
Valid
)
{
destroy
();
}
if
(
Other
.
Valid
)
{
cr
(
Other
.
Value
);
}
return
*
this
;
}
/// Updates \p this object by copying the state of another one.
///
/// \param Other the instance whose state to obtain
///
/// \return reference of the updated instance
Optional
&
operator
=
(
Optional
&&
Other
)
noexcept
{
if
(
Valid
)
{
destroy
();
}
if
(
Other
.
Valid
)
{
cr
(
std
::
move
(
Other
.
Value
));
}
return
*
this
;
}
/// Checks whether \p this object contains a value.
///
/// \return if \p this object contains a value
explicit
operator
bool
(
void
)
const
{
return
Valid
;
}
/// Checks whether \p this object does not contain a value.
///
/// \return if \p this object does not contain a value
bool
operator
!
(
void
)
const
{
return
!
Valid
;
}
/// Returns the value stored in \p this object.
///
/// \return reference of the stored value
///
/// \pre \p this object contains a value
AgentHandle
&
operator
*
(
void
)
{
ASSERT
(
Valid
);
return
Value
;
}
/// Returns the value stored in \p this object.
///
/// \return reference of the stored value
///
/// \pre \p this object contains a value
const
AgentHandle
&
operator
*
(
void
)
const
{
ASSERT
(
Valid
);
return
Value
;
}
/// Returns the value stored in \p this object.
///
/// \return pointer to the stored value
///
/// \pre \p this object contains a value
const
AgentHandle
*
operator
->
(
void
)
const
{
ASSERT
(
Valid
);
return
&
Value
;
}
/// Returns the value stored in \p this object.
///
/// \return pointer of the stored value
///
/// \pre \p this object contains a value
AgentHandle
*
operator
->
(
void
)
{
ASSERT
(
Valid
);
return
&
Value
;
}
/// Returns the value stored in \p this object.
///
/// \return reference of the stored value
///
/// \pre \p this object contains a value
AgentHandle
&
value
(
void
)
{
ASSERT
(
Valid
);
return
Value
;
}
/// Returns the value stored in \p this object.
///
/// \return reference of the stored value
///
/// \pre \p this object contains a value
const
AgentHandle
&
value
(
void
)
const
{
ASSERT
(
Valid
);
return
Value
;
}
/// Returns the stored value or a default.
///
/// If \p this object contains a value, then the stored value is returned. A
/// given default value is returned otherwise.
///
/// \param DefaultValue the value to return if \p this object does not contain
/// a value
///
/// \return reference to either the stored value or \p DefaultValue if \p this
/// object does not contain a value
const
AgentHandle
&
valueOr
(
const
AgentHandle
&
DefaultValue
)
const
{
return
Valid
?
Value
:
DefaultValue
;
}
private
:
/// Deallocates the stored value if any.
void
destroy
(
void
)
{
if
(
Valid
)
{
Value
.
~
AgentHandle
();
Valid
=
false
;
}
}
/// Updates the state of \p this object by copying a value into it.
///
/// \tparam V type of \p X
///
/// \param X value to copy
///
/// \pre \p this object does not contain a value
template
<
typename
V
>
void
cr
(
V
&&
X
)
{
ASSERT
(
!
Valid
);
Valid
=
true
;
new
(
&
Value
)
AgentHandle
(
std
::
forward
<
V
>
(
X
));
}
/// Denotes if \p this object contains a value.
bool
Valid
;
/// Holds the stored value if any.
union
{
AgentHandle
Value
;
///< The stored value.
};
};
}
// End namespace rosa
#endif
// ROSA_CORE_AGENTHANDLE_HPP
File Metadata
Details
Attached
Mime Type
text/x-c++
Expires
Sat, Jun 7, 5:09 PM (4 h, 33 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
150282
Default Alt Text
AgentHandle.hpp (8 KB)
Attached To
Mode
R20 SoC_Rosa_repo
Attached
Detach File
Event Timeline
Log In to Comment