diff options
author | Marius Halden <marius.h@lden.org> | 2016-05-26 15:07:34 +0200 |
---|---|---|
committer | Marius Halden <marius.h@lden.org> | 2016-05-26 15:07:34 +0200 |
commit | 3448d86a3f329ec4d625bd72e64a96061e71e675 (patch) | |
tree | ff41da0d1f55d449b24a91e4b7a91cab0cbcc84d | |
parent | 8e4d9a1769a7d566278ed95d94a1cabd8fdc62e7 (diff) | |
parent | 59a7dc58dcf39b7eaed2015423f8a4fc2da3c7fd (diff) |
Merge branch 'master' into patched-master
-rw-r--r-- | bitlbee.h | 1 | ||||
-rwxr-xr-x | configure | 2 | ||||
-rw-r--r-- | doc/user-guide/commands.xml | 12 | ||||
-rw-r--r-- | otr.c | 16 | ||||
-rw-r--r-- | protocols/nogaim.c | 81 | ||||
-rw-r--r-- | protocols/nogaim.h | 16 | ||||
-rw-r--r-- | protocols/purple/purple.c | 9 | ||||
-rw-r--r-- | protocols/skype/skype.c | 14 | ||||
-rw-r--r-- | protocols/twitter/twitter.c | 3 | ||||
-rw-r--r-- | root_commands.c | 86 |
10 files changed, 235 insertions, 5 deletions
@@ -41,6 +41,7 @@ extern "C" { #define VERSION BITLBEE_VERSION #define BITLBEE_VER(a, b, c) (((a) << 16) + ((b) << 8) + (c)) #define BITLBEE_VERSION_CODE BITLBEE_VER(3, 4, 2) +#define BITLBEE_ABI_VERSION_CODE 1 #define MAX_STRING 511 @@ -57,6 +57,8 @@ ldap=0 pie=1 +arch=$(uname -s) + GLIB_MIN_VERSION=2.16 # Cygwin and Darwin don't support PIC/PIE diff --git a/doc/user-guide/commands.xml b/doc/user-guide/commands.xml index 6f66a39d..56beba54 100644 --- a/doc/user-guide/commands.xml +++ b/doc/user-guide/commands.xml @@ -1834,6 +1834,18 @@ </description> </bitlbee-command> + <bitlbee-command name="plugins"> + <short-description>List all the external plugins and protocols</short-description> + <syntax>plugins</syntax> + + <description> + <para> + This gives you a list of all the external plugins and protocols. + </para> + </description> + + </bitlbee-command> + <bitlbee-command name="qlist"> <short-description>List all the unanswered questions root asked</short-description> <syntax>qlist</syntax> @@ -267,6 +267,22 @@ void init_plugin(void) register_irc_plugin(&otr_plugin); } +#ifndef OTR_BI +struct plugin_info *init_plugin_info(void) +{ + static struct plugin_info info = { + BITLBEE_ABI_VERSION_CODE, + "otr", + BITLBEE_VERSION, + "Off-the-Record communication", + NULL, + NULL + }; + + return &info; +} +#endif + gboolean otr_irc_new(irc_t *irc) { set_t *s; diff --git a/protocols/nogaim.c b/protocols/nogaim.c index c9cbb033..ab11508b 100644 --- a/protocols/nogaim.c +++ b/protocols/nogaim.c @@ -39,24 +39,84 @@ GSList *connections; #ifdef WITH_PLUGINS +GList *plugins = NULL; + +static gint pluginscmp(gconstpointer a, gconstpointer b, gpointer data) +{ + const struct plugin_info *ia = a; + const struct plugin_info *ib = b; + + return g_strcasecmp(ia->name, ib->name); +} + gboolean load_plugin(char *path) { + GList *l; + struct plugin_info *i; + struct plugin_info *info; + struct plugin_info * (*info_function) (void) = NULL; void (*init_function) (void); GModule *mod = g_module_open(path, G_MODULE_BIND_LAZY); + gboolean loaded = FALSE; if (!mod) { log_message(LOGLVL_ERROR, "Error loading plugin `%s': %s\n", path, g_module_error()); return FALSE; } + if (g_module_symbol(mod, "init_plugin_info", (gpointer *) &info_function)) { + info = info_function(); + + if (info->abiver != BITLBEE_ABI_VERSION_CODE) { + log_message(LOGLVL_ERROR, + "`%s' uses ABI %u but %u is required\n", + path, info->abiver, + BITLBEE_ABI_VERSION_CODE); + g_module_close(mod); + return FALSE; + } + + if (!info->name || !info->version) { + log_message(LOGLVL_ERROR, + "Name or version missing from the " + "plugin info in `%s'\n", path); + g_module_close(mod); + return FALSE; + } + + for (l = plugins; l; l = l->next) { + i = l->data; + + if (g_strcasecmp(i->name, info->name) == 0) { + loaded = TRUE; + break; + } + } + + if (loaded) { + log_message(LOGLVL_WARNING, + "%s plugin already loaded\n", + info->name); + g_module_close(mod); + return FALSE; + } + } else { + log_message(LOGLVL_WARNING, "Can't find function `init_plugin_info' in `%s'\n", path); + } + if (!g_module_symbol(mod, "init_plugin", (gpointer *) &init_function)) { log_message(LOGLVL_WARNING, "Can't find function `init_plugin' in `%s'\n", path); + g_module_close(mod); return FALSE; } - init_function(); + if (info_function) { + plugins = g_list_insert_sorted_with_data(plugins, info, + pluginscmp, NULL); + } + init_function(); return TRUE; } @@ -72,6 +132,10 @@ void load_plugins(void) char *path; while ((entry = g_dir_read_name(dir))) { + if (!g_str_has_suffix(entry, "." G_MODULE_SUFFIX)) { + continue; + } + path = g_build_filename(global.conf->plugindir, entry, NULL); if (!path) { log_message(LOGLVL_WARNING, "Can't build path for %s\n", entry); @@ -86,6 +150,11 @@ void load_plugins(void) g_dir_close(dir); } } + +GList *get_plugins() +{ + return plugins; +} #endif GList *protocols = NULL; @@ -164,6 +233,16 @@ void nogaim_init() #endif } +GList *get_protocols() +{ + return protocols; +} + +GList *get_protocols_disabled() +{ + return disabled_protocols; +} + GSList *get_connections() { return connections; diff --git a/protocols/nogaim.h b/protocols/nogaim.h index 40b1ed7b..e5569313 100644 --- a/protocols/nogaim.h +++ b/protocols/nogaim.h @@ -270,8 +270,24 @@ struct prpl { void *resv5; }; +struct plugin_info +{ + guint abiver; + const char *name; + const char *version; + const char *description; + const char *author; + const char *url; +}; + +#ifdef WITH_PLUGINS +G_MODULE_EXPORT GList *get_plugins(); +#endif + /* im_api core stuff. */ void nogaim_init(); +G_MODULE_EXPORT GList *get_protocols(); +G_MODULE_EXPORT GList *get_protocols_disabled(); G_MODULE_EXPORT GSList *get_connections(); G_MODULE_EXPORT struct prpl *find_protocol(const char *name); G_MODULE_EXPORT gboolean is_protocol_disabled(const char *name); diff --git a/protocols/purple/purple.c b/protocols/purple/purple.c index 2b3a09a3..589cc093 100644 --- a/protocols/purple/purple.c +++ b/protocols/purple/purple.c @@ -978,10 +978,11 @@ void prplcb_conv_del_users(PurpleConversation *conv, GList *cbuddies) } /* Generic handler for IM or chat messages, covers write_chat, write_im and write_conv */ -static void handle_conv_msg(PurpleConversation *conv, const char *who, const char *message, guint32 bee_flags, time_t mtime) +static void handle_conv_msg(PurpleConversation *conv, const char *who, const char *message_, guint32 bee_flags, time_t mtime) { struct im_connection *ic = purple_ic_by_pa(conv->account); struct groupchat *gc = conv->ui_data; + char *message = g_strdup(message_); PurpleBuddy *buddy; buddy = purple_find_buddy(conv->account, who); @@ -990,10 +991,12 @@ static void handle_conv_msg(PurpleConversation *conv, const char *who, const cha } if (conv->type == PURPLE_CONV_TYPE_IM) { - imcb_buddy_msg(ic, (char *) who, (char *) message, bee_flags, mtime); + imcb_buddy_msg(ic, who, message, bee_flags, mtime); } else if (gc) { - imcb_chat_msg(gc, who, (char *) message, bee_flags, mtime); + imcb_chat_msg(gc, who, message, bee_flags, mtime); } + + g_free(message); } /* Handles write_im and write_chat. Removes echoes of locally sent messages */ diff --git a/protocols/skype/skype.c b/protocols/skype/skype.c index a21af8ef..bd8a1850 100644 --- a/protocols/skype/skype.c +++ b/protocols/skype/skype.c @@ -1762,3 +1762,17 @@ void init_plugin(void) #endif register_protocol(ret); } + +struct plugin_info *init_plugin_info(void) +{ + static struct plugin_info info = { + BITLBEE_ABI_VERSION_CODE, + "skype", + BITLBEE_VERSION, + "Skype protocol plugin", + NULL, + NULL + }; + + return &info; +} diff --git a/protocols/twitter/twitter.c b/protocols/twitter/twitter.c index 5694c1b6..5f6156a6 100644 --- a/protocols/twitter/twitter.c +++ b/protocols/twitter/twitter.c @@ -985,7 +985,8 @@ static void twitter_handle_command(struct im_connection *ic, char *message) goto eof; } else if ((g_strcasecmp(cmd[0], "favourite") == 0 || g_strcasecmp(cmd[0], "favorite") == 0 || - g_strcasecmp(cmd[0], "fav") == 0) && cmd[1]) { + g_strcasecmp(cmd[0], "fav") == 0 || + g_strcasecmp(cmd[0], "like") == 0) && cmd[1]) { if ((id = twitter_message_id_from_command_arg(ic, cmd[1], NULL))) { twitter_favourite_tweet(ic, id); } else { diff --git a/root_commands.c b/root_commands.c index 702a068d..add9bceb 100644 --- a/root_commands.c +++ b/root_commands.c @@ -1123,6 +1123,91 @@ static void cmd_blist(irc_t *irc, char **cmd) } } +static gint prplcmp(gconstpointer a, gconstpointer b) +{ + const struct prpl *pa = a; + const struct prpl *pb = b; + + return g_strcasecmp(pa->name, pb->name); +} + +static void prplstr(GList *prpls, GString *gstr) +{ + const char *last = NULL; + GList *l; + struct prpl *p; + + prpls = g_list_copy(prpls); + prpls = g_list_sort(prpls, prplcmp); + + for (l = prpls; l; l = l->next) { + p = l->data; + + if (last && g_strcasecmp(p->name, last) == 0) { + /* Ignore duplicates (mainly for libpurple) */ + continue; + } + + if (gstr->len != 0) { + g_string_append(gstr, ", "); + } + + g_string_append(gstr, p->name); + last = p->name; + } + + g_list_free(prpls); +} + +static void cmd_plugins(irc_t *irc, char **cmd) +{ + GList *prpls; + GString *gstr; + +#ifdef WITH_PLUGINS + GList *l; + struct plugin_info *info; + + for (l = get_plugins(); l; l = l->next) { + info = l->data; + irc_rootmsg(irc, "%s:", info->name); + irc_rootmsg(irc, " Version: %s", info->version); + + if (info->description) { + irc_rootmsg(irc, " Description: %s", info->description); + } + + if (info->author) { + irc_rootmsg(irc, " Author: %s", info->author); + } + + if (info->url) { + irc_rootmsg(irc, " URL: %s", info->url); + } + + irc_rootmsg(irc, ""); + } +#endif + + gstr = g_string_new(NULL); + prpls = get_protocols(); + + if (prpls) { + prplstr(prpls, gstr); + irc_rootmsg(irc, "Enabled Protocols: %s", gstr->str); + g_string_truncate(gstr, 0); + } + + prpls = get_protocols_disabled(); + + if (prpls) { + prplstr(prpls, gstr); + irc_rootmsg(irc, "Disabled Protocols: %s", gstr->str); + } + + g_string_free(gstr, TRUE); +} + static void cmd_qlist(irc_t *irc, char **cmd) { query_t *q = irc->queries; @@ -1381,6 +1466,7 @@ command_t root_commands[] = { { "info", 1, cmd_info, 0 }, { "nick", 1, cmd_nick, 0 }, { "no", 0, cmd_yesno, 0 }, + { "plugins", 0, cmd_plugins, 0 }, { "qlist", 0, cmd_qlist, 0 }, { "register", 0, cmd_register, 0 }, { "remove", 1, cmd_remove, 0 }, |