hookmgr.h 7.1 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68
/*
 * Copyright (c) 2021 Huawei Device Co., Ltd.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#ifndef OHOS_HOOK_MANAGER_H__
#define OHOS_HOOK_MANAGER_H__

#ifdef __cplusplus
#if __cplusplus
extern "C" {
#endif
#endif

/**
 * @brief A Hook is a means of executing custom code (function) for existing running code.
 *
 * For a running process, it may consists of several stages.
 * HookManager can help to add hooks to different stages with different priorities.
 * The relationships for HookManager, HookStage and HookItem are shown as below:
 * 
 * | ̄ ̄ ̄ ̄ ̄ ̄|
 * |  HookMgr |
 * |__________|
 *      |
 *      |    |▔▔▔▔▔▔▔▔▔▔▔|    |▔▔▔▔▔▔▔▔▔▔▔| 
 *      └--->| HookStage |--->| HookStage | ...
 *           |___________|    |___________|
 *               |
 *               |    |▔▔▔▔▔▔▔▔▔▔|    |▔▔▔▔▔▔▔▔▔▔| 
 *               └--->| HookItem |--->| HookItem | ...
 *                    |__________|    |__________|
 *
 * Usage example:
 * 
 * For an existing module with several stages as below:
 *      ExistingStage1(...);
 *      ExistingStage2(...);
 *      ExistingStage3(...);
 * We can add hooks capability to it as below:
 *      HookMgrExecute(hookMgr, PRE_STAGE1, ...);
 *      ExistingStage1(...);
 *      HookMgrExecute(hookMgr, PRE_STAGE2, ...);
 *      ExistingStage2(...);
 *      HookMgrExecute(hookMgr, PRE_STAGE3, ...);
 *      ExistingStage3(...);
 *      HookMgrExecute(hookMgr, POST_STAGE3, ...);
 * 
 * For extending modules, we can add hooks without changing the existing module as below:
 *      int sampleHook() {
 *          ...
 *      }
 *      HookMgrAdd(hookMgr, PRE_STAGE1, priority, sampleHook);
 */

/* Forward declaration for HookManager */
typedef struct tagHOOK_MGR HOOK_MGR;

69 70 71
/* Forward declaration for HOOK_INFO */
typedef struct tagHOOK_INFO HOOK_INFO;

72 73 74
/**
 * @brief Hook function prototype
 *
75 76
 * @param hookInfo hook information
 * @param executionContext input arguments for running the hook execution context
77 78
 * @return return 0 if succeed; other values if failed.
 */
79 80 81 82 83 84 85 86
typedef int (*OhosHook)(const HOOK_INFO *hookInfo, void *executionContext);

struct tagHOOK_INFO {
    int stage;          /* hook stage */
    int prio;           /* hook priority */
    OhosHook hook;      /* hook function */
    void *hookCookie;   /* hook function cookie, for current hook only */
};
87 88 89 90 91 92 93 94 95 96 97 98 99

/**
 * @brief Add a hook function
 *
 * @param hookMgr HookManager handle.
 *                If hookMgr is NULL, it will use default HookManager
 * @param stage hook stage
 * @param prio hook priority
 * @param hook hook function pointer
 * @return return 0 if succeed; other values if failed.
 */
int HookMgrAdd(HOOK_MGR *hookMgr, int stage, int prio, OhosHook hook);

100 101 102 103 104 105 106 107 108 109
/**
 * @brief Add a hook function with full hook information
 *
 * @param hookMgr HookManager handle.
 *                If hookMgr is NULL, it will use default HookManager
 * @param hookInfo full hook information
 * @return return 0 if succeed; other values if failed.
 */
int HookMgrAddEx(HOOK_MGR *hookMgr, const HOOK_INFO *hookInfo);

110 111 112 113 114 115 116 117 118 119 120 121 122
/**
 * @brief Delete hook function
 *
 * @param hookMgr HookManager handle.
 *                If hookMgr is NULL, it will use default HookManager
 * @param stage hook stage
 * @param hook hook function pointer
 *                If hook is NULL, it will delete all hooks in the stage
 * @return None
 */
