1 /* 2 * Copyright 2011, Ingo Weinhold, ingo_weinhold@gmx.de. 3 * Distributed under the terms of the MIT License. 4 */ 5 #ifndef NODE_LISTENER_H 6 #define NODE_LISTENER_H 7 8 9 #include <time.h> 10 11 #include <util/DoublyLinkedList.h> 12 #include <util/OpenHashTable.h> 13 14 #include "StringKey.h" 15 16 17 class Node; 18 19 20 #define NOT_LISTENING_NODE ((Node*)~(addr_t)0) 21 22 23 class OldNodeAttributes { 24 public: 25 virtual ~OldNodeAttributes(); 26 27 virtual timespec ModifiedTime() const = 0; 28 virtual off_t FileSize() const = 0; 29 virtual void* IndexCookieForAttribute(const StringKey& name) 30 const; 31 }; 32 33 34 class NodeListener { 35 public: 36 NodeListener(); 37 virtual ~NodeListener(); 38 39 virtual void NodeAdded(Node* node); 40 virtual void NodeRemoved(Node* node); 41 virtual void NodeChanged(Node* node, uint32 statFields, 42 const OldNodeAttributes& oldAttributes); 43 StartedListening(Node * node)44 void StartedListening(Node* node) 45 { fNode = node; } StoppedListening()46 void StoppedListening() 47 { fNode = NOT_LISTENING_NODE; } IsListening()48 bool IsListening() const 49 { return fNode != NOT_LISTENING_NODE; } ListenedNode()50 Node* ListenedNode() const 51 { return fNode; } 52 53 inline void AddNodeListener(NodeListener* listener); 54 inline NodeListener* RemoveNodeListener(); 55 PreviousNodeListener()56 NodeListener* PreviousNodeListener() const 57 { return fPrevious; } NextNodeListener()58 NodeListener* NextNodeListener() const 59 { return fNext; } 60 NodeListenerHashLink()61 NodeListener*& NodeListenerHashLink() 62 { return fHashLink; } 63 64 private: 65 NodeListener* fHashLink; 66 NodeListener* fPrevious; 67 NodeListener* fNext; 68 Node* fNode; 69 }; 70 71 72 inline void AddNodeListener(NodeListener * listener)73NodeListener::AddNodeListener(NodeListener* listener) 74 { 75 listener->fPrevious = this; 76 listener->fNext = fNext; 77 78 fNext->fPrevious = listener; 79 fNext = listener; 80 } 81 82 83 inline NodeListener* RemoveNodeListener()84NodeListener::RemoveNodeListener() 85 { 86 if (fNext == this) 87 return NULL; 88 89 NodeListener* next = fNext; 90 91 fPrevious->fNext = next; 92 next->fPrevious = fPrevious; 93 94 fPrevious = fNext = this; 95 96 return next; 97 } 98 99 100 101 struct NodeListenerHashDefinition { 102 typedef Node* KeyType; 103 typedef NodeListener ValueType; 104 HashKeyNodeListenerHashDefinition105 size_t HashKey(Node* key) const 106 { 107 return (size_t)key; 108 } 109 HashNodeListenerHashDefinition110 size_t Hash(const NodeListener* value) const 111 { 112 return HashKey(value->ListenedNode()); 113 } 114 CompareNodeListenerHashDefinition115 bool Compare(Node* key, const NodeListener* value) const 116 { 117 return key == value->ListenedNode(); 118 } 119 GetLinkNodeListenerHashDefinition120 NodeListener*& GetLink(NodeListener* value) const 121 { 122 return value->NodeListenerHashLink(); 123 } 124 }; 125 126 127 typedef DoublyLinkedList<NodeListener> NodeListenerList; 128 typedef BOpenHashTable<NodeListenerHashDefinition> NodeListenerHashTable; 129 130 131 #endif // NODE_LISTENER_H 132