diff options
Diffstat (limited to 'src/plugins/ruby/weechat-ruby.c')
-rw-r--r-- | src/plugins/ruby/weechat-ruby.c | 562 |
1 files changed, 393 insertions, 169 deletions
diff --git a/src/plugins/ruby/weechat-ruby.c b/src/plugins/ruby/weechat-ruby.c index 09462cd56..09aa122d5 100644 --- a/src/plugins/ruby/weechat-ruby.c +++ b/src/plugins/ruby/weechat-ruby.c @@ -1,7 +1,7 @@ /* * weechat-ruby.c - ruby plugin for WeeChat * - * Copyright (C) 2003-2017 Sébastien Helleu <flashcode@flashtux.org> + * Copyright (C) 2003-2018 Sébastien Helleu <flashcode@flashtux.org> * Copyright (C) 2005-2007 Emmanuel Bouthenot <kolter@openics.org> * * This file is part of WeeChat, the extensible chat client. @@ -61,18 +61,43 @@ WEECHAT_PLUGIN_DESCRIPTION(N_("Support of ruby scripts")); WEECHAT_PLUGIN_AUTHOR("Sébastien Helleu <flashcode@flashtux.org>"); WEECHAT_PLUGIN_VERSION(WEECHAT_VERSION); WEECHAT_PLUGIN_LICENSE(WEECHAT_LICENSE); -WEECHAT_PLUGIN_PRIORITY(3000); +WEECHAT_PLUGIN_PRIORITY(4000); struct t_weechat_plugin *weechat_ruby_plugin = NULL; +struct t_plugin_script_data ruby_data; + +struct t_config_file *ruby_config_file = NULL; +struct t_config_option *ruby_config_look_check_license = NULL; +struct t_config_option *ruby_config_look_eval_keep_context = NULL; + int ruby_quiet = 0; int ruby_hide_errors = 0; + +struct t_plugin_script *ruby_script_eval = NULL; +int ruby_eval_mode = 0; +int ruby_eval_send_input = 0; +int ruby_eval_exec_commands = 0; +struct t_gui_buffer *ruby_eval_buffer = NULL; +char *ruby_eval_output = NULL; +#define RUBY_EVAL_SCRIPT \ + "def weechat_init\n" \ + " Weechat.register('" WEECHAT_SCRIPT_EVAL_NAME "', '', '1.0', " \ + "'" WEECHAT_LICENSE "', 'Evaluation of source code', '', '')\n" \ + " return Weechat::WEECHAT_RC_OK\n" \ + "end\n" \ + "\n" \ + "def script_ruby_eval(code)\n" \ + " module_eval(code)\n" \ + "end\n" + struct t_plugin_script *ruby_scripts = NULL; struct t_plugin_script *last_ruby_script = NULL; struct t_plugin_script *ruby_current_script = NULL; struct t_plugin_script *ruby_registered_script = NULL; const char *ruby_current_script_filename = NULL; VALUE ruby_current_module; +char **ruby_buffer_output = NULL; /* * string used to execute action "install": @@ -103,8 +128,6 @@ VALUE ruby_mWeechat, ruby_mWeechatOutputs; #define MOD_NAME_PREFIX "WeechatRubyModule" int ruby_num = 0; -char ruby_buffer_output[128]; - typedef struct protect_call_arg { VALUE recv; ID mid; @@ -169,16 +192,16 @@ weechat_ruby_hash_foreach_cb (VALUE key, VALUE value, void *arg) type_values = weechat_hashtable_get_string (hashtable, "type_values"); if (strcmp (type_values, WEECHAT_HASHTABLE_STRING) == 0) { - weechat_hashtable_set (hashtable, StringValuePtr(key), - StringValuePtr(value)); + weechat_hashtable_set (hashtable, StringValuePtr (key), + StringValuePtr (value)); } else if (strcmp (type_values, WEECHAT_HASHTABLE_POINTER) == 0) { - weechat_hashtable_set (hashtable, StringValuePtr(key), + weechat_hashtable_set (hashtable, StringValuePtr (key), plugin_script_str2ptr ( weechat_ruby_plugin, NULL, NULL, - StringValuePtr(value))); + StringValuePtr (value))); } } @@ -252,30 +275,30 @@ weechat_ruby_print_exception (VALUE err) char* err_msg; char* err_class; - backtrace = rb_protect_funcall (err, rb_intern("backtrace"), + backtrace = rb_protect_funcall (err, rb_intern ("backtrace"), &ruby_error, 0, NULL); - tmp1 = rb_protect_funcall(err, rb_intern("message"), &ruby_error, 0, NULL); - err_msg = StringValueCStr(tmp1); + tmp1 = rb_protect_funcall(err, rb_intern ("message"), &ruby_error, 0, NULL); + err_msg = StringValueCStr (tmp1); - tmp2 = rb_protect_funcall(rb_protect_funcall(err, rb_intern("class"), - &ruby_error, 0, NULL), - rb_intern("name"), &ruby_error, 0, NULL); - err_class = StringValuePtr(tmp2); + tmp2 = rb_protect_funcall (rb_protect_funcall (err, rb_intern ("class"), + &ruby_error, 0, NULL), + rb_intern ("name"), &ruby_error, 0, NULL); + err_class = StringValuePtr (tmp2); if (strcmp (err_class, "SyntaxError") == 0) { - tmp3 = rb_inspect(err); + tmp3 = rb_inspect (err); weechat_printf (NULL, weechat_gettext ("%s%s: error: %s"), weechat_prefix ("error"), RUBY_PLUGIN_NAME, - StringValuePtr(tmp3)); + StringValuePtr (tmp3)); } else { for (i = 0; i < RARRAY_LEN(backtrace); i++) { - line = StringValuePtr(RARRAY_PTR(backtrace)[i]); + line = StringValuePtr (RARRAY_PTR(backtrace)[i]); cline = NULL; if (i == 0) { @@ -294,8 +317,8 @@ weechat_ruby_print_exception (VALUE err) } else { - cline = (char *)calloc(strlen (line) + strlen (" from ") + 1, - sizeof (char)); + cline = (char *)calloc (strlen (line) + strlen (" from ") + 1, + sizeof (char)); if (cline) { strcat (cline, " from "); @@ -319,6 +342,117 @@ weechat_ruby_print_exception (VALUE err) } /* + * Function used for compatibility. + */ + +static VALUE +weechat_ruby_output_flush_ruby (VALUE self) +{ + /* make C compiler happy */ + (void) self; + + return Qnil; +} + +/* + * Flushes output. + */ + +void +weechat_ruby_output_flush () +{ + const char *ptr_command; + char *command; + int length; + + if (!*ruby_buffer_output[0]) + return; + + if (ruby_eval_mode) + { + /* if there's no buffer, we catch the output, so there's no flush */ + if (!ruby_eval_buffer) + return; + + if (ruby_eval_send_input) + { + if (ruby_eval_exec_commands) + ptr_command = *ruby_buffer_output; + else + ptr_command = weechat_string_input_for_buffer (*ruby_buffer_output); + if (ptr_command) + { + weechat_command (ruby_eval_buffer, *ruby_buffer_output); + } + else + { + length = 1 + strlen (*ruby_buffer_output) + 1; + command = malloc (length); + if (command) + { + snprintf (command, length, "%c%s", + *ruby_buffer_output[0], *ruby_buffer_output); + weechat_command (ruby_eval_buffer, + (command[0]) ? command : " "); + free (command); + } + } + } + else + { + weechat_printf (ruby_eval_buffer, "%s", *ruby_buffer_output); + } + } + else + { + /* script (no eval mode) */ + weechat_printf ( + NULL, + weechat_gettext ("%s: stdout/stderr (%s): %s"), + RUBY_PLUGIN_NAME, + (ruby_current_script) ? ruby_current_script->name : "?", + *ruby_buffer_output); + } + + weechat_string_dyn_copy (ruby_buffer_output, NULL); +} + +/* + * Redirection for stdout and stderr. + */ + +static VALUE +weechat_ruby_output (VALUE self, VALUE str) +{ + char *msg, *m, *p; + + /* make C compiler happy */ + (void) self; + + if (ruby_hide_errors) + return Qnil; + + msg = strdup (StringValuePtr (str)); + + m = msg; + while ((p = strchr (m, '\n')) != NULL) + { + *p = '\0'; + weechat_string_dyn_concat (ruby_buffer_output, m); + weechat_ruby_output_flush (); + *p = '\n'; + m = ++p; + } + + weechat_string_dyn_concat (ruby_buffer_output, m); + + if (msg) + free (msg); + + return Qnil; +} + +/* * Executes a ruby function. */ @@ -333,6 +467,8 @@ weechat_ruby_exec (struct t_plugin_script *script, void *ret_value; struct t_plugin_script *old_ruby_current_script; + ret_value = NULL; + old_ruby_current_script = ruby_current_script; ruby_current_script = script; @@ -360,24 +496,26 @@ weechat_ruby_exec (struct t_plugin_script *script, if (argc > 0) { rc = rb_protect_funcall ((VALUE) script->interpreter, - rb_intern(function), + rb_intern (function), &ruby_error, argc, argv2); } else { rc = rb_protect_funcall ((VALUE) script->interpreter, - rb_intern(function), + rb_intern (function), &ruby_error, 0, NULL); } + weechat_ruby_output_flush (); + if (ruby_error) { weechat_printf (NULL, weechat_gettext ("%s%s: unable to run function \"%s\""), weechat_prefix ("error"), RUBY_PLUGIN_NAME, function); - err = rb_gv_get("$!"); - weechat_ruby_print_exception(err); + err = rb_gv_get ("$!"); + weechat_ruby_print_exception (err); return NULL; } @@ -389,6 +527,19 @@ weechat_ruby_exec (struct t_plugin_script *script, else ret_value = NULL; } + else if ((TYPE(rc) == T_STRING) && (ret_type == WEECHAT_SCRIPT_EXEC_POINTER)) + { + if (StringValuePtr (rc)) + { + ret_value = plugin_script_str2ptr (weechat_ruby_plugin, + script->name, function, + StringValuePtr (rc)); + } + else + { + ret_value = NULL; + } + } else if ((TYPE(rc) == T_FIXNUM) && (ret_type == WEECHAT_SCRIPT_EXEC_INT)) { ret_i = malloc (sizeof (*ret_i)); @@ -405,114 +556,55 @@ weechat_ruby_exec (struct t_plugin_script *script, } else { - weechat_printf (NULL, - weechat_gettext ("%s%s: function \"%s\" must return a " - "valid value"), - weechat_prefix ("error"), RUBY_PLUGIN_NAME, function); - ruby_current_script = old_ruby_current_script; - return WEECHAT_RC_OK; - } - - if (ret_value == NULL) - { - weechat_printf (NULL, - weechat_gettext ("%s%s: not enough memory in function " - "\"%s\""), - weechat_prefix ("error"), RUBY_PLUGIN_NAME, function); - ruby_current_script = old_ruby_current_script; - return NULL; - } - - ruby_current_script = old_ruby_current_script; - - return ret_value; -} - -/* - * Redirection for stdout and stderr. - */ - -static VALUE -weechat_ruby_output (VALUE self, VALUE str) -{ - char *msg, *p, *m; - - /* make C compiler happy */ - (void) self; - - if (ruby_hide_errors) - return Qnil; - - msg = strdup(StringValuePtr(str)); - - m = msg; - while ((p = strchr (m, '\n')) != NULL) - { - *p = '\0'; - if (strlen (m) + strlen (ruby_buffer_output) > 0) + if (ret_type != WEECHAT_SCRIPT_EXEC_IGNORE) { weechat_printf (NULL, - weechat_gettext ("%s%s: stdout/stderr: %s%s"), + weechat_gettext ("%s%s: function \"%s\" must " + "return a valid value"), weechat_prefix ("error"), RUBY_PLUGIN_NAME, - ruby_buffer_output, m); + function); } - *p = '\n'; - ruby_buffer_output[0] = '\0'; - m = ++p; } - if (strlen(m) + strlen(ruby_buffer_output) > sizeof(ruby_buffer_output)) + if ((ret_type != WEECHAT_SCRIPT_EXEC_IGNORE) && !ret_value) { weechat_printf (NULL, - weechat_gettext ("%s%s: stdout/stderr: %s%s"), - weechat_prefix ("error"), RUBY_PLUGIN_NAME, - ruby_buffer_output, m); - ruby_buffer_output[0] = '\0'; + weechat_gettext ("%s%s: error in function \"%s\""), + weechat_prefix ("error"), RUBY_PLUGIN_NAME, function); } - else - strcat (ruby_buffer_output, m); - - if (msg) - free (msg); - - return Qnil; -} - -/* - * Function used for compatibility. - */ -static VALUE -weechat_ruby_output_flush (VALUE self) -{ - /* make C compiler happy */ - (void) self; + ruby_current_script = old_ruby_current_script; - return Qnil; + return ret_value; } /* * Loads a ruby script. * - * Returns: - * 1: OK - * 0: error + * If code is NULL, the content of filename is read and executed. + * If code is not NULL, it is executed (the file is not read). + * + * Returns pointer to new registered script, NULL if error. */ -int -weechat_ruby_load (const char *filename) +struct t_plugin_script * +weechat_ruby_load (const char *filename, const char *code) { char modname[64]; - VALUE ruby_retcode, err, argv[1]; + VALUE ruby_retcode, err, argv[2]; int ruby_error; struct stat buf; - if (stat (filename, &buf) != 0) + if (!code) { - weechat_printf (NULL, - weechat_gettext ("%s%s: script \"%s\" not found"), - weechat_prefix ("error"), RUBY_PLUGIN_NAME, filename); - return 0; + if (stat (filename, &buf) != 0) + { + weechat_printf (NULL, + weechat_gettext ("%s%s: script \"%s\" not found"), + weechat_prefix ("error"), RUBY_PLUGIN_NAME, + filename); + return NULL; + } } if ((weechat_ruby_plugin->debug >= 2) || !ruby_quiet) @@ -525,7 +617,7 @@ weechat_ruby_load (const char *filename) ruby_current_script = NULL; ruby_registered_script = NULL; - snprintf (modname, sizeof(modname), "%s%d", MOD_NAME_PREFIX, ruby_num); + snprintf (modname, sizeof (modname), "%s%d", MOD_NAME_PREFIX, ruby_num); ruby_num++; ruby_current_module = rb_define_module (modname); @@ -533,15 +625,16 @@ weechat_ruby_load (const char *filename) ruby_current_script_filename = filename; argv[0] = rb_str_new2 (filename); + argv[1] = rb_str_new2 ((code) ? code : ""); ruby_retcode = rb_protect_funcall (ruby_current_module, rb_intern ("load_eval_file"), - &ruby_error, 1, argv); + &ruby_error, 2, argv); if (ruby_retcode == Qnil) { - err = rb_gv_get("$!"); - weechat_ruby_print_exception(err); - return 0; + err = rb_gv_get ("$!"); + weechat_ruby_print_exception (err); + return NULL; } if (NUM2INT(ruby_retcode) != 0) @@ -578,7 +671,7 @@ weechat_ruby_load (const char *filename) "@load_eval_file_error")); } - return 0; + return NULL; } (void) rb_protect_funcall (ruby_current_module, rb_intern ("weechat_init"), @@ -591,8 +684,8 @@ weechat_ruby_load (const char *filename) "\"weechat_init\" in file \"%s\""), weechat_prefix ("error"), RUBY_PLUGIN_NAME, filename); - err = rb_gv_get("$!"); - weechat_ruby_print_exception(err); + err = rb_gv_get ("$!"); + weechat_ruby_print_exception (err); if (ruby_current_script) { @@ -602,7 +695,7 @@ weechat_ruby_load (const char *filename) ruby_current_script = NULL; } - return 0; + return NULL; } if (!ruby_registered_script) @@ -611,7 +704,7 @@ weechat_ruby_load (const char *filename) weechat_gettext ("%s%s: function \"register\" not " "found (or failed) in file \"%s\""), weechat_prefix ("error"), RUBY_PLUGIN_NAME, filename); - return 0; + return NULL; } ruby_current_script = ruby_registered_script; @@ -631,7 +724,7 @@ weechat_ruby_load (const char *filename) WEECHAT_HOOK_SIGNAL_STRING, ruby_current_script->filename); - return 1; + return ruby_current_script; } /* @@ -644,7 +737,7 @@ weechat_ruby_load_cb (void *data, const char *filename) /* make C compiler happy */ (void) data; - weechat_ruby_load (filename); + weechat_ruby_load (filename, NULL); } /* @@ -745,7 +838,7 @@ weechat_ruby_reload_name (const char *name) weechat_gettext ("%s: script \"%s\" unloaded"), RUBY_PLUGIN_NAME, name); } - weechat_ruby_load (filename); + weechat_ruby_load (filename, NULL); free (filename); } } @@ -771,6 +864,65 @@ weechat_ruby_unload_all () } /* + * Evaluates ruby source code. + * + * Returns: + * 1: OK + * 0: error + */ + +int +weechat_ruby_eval (struct t_gui_buffer *buffer, int send_to_buffer_as_input, + int exec_commands, const char *code) +{ + void *func_argv[1], *result; + char empty_arg[1] = { '\0' }; + + if (!ruby_script_eval) + { + ruby_quiet = 1; + ruby_script_eval = weechat_ruby_load (WEECHAT_SCRIPT_EVAL_NAME, + RUBY_EVAL_SCRIPT); + ruby_quiet = 0; + if (!ruby_script_eval) + return 0; + } + + weechat_ruby_output_flush (); + + ruby_eval_mode = 1; + ruby_eval_send_input = send_to_buffer_as_input; + ruby_eval_exec_commands = exec_commands; + ruby_eval_buffer = buffer; + + func_argv[0] = (code) ? (char *)code : empty_arg; + result = weechat_ruby_exec (ruby_script_eval, + WEECHAT_SCRIPT_EXEC_IGNORE, + "script_ruby_eval", + "s", func_argv); + /* result is ignored */ + if (result) + free (result); + + weechat_ruby_output_flush (); + + ruby_eval_mode = 0; + ruby_eval_send_input = 0; + ruby_eval_exec_commands = 0; + ruby_eval_buffer = NULL; + + if (!weechat_config_boolean (ruby_config_look_eval_keep_context)) + { + ruby_quiet = 1; + weechat_ruby_unload (ruby_script_eval); + ruby_quiet = 0; + ruby_script_eval = NULL; + } + + return 1; +} + +/* * Callback for command "/ruby". */ @@ -779,12 +931,12 @@ weechat_ruby_command_cb (const void *pointer, void *data, struct t_gui_buffer *buffer, int argc, char **argv, char **argv_eol) { - char *ptr_name, *path_script; + char *ptr_name, *ptr_code, *path_script; + int i, send_to_buffer_as_input, exec_commands; /* make C compiler happy */ (void) pointer; (void) data; - (void) buffer; if (argc == 1) { @@ -816,6 +968,10 @@ weechat_ruby_command_cb (const void *pointer, void *data, { weechat_ruby_unload_all (); } + else if (weechat_strcasecmp (argv[1], "version") == 0) + { + plugin_script_display_interpreter (weechat_ruby_plugin, 0); + } else WEECHAT_COMMAND_ERROR; } @@ -850,7 +1006,8 @@ weechat_ruby_command_cb (const void *pointer, void *data, /* load ruby script */ path_script = plugin_script_search_path (weechat_ruby_plugin, ptr_name); - weechat_ruby_load ((path_script) ? path_script : ptr_name); + weechat_ruby_load ((path_script) ? path_script : ptr_name, + NULL); if (path_script) free (path_script); } @@ -866,6 +1023,39 @@ weechat_ruby_command_cb (const void *pointer, void *data, } ruby_quiet = 0; } + else if (weechat_strcasecmp (argv[1], "eval") == 0) + { + send_to_buffer_as_input = 0; + exec_commands = 0; + ptr_code = argv_eol[2]; + for (i = 2; i < argc; i++) + { + if (argv[i][0] == '-') + { + if (strcmp (argv[i], "-o") == 0) + { + if (i + 1 >= argc) + WEECHAT_COMMAND_ERROR; + send_to_buffer_as_input = 1; + exec_commands = 0; + ptr_code = argv_eol[i + 1]; + } + else if (strcmp (argv[i], "-oc") == 0) + { + if (i + 1 >= argc) + WEECHAT_COMMAND_ERROR; + send_to_buffer_as_input = 1; + exec_commands = 1; + ptr_code = argv_eol[i + 1]; + } + } + else + break; + } + if (!weechat_ruby_eval (buffer, send_to_buffer_as_input, + exec_commands, ptr_code)) + WEECHAT_COMMAND_ERROR; + } else WEECHAT_COMMAND_ERROR; } @@ -912,6 +1102,29 @@ weechat_ruby_hdata_cb (const void *pointer, void *data, } /* + * Returns ruby info "ruby_eval". + */ + +const char * +weechat_ruby_info_eval_cb (const void *pointer, void *data, + const char *info_name, + const char *arguments) +{ + /* make C compiler happy */ + (void) pointer; + (void) data; + (void) info_name; + + weechat_ruby_eval (NULL, 0, 0, (arguments) ? arguments : ""); + if (ruby_eval_output) + free (ruby_eval_output); + ruby_eval_output = strdup (*ruby_buffer_output); + weechat_string_dyn_copy (ruby_buffer_output, NULL); + + return ruby_eval_output; +} + +/* * Returns infolist with ruby scripts. */ @@ -962,31 +1175,6 @@ weechat_ruby_signal_debug_dump_cb (const void *pointer, void *data, } /* - * Display infos about external libraries used. - */ - -int -weechat_ruby_signal_debug_libs_cb (const void *pointer, void *data, - const char *signal, - const char *type_data, void *signal_data) -{ - /* make C compiler happy */ - (void) pointer; - (void) data; - (void) signal; - (void) type_data; - (void) signal_data; - -#ifdef HAVE_RUBY_VERSION_H - weechat_printf (NULL, " %s: %s", RUBY_PLUGIN_NAME, ruby_version); -#else - weechat_printf (NULL, " %s: (?)", RUBY_PLUGIN_NAME); -#endif /* HAVE_RUBY_VERSION_H */ - - return WEECHAT_RC_OK; -} - -/* * Timer for executing actions. */ @@ -1080,8 +1268,8 @@ weechat_ruby_signal_script_action_cb (const void *pointer, void *data, int weechat_plugin_init (struct t_weechat_plugin *plugin, int argc, char *argv[]) { - struct t_plugin_script_init init; int ruby_error; + VALUE err; char *weechat_ruby_code = { "$stdout = WeechatOutputs\n" "$stderr = WeechatOutputs\n" @@ -1102,12 +1290,16 @@ weechat_plugin_init (struct t_weechat_plugin *plugin, int argc, char *argv[]) "\n" "class Module\n" "\n" - " def load_eval_file (file)\n" - " lines = ''\n" - " begin\n" - " lines = File.read(file)\n" - " rescue => e\n" - " return 1\n" + " def load_eval_file (file, code)\n" + " if !code.empty?\n" + " lines = code\n" + " else\n" + " lines = ''\n" + " begin\n" + " lines = File.read(file)\n" + " rescue => e\n" + " return 1\n" + " end\n" " end\n" "\n" " begin\n" @@ -1134,15 +1326,32 @@ weechat_plugin_init (struct t_weechat_plugin *plugin, int argc, char *argv[]) "\n" " return 0\n" " end\n" + "\n" + " def eval_code (code)\n" + " module_eval(code)\n" + " end\n" "end\n" }; weechat_ruby_plugin = plugin; + /* set interpreter name and version */ + weechat_hashtable_set (plugin->variables, "interpreter_name", + plugin->name); +#ifdef HAVE_RUBY_VERSION_H + weechat_hashtable_set (plugin->variables, "interpreter_version", + ruby_version); +#else + weechat_hashtable_set (plugin->variables, "interpreter_version", + ""); +#endif /* HAVE_RUBY_VERSION_H */ + ruby_error = 0; /* init stdout/stderr buffer */ - ruby_buffer_output[0] = '\0'; + ruby_buffer_output = weechat_string_dyn_alloc (256); + if (!ruby_buffer_output) + return WEECHAT_RC_ERROR; #if (defined(RUBY_API_VERSION_MAJOR) && defined(RUBY_API_VERSION_MINOR)) && (RUBY_API_VERSION_MAJOR >= 2 || (RUBY_API_VERSION_MAJOR == 1 && RUBY_API_VERSION_MINOR >= 9)) RUBY_INIT_STACK; @@ -1159,7 +1368,7 @@ weechat_plugin_init (struct t_weechat_plugin *plugin, int argc, char *argv[]) rb_define_singleton_method (ruby_mWeechatOutputs, "p", weechat_ruby_output, 1); rb_define_singleton_method (ruby_mWeechatOutputs, "flush", - weechat_ruby_output_flush, 0); + weechat_ruby_output_flush_ruby, 0); ruby_script ("__weechat_plugin__"); @@ -1173,24 +1382,31 @@ weechat_plugin_init (struct t_weechat_plugin *plugin, int argc, char *argv[]) weechat_gettext ("%s%s: unable to eval WeeChat ruby " "internal code"), weechat_prefix ("error"), RUBY_PLUGIN_NAME); - VALUE err = rb_gv_get ("$!"); + err = rb_gv_get ("$!"); weechat_ruby_print_exception (err); + weechat_string_dyn_free (ruby_buffer_output, 1); return WEECHAT_RC_ERROR; } ruby_init_loadpath (); - init.callback_command = &weechat_ruby_command_cb; - init.callback_completion = &weechat_ruby_completion_cb; - init.callback_hdata = &weechat_ruby_hdata_cb; - init.callback_infolist = &weechat_ruby_infolist_cb; - init.callback_signal_debug_dump = &weechat_ruby_signal_debug_dump_cb; - init.callback_signal_debug_libs = &weechat_ruby_signal_debug_libs_cb; - init.callback_signal_script_action = &weechat_ruby_signal_script_action_cb; - init.callback_load_file = &weechat_ruby_load_cb; + ruby_data.config_file = &ruby_config_file; + ruby_data.config_look_check_license = &ruby_config_look_check_license; + ruby_data.config_look_eval_keep_context = &ruby_config_look_eval_keep_context; + ruby_data.scripts = &ruby_scripts; + ruby_data.last_script = &last_ruby_script; + ruby_data.callback_command = &weechat_ruby_command_cb; + ruby_data.callback_completion = &weechat_ruby_completion_cb; + ruby_data.callback_hdata = &weechat_ruby_hdata_cb; + ruby_data.callback_info_eval = &weechat_ruby_info_eval_cb; + ruby_data.callback_infolist = &weechat_ruby_infolist_cb; + ruby_data.callback_signal_debug_dump = &weechat_ruby_signal_debug_dump_cb; + ruby_data.callback_signal_script_action = &weechat_ruby_signal_script_action_cb; + ruby_data.callback_load_file = &weechat_ruby_load_cb; + ruby_data.unload_all = &weechat_ruby_unload_all; ruby_quiet = 1; - plugin_script_init (weechat_ruby_plugin, argc, argv, &init); + plugin_script_init (weechat_ruby_plugin, argc, argv, &ruby_data); ruby_quiet = 0; plugin_script_display_short_list (weechat_ruby_plugin, @@ -1209,7 +1425,12 @@ weechat_plugin_end (struct t_weechat_plugin *plugin) { /* unload all scripts */ ruby_quiet = 1; - plugin_script_end (plugin, &ruby_scripts, &weechat_ruby_unload_all); + if (ruby_script_eval) + { + weechat_ruby_unload (ruby_script_eval); + ruby_script_eval = NULL; + } + plugin_script_end (plugin, &ruby_data); ruby_quiet = 0; ruby_cleanup (0); @@ -1221,6 +1442,9 @@ weechat_plugin_end (struct t_weechat_plugin *plugin) free (ruby_action_remove_list); if (ruby_action_autoload_list) free (ruby_action_autoload_list); + weechat_string_dyn_free (ruby_buffer_output, 1); + if (ruby_eval_output) + free (ruby_eval_output); return WEECHAT_RC_OK; } |