| 260 | } |
| 261 | |
| 262 | EventHookError EventManager::UnhookEvent(const char *name, IPluginFunction *pFunction, EventHookMode mode) |
| 263 | { |
| 264 | EventHook *pHook; |
| 265 | IChangeableForward **pEventForward; |
| 266 | |
| 267 | /* If hook does not exist at all */ |
| 268 | if (!m_EventHooks.retrieve(name, &pHook)) |
| 269 | { |
| 270 | return EventHookErr_NotActive; |
| 271 | } |
| 272 | |
| 273 | /* One forward to rule them all */ |
| 274 | if (mode == EventHookMode_Pre) |
| 275 | { |
| 276 | pEventForward = &pHook->pPreHook; |
| 277 | } else { |
| 278 | pEventForward = &pHook->pPostHook; |
| 279 | } |
| 280 | |
| 281 | /* Remove function from forward's list */ |
| 282 | if (*pEventForward == NULL || !(*pEventForward)->RemoveFunction(pFunction)) |
| 283 | { |
| 284 | return EventHookErr_InvalidCallback; |
| 285 | } |
| 286 | |
| 287 | /* If forward's list contains 0 functions now, free it */ |
| 288 | if ((*pEventForward)->GetFunctionCount() == 0) |
| 289 | { |
| 290 | forwardsys->ReleaseForward(*pEventForward); |
| 291 | *pEventForward = NULL; |
| 292 | } |
| 293 | |
| 294 | /* Decrement reference count */ |
| 295 | if (--pHook->refCount == 0) |
| 296 | { |
| 297 | /* If reference count is now 0, free hook structure */ |
| 298 | |
| 299 | EventHookList *pHookList; |
| 300 | IPlugin *plugin = scripts->FindPluginByContext(pFunction->GetParentContext()); |
| 301 | |
| 302 | /* Get plugin's event hook list */ |
| 303 | if (!plugin->GetProperty("EventHooks", (void**)&pHookList)) |
| 304 | { |
| 305 | return EventHookErr_NotActive; |
| 306 | } |
| 307 | |
| 308 | /* Make sure the event was actually being hooked */ |
| 309 | if (pHookList->find(pHook) == pHookList->end()) |
| 310 | { |
| 311 | return EventHookErr_NotActive; |
| 312 | } |
| 313 | |
| 314 | /* Remove current structure from plugin's list */ |
| 315 | pHookList->remove(pHook); |
| 316 | |
| 317 | /* Delete entry in trie */ |
| 318 | m_EventHooks.remove(name); |
| 319 |
no test coverage detected