Added implementation of the node monitoring functions.
git-svn-id: file:///srv/svn/repos/haiku/trunk/current@3065 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -0,0 +1,217 @@
|
|||||||
|
//----------------------------------------------------------------------
|
||||||
|
// This software is part of the OpenBeOS distribution and is covered
|
||||||
|
// by the OpenBeOS license.
|
||||||
|
//---------------------------------------------------------------------
|
||||||
|
|
||||||
|
#include <AppMisc.h>
|
||||||
|
#include <Looper.h>
|
||||||
|
#include <Messenger.h>
|
||||||
|
#include <NodeMonitor.h>
|
||||||
|
|
||||||
|
// TODO: Tests!
|
||||||
|
|
||||||
|
// private libroot.so functions
|
||||||
|
|
||||||
|
/*! \brief Subscribes a target to node and/or mount watching.
|
||||||
|
|
||||||
|
Depending on \a flags, different actions are performed. If flags is \c 0,
|
||||||
|
mount watching is requested. \a device and \a node must be \c -1 in this
|
||||||
|
case. Otherwise node watching is requested. \a device and \a node must
|
||||||
|
refer to a valid node, and \a flags must note contain the flag
|
||||||
|
\c B_WATCH_MOUNT, but at least one of the other valid flags.
|
||||||
|
|
||||||
|
\param device The device the node resides on (node_ref::device). \c -1, if
|
||||||
|
only mount watching is requested.
|
||||||
|
\param node The node ID of the node (node_ref::device). \c -1, if
|
||||||
|
only mount watching is requested.
|
||||||
|
\param flags A bit mask composed of the values specified in
|
||||||
|
<NodeMonitor.h>.
|
||||||
|
\param port The port of the target (a looper port).
|
||||||
|
\param handlerToken The token of the target handler. \c -2, if the
|
||||||
|
preferred handler of the looper is the target.
|
||||||
|
\return \c B_OK, if everything went fine, another error code otherwise.
|
||||||
|
*/
|
||||||
|
extern "C" status_t _kstart_watching_vnode_(dev_t device, ino_t node,
|
||||||
|
uint32 flags, port_id port,
|
||||||
|
int32 handlerToken);
|
||||||
|
|
||||||
|
/*! \brief Unsubscribes a target from watching a node.
|
||||||
|
\param device The device the node resides on (node_ref::device).
|
||||||
|
\param node The node ID of the node (node_ref::device).
|
||||||
|
\param port The port of the target (a looper port).
|
||||||
|
\param handlerToken The token of the target handler. \c -2, if the
|
||||||
|
preferred handler of the looper is the target.
|
||||||
|
\return \c B_OK, if everything went fine, another error code otherwise.
|
||||||
|
*/
|
||||||
|
extern "C" status_t _kstop_watching_vnode_(dev_t device, ino_t node,
|
||||||
|
port_id port, int32 handlerToken);
|
||||||
|
|
||||||
|
|
||||||
|
/*! \brief Unsubscribes a target from node and mount monitoring.
|
||||||
|
\param port The port of the target (a looper port).
|
||||||
|
\param handlerToken The token of the target handler. \c -2, if the
|
||||||
|
preferred handler of the looper is the target.
|
||||||
|
\return \c B_OK, if everything went fine, another error code otherwise.
|
||||||
|
*/
|
||||||
|
extern "C" status_t _kstop_notifying_(port_id port, int32 handlerToken);
|
||||||
|
|
||||||
|
|
||||||
|
// actual implementation
|
||||||
|
|
||||||
|
// watch_node
|
||||||
|
/*! \brief Subscribes a target to node and/or mount watching, or unsubscribes
|
||||||
|
it from node watching.
|
||||||
|
|
||||||
|
Depending of \a flags the action performed by this function varies:
|
||||||
|
- \a flags is \c 0: The target is unsubscribed from watching the node.
|
||||||
|
\a node must not be \c NULL in this case.
|
||||||
|
- \a flags contains \c B_WATCH_MOUNT: The target is subscribed to mount
|
||||||
|
watching.
|
||||||
|
- \a flags contains at least one of \c B_WATCH_NAME, \c B_WATCH_STAT,
|
||||||
|
\c B_WATCH_ATTR, or \c B_WATCH_DIRECTORY: The target is subscribed to
|
||||||
|
watching the specified aspects of the node. \a node must not be \c NULL
|
||||||
|
in this case.
|
||||||
|
|
||||||
|
Note, that the latter two cases are not mutual exlusive, i.e. mount and
|
||||||
|
node watching can be requested with a single call.
|
||||||
|
|
||||||
|
\param node node_ref referring to the node to be watched. May be \c NULL,
|
||||||
|
if only mount watching is requested.
|
||||||
|
\param flags Flags indicating the actions to be performed.
|
||||||
|
\param target Messenger referring to the target. Must be valid.
|
||||||
|
\return \c B_OK, if everything went fine, another error code otherwise.
|
||||||
|
*/
|
||||||
|
status_t
|
||||||
|
watch_node(const node_ref *node, uint32 flags, BMessenger target)
|
||||||
|
{
|
||||||
|
status_t error = (target.IsValid() ? B_OK : B_BAD_VALUE);
|
||||||
|
if (error == B_OK) {
|
||||||
|
BLooper *looper = NULL;
|
||||||
|
BHandler *handler = target.Target(&looper);
|
||||||
|
error = watch_node(node, flags, handler, looper);
|
||||||
|
}
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
|
||||||
|
// watch_node
|
||||||
|
/*! \brief Subscribes a target to node and/or mount watching, or unsubscribes
|
||||||
|
it from node watching.
|
||||||
|
|
||||||
|
Depending of \a flags the action performed by this function varies:
|
||||||
|
- \a flags is \c 0: The target is unsubscribed from watching the node.
|
||||||
|
\a node must not be \c NULL in this case.
|
||||||
|
- \a flags contains \c B_WATCH_MOUNT: The target is subscribed to mount
|
||||||
|
watching.
|
||||||
|
- \a flags contains at least one of \c B_WATCH_NAME, \c B_WATCH_STAT,
|
||||||
|
\c B_WATCH_ATTR, or \c B_WATCH_DIRECTORY: The target is subscribed to
|
||||||
|
watching the specified aspects of the node. \a node must not be \c NULL
|
||||||
|
in this case.
|
||||||
|
|
||||||
|
Note, that the latter two cases are not mutual exlusive, i.e. mount and
|
||||||
|
node watching can be requested with a single call.
|
||||||
|
|
||||||
|
\param node node_ref referring to the node to be watched. May be \c NULL,
|
||||||
|
if only mount watching is requested.
|
||||||
|
\param flags Flags indicating the actions to be performed.
|
||||||
|
\param handler The target handler. May be \c NULL, if \a looper is not
|
||||||
|
\c NULL. Then the preferred handler of the looper is targeted.
|
||||||
|
\param looper The target looper. May be \c NULL, if \a handler is not
|
||||||
|
\c NULL. Then the handler's looper is the target looper.
|
||||||
|
\return \c B_OK, if everything went fine, another error code otherwise.
|
||||||
|
*/
|
||||||
|
status_t
|
||||||
|
watch_node(const node_ref *node, uint32 flags, const BHandler *handler,
|
||||||
|
const BLooper *looper)
|
||||||
|
{
|
||||||
|
status_t error = B_OK;
|
||||||
|
// check looper and handler and get the handler token
|
||||||
|
int32 handlerToken = -2;
|
||||||
|
if (handler) {
|
||||||
|
handlerToken = _get_object_token_(handler);
|
||||||
|
if (looper) {
|
||||||
|
if (looper != handler->Looper())
|
||||||
|
error = B_BAD_VALUE;
|
||||||
|
} else {
|
||||||
|
looper = handler->Looper();
|
||||||
|
if (!looper)
|
||||||
|
error = B_BAD_VALUE;
|
||||||
|
}
|
||||||
|
} else if (!looper)
|
||||||
|
error = B_BAD_VALUE;
|
||||||
|
if (error == B_OK) {
|
||||||
|
port_id port = _get_looper_port_(looper);
|
||||||
|
if (flags == B_STOP_WATCHING) {
|
||||||
|
// unsubscribe from node node watching
|
||||||
|
if (node) {
|
||||||
|
error = _kstop_watching_vnode_(node->device, node->node, port,
|
||||||
|
handlerToken);
|
||||||
|
} else
|
||||||
|
error = B_BAD_VALUE;
|
||||||
|
} else {
|
||||||
|
// subscribe to...
|
||||||
|
// mount watching
|
||||||
|
if (flags & B_WATCH_MOUNT) {
|
||||||
|
error = _kstart_watching_vnode_(-1, -1, 0, port, handlerToken);
|
||||||
|
flags &= ~B_WATCH_MOUNT;
|
||||||
|
}
|
||||||
|
// node watching
|
||||||
|
if (error == B_OK && flags) {
|
||||||
|
error = _kstart_watching_vnode_(node->device, node->node,
|
||||||
|
flags, port, handlerToken);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
|
||||||
|
// stop_watching
|
||||||
|
/*! \brief Unsubscribes a target from node and mount monitoring.
|
||||||
|
\param target Messenger referring to the target. Must be valid.
|
||||||
|
\return \c B_OK, if everything went fine, another error code otherwise.
|
||||||
|
*/
|
||||||
|
status_t
|
||||||
|
stop_watching(BMessenger target)
|
||||||
|
{
|
||||||
|
status_t error = (target.IsValid() ? B_OK : B_BAD_VALUE);
|
||||||
|
if (error == B_OK) {
|
||||||
|
BLooper *looper = NULL;
|
||||||
|
BHandler *handler = target.Target(&looper);
|
||||||
|
error = stop_watching(handler, looper);
|
||||||
|
}
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
|
||||||
|
// stop_watching
|
||||||
|
/*! \brief Unsubscribes a target from node and mount monitoring.
|
||||||
|
\param handler The target handler. May be \c NULL, if \a looper is not
|
||||||
|
\c NULL. Then the preferred handler of the looper is targeted.
|
||||||
|
\param looper The target looper. May be \c NULL, if \a handler is not
|
||||||
|
\c NULL. Then the handler's looper is the target looper.
|
||||||
|
\return \c B_OK, if everything went fine, another error code otherwise.
|
||||||
|
*/
|
||||||
|
status_t
|
||||||
|
stop_watching(const BHandler *handler, const BLooper *looper)
|
||||||
|
{
|
||||||
|
status_t error = B_OK;
|
||||||
|
// check looper and handler and get the handler token
|
||||||
|
int32 handlerToken = -2;
|
||||||
|
if (handler) {
|
||||||
|
handlerToken = _get_object_token_(handler);
|
||||||
|
if (looper) {
|
||||||
|
if (looper != handler->Looper())
|
||||||
|
error = B_BAD_VALUE;
|
||||||
|
} else {
|
||||||
|
looper = handler->Looper();
|
||||||
|
if (!looper)
|
||||||
|
error = B_BAD_VALUE;
|
||||||
|
}
|
||||||
|
} else if (!looper)
|
||||||
|
error = B_BAD_VALUE;
|
||||||
|
// unsubscribe
|
||||||
|
if (error == B_OK) {
|
||||||
|
port_id port = _get_looper_port_(looper);
|
||||||
|
error = _kstop_notifying_(port, handlerToken);
|
||||||
|
}
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
|
||||||
@@ -11,6 +11,7 @@ STORAGE_KIT_SOURCE =
|
|||||||
MimeType.cpp
|
MimeType.cpp
|
||||||
Node.cpp
|
Node.cpp
|
||||||
NodeInfo.cpp
|
NodeInfo.cpp
|
||||||
|
NodeMonitor.cpp
|
||||||
OffsetFile.cpp
|
OffsetFile.cpp
|
||||||
Path.cpp
|
Path.cpp
|
||||||
Query.cpp
|
Query.cpp
|
||||||
|
|||||||
Reference in New Issue
Block a user