Easier API for creating global variable (#3655)
This commit is contained in:
parent
3599ba226f
commit
8e41d975bf
3 changed files with 58 additions and 9 deletions
|
|
@ -9,7 +9,6 @@
|
|||
*
|
||||
* \param name variable name
|
||||
* \param addr variable address
|
||||
* \param comment variable comment
|
||||
* \return RzAnalysisVarGlobal *
|
||||
*/
|
||||
RZ_API RZ_OWN RzAnalysisVarGlobal *rz_analysis_var_global_new(RZ_NONNULL const char *name, ut64 addr) {
|
||||
|
|
@ -25,7 +24,7 @@ RZ_API RZ_OWN RzAnalysisVarGlobal *rz_analysis_var_global_new(RZ_NONNULL const c
|
|||
return glob;
|
||||
}
|
||||
|
||||
int global_var_node_cmp(const void *incoming, const RBNode *in_tree, void *user) {
|
||||
static int global_var_node_cmp(const void *incoming, const RBNode *in_tree, void *user) {
|
||||
ut64 ia = *(ut64 *)incoming;
|
||||
ut64 ta = container_of(in_tree, const RzAnalysisVarGlobal, rb)->addr;
|
||||
if (ia < ta) {
|
||||
|
|
@ -36,6 +35,15 @@ int global_var_node_cmp(const void *incoming, const RBNode *in_tree, void *user)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static void global_var_set_type(RzAnalysisVarGlobal *glob, RzType *type) {
|
||||
glob->type = type;
|
||||
|
||||
RzFlagItem *flag = rz_analysis_var_global_get_flag_item(glob);
|
||||
if (flag) {
|
||||
flag->size = rz_type_db_get_bitsize(glob->analysis->typedb, glob->type) / 8;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Add the global variable into hashtable
|
||||
*
|
||||
|
|
@ -43,7 +51,7 @@ int global_var_node_cmp(const void *incoming, const RBNode *in_tree, void *user)
|
|||
* \param global_var Global variable instance
|
||||
* \return true if succeed
|
||||
*/
|
||||
RZ_API RZ_OWN bool rz_analysis_var_global_add(RzAnalysis *analysis, RZ_NONNULL RzAnalysisVarGlobal *global_var) {
|
||||
RZ_API bool rz_analysis_var_global_add(RzAnalysis *analysis, RZ_NONNULL RzAnalysisVarGlobal *global_var) {
|
||||
rz_return_val_if_fail(analysis && global_var, false);
|
||||
|
||||
RzAnalysisVarGlobal *existing_glob = NULL;
|
||||
|
|
@ -70,6 +78,33 @@ RZ_API RZ_OWN bool rz_analysis_var_global_add(RzAnalysis *analysis, RZ_NONNULL R
|
|||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Create the global variable and add into hashtable
|
||||
*
|
||||
* \param analysis RzAnalysis
|
||||
* \param name Global variable name
|
||||
* \param type Global variable type
|
||||
* \param addr Global variable address
|
||||
* \return true if succeed
|
||||
*/
|
||||
RZ_API bool rz_analysis_var_global_create(RzAnalysis *analysis, RZ_NONNULL const char *name, RZ_NONNULL RZ_BORROW RzType *type, ut64 addr) {
|
||||
rz_return_val_if_fail(analysis && name && type, false);
|
||||
|
||||
RzAnalysisVarGlobal *glob = rz_analysis_var_global_new(name, addr);
|
||||
if (!glob) {
|
||||
return false;
|
||||
}
|
||||
|
||||
global_var_set_type(glob, type);
|
||||
|
||||
if (!rz_analysis_var_global_add(analysis, glob)) {
|
||||
rz_analysis_var_global_free(glob);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Free the global variable instance
|
||||
*
|
||||
|
|
@ -302,12 +337,8 @@ RZ_API bool rz_analysis_var_global_rename(RzAnalysis *analysis, RZ_NONNULL const
|
|||
RZ_API void rz_analysis_var_global_set_type(RzAnalysisVarGlobal *glob, RZ_NONNULL RZ_BORROW RzType *type) {
|
||||
rz_return_if_fail(glob && type);
|
||||
rz_type_free(glob->type);
|
||||
glob->type = type;
|
||||
|
||||
RzFlagItem *flag = rz_analysis_var_global_get_flag_item(glob);
|
||||
if (flag) {
|
||||
flag->size = rz_type_db_get_bitsize(glob->analysis->typedb, glob->type) / 8;
|
||||
}
|
||||
global_var_set_type(glob, type);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -1708,7 +1708,8 @@ RZ_API void rz_analysis_fcn_vars_add_types(RzAnalysis *analysis, RZ_NONNULL RzAn
|
|||
|
||||
// Global vars
|
||||
RZ_API RZ_OWN RzAnalysisVarGlobal *rz_analysis_var_global_new(RZ_NONNULL const char *name, ut64 addr);
|
||||
RZ_API RZ_OWN bool rz_analysis_var_global_add(RzAnalysis *analysis, RZ_NONNULL RzAnalysisVarGlobal *global_var);
|
||||
RZ_API bool rz_analysis_var_global_add(RzAnalysis *analysis, RZ_NONNULL RzAnalysisVarGlobal *global_var);
|
||||
RZ_API bool rz_analysis_var_global_create(RzAnalysis *analysis, RZ_NONNULL const char *name, RZ_NONNULL RZ_BORROW RzType *type, ut64 addr);
|
||||
RZ_API void rz_analysis_var_global_free(RzAnalysisVarGlobal *glob);
|
||||
RZ_API RZ_NULLABLE RzFlagItem *rz_analysis_var_global_get_flag_item(RzAnalysisVarGlobal *glob);
|
||||
RZ_API bool rz_analysis_var_global_delete(RZ_NONNULL RzAnalysis *analysis, RZ_NONNULL RzAnalysisVarGlobal *glob);
|
||||
|
|
|
|||
|
|
@ -132,6 +132,23 @@ bool test_rz_analysis_global_var() {
|
|||
glob = rz_analysis_var_global_get_byname(analysis, "bar");
|
||||
mu_assert_null(glob, "get deleted global var");
|
||||
|
||||
// create global
|
||||
typ = rz_type_parse_string_single(parser, "int", &errmsg);
|
||||
mu_assert_notnull(typ, "parsed type");
|
||||
mu_assert_true(rz_analysis_var_global_create(analysis, "crab", typ, 0x125418),
|
||||
"create global var");
|
||||
|
||||
glob = rz_analysis_var_global_get_byname(analysis, "crab");
|
||||
mu_assert_notnull(glob, "create a global variable");
|
||||
mu_assert_streq(glob->name, "crab", "global var name");
|
||||
mu_assert_eq(glob->addr, 0x125418, "global var address");
|
||||
mu_assert_streq(glob->type->identifier.name, "int", "global var type");
|
||||
|
||||
flag = rz_analysis_var_global_get_flag_item(glob);
|
||||
mu_assert_notnull(flag, "global var flag_item");
|
||||
mu_assert_eq(flag->offset, glob->addr, "flag item addr");
|
||||
mu_assert_streq(flag->name, "crab", "flag item name");
|
||||
|
||||
rz_type_parser_free(parser);
|
||||
rz_core_free(core);
|
||||
mu_end;
|
||||
|
|
|
|||
Loading…
Reference in a new issue