diff options
author | Chris Johns <chrisj@rtems.org> | 2014-09-08 19:29:41 +1000 |
---|---|---|
committer | Chris Johns <chrisj@rtems.org> | 2014-09-08 19:29:41 +1000 |
commit | 2126ea7ff045df25fe6588e8820e02504744549d (patch) | |
tree | c8294b127cee0c8c7e3a8e3c993664a9097e272d | |
parent | 17c836402fe28360d9805eed1584dd0e2dd33db5 (diff) |
rtems-tld: Generate arg and ret code in the wrapper.
-rw-r--r-- | linkers/rtems-tld.cpp | 47 | ||||
-rw-r--r-- | linkers/rtld-base.ini | 23 |
2 files changed, 48 insertions, 22 deletions
diff --git a/linkers/rtems-tld.cpp b/linkers/rtems-tld.cpp index 28f154d..8e3d7c7 100644 --- a/linkers/rtems-tld.cpp +++ b/linkers/rtems-tld.cpp @@ -135,7 +135,6 @@ namespace rld std::string name; /**< The name of this wrapper. */ rld::strings headers; /**< Include statements. */ rld::strings defines; /**< Define statements. */ - std::string map_sym_prefix; /**< Mapping symbol prefix. */ std::string arg_trace; /**< Code template to trace an argument. */ std::string ret_trace; /**< Code template to trace the return value. */ rld::strings code; /**< Code block inserted before the trace code. */ @@ -441,7 +440,6 @@ namespace rld parse (config, section, "defines", "define", defines); parse (config, section, "code-blocks", "code", code, false); - map_sym_prefix = section.get_record_item ("map-sym-prefix"); arg_trace = rld::dequote (section.get_record_item ("arg-trace")); ret_trace = rld::dequote (section.get_record_item ("ret-trace")); } @@ -464,8 +462,7 @@ namespace rld { out << " " << (*di) << std::endl; } - out << " Mapping Symbol Prefix: " << map_sym_prefix << std::endl - << " Arg Trace Code: " << arg_trace << std::endl + out << " Arg Trace Code: " << arg_trace << std::endl << " Return Trace Code: " << ret_trace << std::endl << " Code blocks: " << std::endl; for (rld::strings::const_iterator ci = code.begin (); @@ -646,18 +643,33 @@ namespace rld c.write_line(sig.decl ("__wrap_")); c.write_line("{"); - std::string l; - /* * @todo Need to define as part of the function signature if ret * processing is required. */ - if (sig.ret != "void") - { + bool has_ret = sig.ret != "void"; + + if (has_ret) c.write_line(" " + sig.ret + " ret;"); - l = " ret ="; + + std::string l; + + for (size_t a = 0; a < sig.args.size (); ++a) + { + std::string l = ' ' + generator_.arg_trace; + std::string n = rld::to_string ((int) (a + 1)); + l = rld::find_replace (l, "@ARG_NUM@", n); + l = rld::find_replace (l, "@ARG_TYPE@", '"' + sig.args[0] + '"'); + l = rld::find_replace (l, "@ARG_SIZE@", "sizeof(" + sig.args[0] + ')'); + l = rld::find_replace (l, "@ARG_LABEL@", "a" + n); + c.write_line(l); } + l.clear (); + + if (has_ret) + l = " ret ="; + l += " __real_" + sig.name + '('; for (size_t a = 0; a < sig.args.size (); ++a) { @@ -668,8 +680,13 @@ namespace rld l += ");"; c.write_line(l); - if (sig.ret != "void") + if (has_ret) { + std::string l = ' ' + generator_.ret_trace; + l = rld::find_replace (l, "@RET_TYPE@", '"' + sig.ret + '"'); + l = rld::find_replace (l, "@RET_SIZE@", "sizeof(" + sig.ret + ')'); + l = rld::find_replace (l, "@RET_LABEL@", "ret"); + c.write_line(l); c.write_line(" return ret;"); } @@ -785,15 +802,14 @@ namespace rld if (rld::verbose ()) std::cout << "linking: " << o.name () << std::endl; - std::string wrap = " -Wl,--wrap -Wl,"; + std::string wrap = " -Wl,--wrap="; rld::cc::make_ld_command (args); - args.push_back (o.name ()); - - rld::process::args_append (args, ld_cmd); rld::process::args_append (args, wrap + rld::join (tracer_.get_traces (), wrap)); + args.push_back (o.name ()); + rld::process::args_append (args, ld_cmd); rld::process::tempfile out; rld::process::tempfile err; @@ -807,9 +823,10 @@ namespace rld if ((status.type != rld::process::status::normal) || (status.code != 0)) { - err.output (rld::cc::get_cc (), std::cout); + err.output (rld::cc::get_ld (), std::cout); throw rld::error ("Linker error", "linking"); } + err.output (rld::cc::get_ld (), std::cout); } void diff --git a/linkers/rtld-base.ini b/linkers/rtld-base.ini index 3293ea8..b15f4cd 100644 --- a/linkers/rtld-base.ini +++ b/linkers/rtld-base.ini @@ -14,15 +14,14 @@ generator = printf-generator ; A printf generator prints to stdout the trace functions. ; [printf-generator] -map-sym-prefix = rtld_pg__ headers = printf-generator-headers -arg-trace = "rtld_pg_print_arg(@ARG_NUM@, @ARG_TYPE@, @ARG_SIZE@, &@ARG_LABEL@);" -ret-trace = "rtld_pg_print_ret(@RET_TYPE@, @RETG_SIZE@, &@RET_LABEL@);" +arg-trace = "rtld_pg_print_arg(@ARG_NUM@, @ARG_TYPE@, @ARG_SIZE@, (void*) &@ARG_LABEL@);" +ret-trace = "rtld_pg_print_ret(@RET_TYPE@, @RET_SIZE@, (void*) &@RET_LABEL@);" code = <<<CODE -static inline void rtld_pg_print_arg(int arg_num, - const char* arg_type, - int arg_size, - void* arg) +static inline void rtld_pg_print_arg(int arg_num, + const char* arg_type, + int arg_size, + void* arg) { const char* p = arg; int i; @@ -30,6 +29,16 @@ static inline void rtld_pg_print_arg(int arg_num, for (i = 0; i < arg_size; ++i, ++p) printf ("%02x", (unsigned int) *p); printf ("\n"); } +static inline void rtld_pg_print_ret(const char* ret_type, + int ret_size, + void* ret) +{ + const char* p = ret; + int i; + printf (" rt] %s(%d) = ", ret_type, ret_size); + for (i = 0; i < ret_size; ++i, ++p) printf ("%02x", (unsigned int) *p); + printf ("\n"); +} CODE [printf-generator-headers] |