Changeset 537d9b9 for protocols/purple/purple.c
- Timestamp:
- 2016-11-20T08:40:36Z (8 years ago)
- Children:
- 3f44e43
- Parents:
- ba52ac5 (diff), 9f03c47 (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the(diff)
links above to see all the changes relative to each parent. - File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
protocols/purple/purple.c
rba52ac5 r537d9b9 43 43 const char *message, const char *who); 44 44 45 void purple_transfer_cancel_all(struct im_connection *ic); 46 45 47 /* purple_request_input specific stuff */ 46 48 typedef void (*ri_callback_t)(gpointer, const gchar *); … … 54 56 }; 55 57 58 struct purple_roomlist_data { 59 GSList *chats; 60 gint topic; 61 gboolean initialized; 62 }; 63 64 56 65 struct im_connection *purple_ic_by_pa(PurpleAccount *pa) 57 66 { … … 94 103 } 95 104 105 static char *purple_get_account_prpl_id(account_t *acc) 106 { 107 /* "oscar" is how non-purple bitlbee calls it, 108 * and it might be icq or aim, depending on the username */ 109 if (g_strcmp0(acc->prpl->name, "oscar") == 0) { 110 return (g_ascii_isdigit(acc->user[0])) ? "prpl-icq" : "prpl-aim"; 111 } 112 113 return acc->prpl->data; 114 } 115 96 116 static void purple_init(account_t *acc) 97 117 { 98 PurplePlugin *prpl = purple_plugins_find_with_id((char *) acc->prpl->data); 118 char *prpl_id = purple_get_account_prpl_id(acc); 119 PurplePlugin *prpl = purple_plugins_find_with_id(prpl_id); 99 120 PurplePluginProtocolInfo *pi = prpl->info->extra_info; 100 121 PurpleAccount *pa; … … 262 283 /* Go through all away states to figure out if away/status messages 263 284 are possible. */ 264 pa = purple_account_new(acc->user, (char *) acc->prpl->data);285 pa = purple_account_new(acc->user, prpl_id); 265 286 for (st = purple_account_get_status_types(pa); st; st = st->next) { 266 287 PurpleStatusPrimitive prim = purple_status_type_get_primitive(st->data); … … 345 366 346 367 ic->proto_data = pd = g_new0(struct purple_data, 1); 347 pd->account = purple_account_new(acc->user, (char *) acc->prpl->data);368 pd->account = purple_account_new(acc->user, purple_get_account_prpl_id(acc)); 348 369 pd->input_requests = g_hash_table_new_full(g_direct_hash, g_direct_equal, 349 370 NULL, g_free); … … 371 392 } 372 393 394 if (pd->filetransfers) { 395 purple_transfer_cancel_all(ic); 396 } 397 373 398 purple_account_set_enabled(pd->account, "BitlBee", FALSE); 374 399 purple_connections = g_slist_remove(purple_connections, ic); 375 400 purple_accounts_remove(pd->account); 401 imcb_chat_list_free(ic); 402 g_free(pd->chat_list_server); 376 403 g_hash_table_destroy(pd->input_requests); 377 404 g_free(pd); … … 673 700 } 674 701 702 void purple_chat_set_topic(struct groupchat *gc, char *topic) 703 { 704 PurpleConversation *pc = gc->data; 705 PurpleConvChat *pcc = PURPLE_CONV_CHAT(pc); 706 struct purple_data *pd = gc->ic->proto_data; 707 PurplePlugin *prpl = purple_plugins_find_with_id(pd->account->protocol_id); 708 PurplePluginProtocolInfo *pi = prpl->info->extra_info; 709 710 if (pi->set_chat_topic) { 711 pi->set_chat_topic(purple_account_get_connection(pd->account), 712 purple_conv_chat_get_id(pcc), 713 topic); 714 } 715 } 716 675 717 void purple_chat_kick(struct groupchat *gc, char *who, const char *message) 676 718 { … … 697 739 GHashTable *chat_hash; 698 740 PurpleConversation *conv; 741 struct groupchat *gc; 699 742 GList *info, *l; 700 743 … … 730 773 g_list_free(info); 731 774 775 /* do this before serv_join_chat to handle cases where prplcb_conv_new is called immediately (not async) */ 776 gc = imcb_chat_new(ic, room); 777 732 778 serv_join_chat(purple_account_get_connection(pd->account), chat_hash); 733 779 734 780 g_hash_table_destroy(chat_hash); 735 781 736 return imcb_chat_new(ic, room); 782 return gc; 783 } 784 785 void purple_chat_list(struct im_connection *ic, const char *server) 786 { 787 PurpleRoomlist *list; 788 struct purple_data *pd = ic->proto_data; 789 PurplePlugin *prpl = purple_plugins_find_with_id(pd->account->protocol_id); 790 PurplePluginProtocolInfo *pi = prpl->info->extra_info; 791 792 if (!pi || !pi->roomlist_get_list) { 793 imcb_log(ic, "Room listing unsupported by this purple plugin"); 794 return; 795 } 796 797 g_free(pd->chat_list_server); 798 pd->chat_list_server = (server && *server) ? g_strdup(server) : NULL; 799 800 list = purple_roomlist_get_list(pd->account->gc); 801 802 if (list) { 803 struct purple_roomlist_data *rld = list->ui_data; 804 rld->initialized = TRUE; 805 806 purple_roomlist_ref(list); 807 } 737 808 } 738 809 … … 970 1041 971 1042 /* Generic handler for IM or chat messages, covers write_chat, write_im and write_conv */ 972 static void handle_conv_msg(PurpleConversation *conv, const char *who, const char *message , guint32 bee_flags, time_t mtime)1043 static void handle_conv_msg(PurpleConversation *conv, const char *who, const char *message_, guint32 bee_flags, time_t mtime) 973 1044 { 974 1045 struct im_connection *ic = purple_ic_by_pa(conv->account); 975 1046 struct groupchat *gc = conv->ui_data; 1047 char *message = g_strdup(message_); 976 1048 PurpleBuddy *buddy; 977 1049 … … 982 1054 983 1055 if (conv->type == PURPLE_CONV_TYPE_IM) { 984 imcb_buddy_msg(ic, (char *) who, (char *)message, bee_flags, mtime);1056 imcb_buddy_msg(ic, who, message, bee_flags, mtime); 985 1057 } else if (gc) { 986 imcb_chat_msg(gc, who, (char *) message, bee_flags, mtime); 987 } 1058 imcb_chat_msg(gc, who, message, bee_flags, mtime); 1059 } 1060 1061 g_free(message); 988 1062 } 989 1063 … … 1171 1245 struct im_connection *ic = purple_ic_by_pa(account); 1172 1246 struct purple_data *pd = ic->proto_data; 1173 struct request_input_data *ri = g_new0(struct request_input_data, 1); 1174 guint id = pd->next_request_id++; 1247 struct request_input_data *ri; 1248 guint id; 1249 1250 /* hack so that jabber's chat list doesn't ask for conference server twice */ 1251 if (pd->chat_list_server && title && g_strcmp0(title, "Enter a Conference Server") == 0) { 1252 ((ri_callback_t) ok_cb)(user_data, pd->chat_list_server); 1253 g_free(pd->chat_list_server); 1254 pd->chat_list_server = NULL; 1255 return NULL; 1256 } 1257 1258 id = pd->next_request_id++; 1259 ri = g_new0(struct request_input_data, 1); 1175 1260 1176 1261 ri->id = id; … … 1182 1267 1183 1268 imcb_add_buddy(ic, ri->buddy, NULL); 1184 imcb_buddy_msg(ic, ri->buddy, secondary, 0, 0); 1269 1270 if (title && *title) { 1271 imcb_buddy_msg(ic, ri->buddy, title, 0, 0); 1272 } 1273 1274 if (primary && *primary) { 1275 imcb_buddy_msg(ic, ri->buddy, primary, 0, 0); 1276 } 1277 1278 if (secondary && *secondary) { 1279 imcb_buddy_msg(ic, ri->buddy, secondary, 0, 0); 1280 } 1185 1281 1186 1282 return ri; … … 1256 1352 prplcb_privacy_deny_added, /* deny_added */ 1257 1353 prplcb_privacy_deny_removed, /* deny_removed */ 1354 }; 1355 1356 static void prplcb_roomlist_create(PurpleRoomlist *list) 1357 { 1358 struct purple_roomlist_data *rld; 1359 1360 list->ui_data = rld = g_new0(struct purple_roomlist_data, 1); 1361 rld->topic = -1; 1362 } 1363 1364 static void prplcb_roomlist_set_fields(PurpleRoomlist *list, GList *fields) 1365 { 1366 gint topic = -1; 1367 GList *l; 1368 guint i; 1369 PurpleRoomlistField *field; 1370 struct purple_roomlist_data *rld = list->ui_data; 1371 1372 for (i = 0, l = fields; l; i++, l = l->next) { 1373 field = l->data; 1374 1375 /* Use the first visible string field as a fallback topic */ 1376 if (i != 0 && topic < 0 && !field->hidden && 1377 field->type == PURPLE_ROOMLIST_FIELD_STRING) { 1378 topic = i; 1379 } 1380 1381 if ((g_strcasecmp(field->name, "description") == 0) || 1382 (g_strcasecmp(field->name, "topic") == 0)) { 1383 if (field->type == PURPLE_ROOMLIST_FIELD_STRING) { 1384 rld->topic = i; 1385 } 1386 } 1387 } 1388 1389 if (rld->topic < 0) { 1390 rld->topic = topic; 1391 } 1392 } 1393 1394 static void prplcb_roomlist_add_room(PurpleRoomlist *list, PurpleRoomlistRoom *room) 1395 { 1396 bee_chat_info_t *ci; 1397 const char *title; 1398 const char *topic; 1399 GList *fields; 1400 struct purple_roomlist_data *rld = list->ui_data; 1401 1402 fields = purple_roomlist_room_get_fields(room); 1403 title = purple_roomlist_room_get_name(room); 1404 1405 if (rld->topic >= 0) { 1406 topic = g_list_nth_data(fields, rld->topic); 1407 } else { 1408 topic = NULL; 1409 } 1410 1411 ci = g_new(bee_chat_info_t, 1); 1412 ci->title = g_strdup(title); 1413 ci->topic = g_strdup(topic); 1414 rld->chats = g_slist_prepend(rld->chats, ci); 1415 } 1416 1417 static void prplcb_roomlist_in_progress(PurpleRoomlist *list, gboolean in_progress) 1418 { 1419 struct im_connection *ic; 1420 struct purple_data *pd; 1421 struct purple_roomlist_data *rld = list->ui_data; 1422 1423 if (in_progress || !rld) { 1424 return; 1425 } 1426 1427 ic = purple_ic_by_pa(list->account); 1428 imcb_chat_list_free(ic); 1429 1430 pd = ic->proto_data; 1431 g_free(pd->chat_list_server); 1432 pd->chat_list_server = NULL; 1433 1434 ic->chatlist = g_slist_reverse(rld->chats); 1435 rld->chats = NULL; 1436 1437 imcb_chat_list_finish(ic); 1438 1439 if (rld->initialized) { 1440 purple_roomlist_unref(list); 1441 } 1442 } 1443 1444 static void prplcb_roomlist_destroy(PurpleRoomlist *list) 1445 { 1446 g_free(list->ui_data); 1447 list->ui_data = NULL; 1448 } 1449 1450 static PurpleRoomlistUiOps bee_roomlist_uiops = 1451 { 1452 NULL, /* show_with_account */ 1453 prplcb_roomlist_create, /* create */ 1454 prplcb_roomlist_set_fields, /* set_fields */ 1455 prplcb_roomlist_add_room, /* add_room */ 1456 prplcb_roomlist_in_progress, /* in_progress */ 1457 prplcb_roomlist_destroy, /* destroy */ 1258 1458 }; 1259 1459 … … 1422 1622 purple_request_set_ui_ops(&bee_request_uiops); 1423 1623 purple_privacy_set_ui_ops(&bee_privacy_uiops); 1624 purple_roomlist_set_ui_ops(&bee_roomlist_uiops); 1424 1625 purple_notify_set_ui_ops(&bee_notify_uiops); 1425 1626 purple_accounts_set_ui_ops(&bee_account_uiops); … … 1438 1639 char *dir; 1439 1640 1641 if (purple_get_core() != NULL) { 1642 log_message(LOGLVL_ERROR, "libpurple already initialized. " 1643 "Please use inetd or ForkDaemon mode instead."); 1644 return; 1645 } 1646 1440 1647 g_assert((int) B_EV_IO_READ == (int) PURPLE_INPUT_READ); 1441 1648 g_assert((int) B_EV_IO_WRITE == (int) PURPLE_INPUT_WRITE); … … 1443 1650 dir = g_strdup_printf("%s/purple", global.conf->configdir); 1444 1651 purple_util_set_user_dir(dir); 1652 g_free(dir); 1653 1654 dir = g_strdup_printf("%s/purple", global.conf->plugindir); 1655 purple_plugins_add_search_path(dir); 1445 1656 g_free(dir); 1446 1657 … … 1506 1717 funcs.chat_with = purple_chat_with; 1507 1718 funcs.chat_invite = purple_chat_invite; 1719 funcs.chat_topic = purple_chat_set_topic; 1508 1720 funcs.chat_kick = purple_chat_kick; 1509 1721 funcs.chat_leave = purple_chat_leave; 1510 1722 funcs.chat_join = purple_chat_join; 1723 funcs.chat_list = purple_chat_list; 1511 1724 funcs.transfer_request = purple_transfer_request; 1512 1725 … … 1517 1730 for (prots = purple_plugins_get_protocols(); prots; prots = prots->next) { 1518 1731 PurplePlugin *prot = prots->data; 1732 PurplePluginProtocolInfo *pi = prot->info->extra_info; 1519 1733 struct prpl *ret; 1520 1734 … … 1530 1744 ret->name += 5; 1531 1745 } 1746 1747 if (pi->options & OPT_PROTO_NO_PASSWORD) { 1748 ret->options |= PRPL_OPT_NO_PASSWORD; 1749 } 1750 1751 if (pi->options & OPT_PROTO_PASSWORD_OPTIONAL) { 1752 ret->options |= PRPL_OPT_PASSWORD_OPTIONAL; 1753 } 1754 1532 1755 register_protocol(ret); 1533 1756 … … 1539 1762 ret = g_memdup(&funcs, sizeof(funcs)); 1540 1763 ret->name = "oscar"; 1541 ret->data = prot->info->id; 1764 /* purple_get_account_prpl_id() determines the actual protocol ID (icq/aim) */ 1765 ret->data = NULL; 1542 1766 register_protocol(ret); 1543 1767 }
Note: See TracChangeset
for help on using the changeset viewer.