void HookMgrDel(HOOK_MGR *hookMgr, int stage, OhosHook hook);

/**
123 124 125 126 127
 * @brief preHook function prototype for HookMgrExecute each hook
 *
 * @param hookInfo HOOK_INFO for the each hook.
 * @param executionContext input arguments for running the hook execution context.
 * @return None
128
 */
129
typedef void (*OhosHookPreExecution)(const HOOK_INFO *hookInfo, void *executionContext);
130 131

/**
132
 * @brief postHook function prototype for HookMgrExecute each hook
133
 *
134 135 136
 * @param hookInfo HOOK_INFO for the each hook.
 * @param executionContext input arguments for running the hook execution context.
 * @param executionRetVal return value for running the hook.
137 138
 * @return None
 */
139
typedef void (*OhosHookPostExecution)(const HOOK_INFO *hookInfo, void *executionContext, int executionRetVal);
140 141 142 143 144 145 146 147 148

/* Executing hooks in descending priority order */
#define HOOK_EXEC_REVERSE_ORDER     0x01
/* Stop executing hooks when error returned for each hook */
#define HOOK_EXEC_EXIT_WHEN_ERROR   0x02

/**
 * @brief Extra execution arguments for HookMgrExecute
 */
149
typedef struct tagHOOK_EXEC_OPTIONS {
150 151 152
    /* Executing flags */
    int flags;
    /* preHook for before executing each hook */
153
    OhosHookPreExecution preHook;
154
    /* postHook for before executing each hook */
155 156
    OhosHookPostExecution postHook;
} HOOK_EXEC_OPTIONS;
157 158 159 160 161 162 163 164 165 166

/**
 * @brief Executing each hooks in specified stages
 *
 * @param hookMgr HookManager handle.
 *                If hookMgr is NULL, it will use default HookManager
 * @param stage hook stage
 * @param extraArgs HOOK_EXEC_ARGS for executing each hook.
 * @return return 0 if succeed; other values if failed.
 */
167
int HookMgrExecute(HOOK_MGR *hookMgr, int stage, void *executionContext, const HOOK_EXEC_OPTIONS *extraArgs);
168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191

/**
 * @brief Create a HookManager handle
 *
 * @param name HookManager name.
 * @return return HookManager handle; NULL if failed.
 */
HOOK_MGR *HookMgrCreate(const char *name);

/**
 * @brief Destroy HookManager
 *
 * @param hookMgr HookManager handle.
 *                If hookMgr is NULL, it will use default HookManager
 * @return None.
 */
void HookMgrDestroy(HOOK_MGR *hookMgr);

/**
 * @brief Hook traversal function prototype
 *
 * @param hookInfo HOOK_INFO for traversing each hook.
 * @return None
 */
192
typedef void (*OhosHookTraversal)(const HOOK_INFO *hookInfo, void *traversalCookie);
193 194 195 196 197 198

/**
 * @brief Traversing all hooks in the HookManager
 *
 * @param hookMgr HookManager handle.
 *                If hookMgr is NULL, it will use default HookManager
199
 * @param traversalCookie traversal cookie.
200 201 202
 * @param traversal traversal function.
 * @return None.
 */
203
void HookMgrTraversal(HOOK_MGR *hookMgr, void *traversalCookie, OhosHookTraversal traversal);
204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229

/**
 * @brief Get number of hooks in specified stage
 *
 * @param hookMgr HookManager handle.
 *                If hookMgr is NULL, it will use default HookManager
 * @param stage hook stage.
 * @return number of hooks, return 0 if none
 */
int HookMgrGetHooksCnt(HOOK_MGR *hookMgr, int stage);

/**
 * @brief Get number of stages in the HookManager
 *
 * @param hookMgr HookManager handle.
 *                If hookMgr is NULL, it will use default HookManager
 * @return number of stages, return 0 if none
 */
int HookMgrGetStagesCnt(HOOK_MGR *hookMgr);

#ifdef __cplusplus
#if __cplusplus
}
#endif
#endif
#endif