~ubuntu-branches/ubuntu/trusty/irssi-plugin-xmpp/trusty

« back to all changes in this revision

Viewing changes to src/core/xmpp-rosters-tools.c

  • Committer: Bazaar Package Importer
  • Author(s): David Ammouial
  • Date: 2009-05-12 12:14:44 UTC
  • mfrom: (1.1.3 upstream) (2.1.2 sid)
  • Revision ID: james.westby@ubuntu.com-20090512121444-5jeho5h3zsy4oij7
Tags: 0.13+cvs20090406-1
* New CVS snapshot, built against irssi-dev 0.8.13:
  - New features and bugfixes.
  - Fix segfault when successfully identified (Closes: #521227).
  - Fix build error (Closes: #527697)
* Depend on irssi >=0.8.13, build-depend on irssi-dev >=0.8.13.
* Bump Standards-Version to 3.8.1 (no changes needed).
* Add INTERNAL to documentation files.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/*
2
 
 * $Id: xmpp-rosters-tools.c,v 1.8 2008/04/05 20:50:45 errtu Exp $
3
 
 *
4
 
 * Copyright (C) 2007 Colin DIDIER
5
 
 *
6
 
 * This program is free software; you can redistribute it and/or modify
7
 
 * it under the terms of the GNU General Public License version 2 as
8
 
 * published by the Free Software Foundation.
9
 
 *
10
 
 * This program is distributed in the hope that it will be useful,
11
 
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
 
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
 
 * GNU General Public License for more details.
14
 
 *
15
 
 * You should have received a copy of the GNU General Public License along
16
 
 * with this program; if not, write to the Free Software Foundation, Inc.,
17
 
 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18
 
 */
19
 
 
20
 
#include <string.h>
21
 
#include <stdlib.h>
22
 
 
23
 
#include "module.h"
24
 
#include "settings.h"
25
 
 
26
 
#include "xmpp-servers.h"
27
 
#include "xmpp-rosters.h"
28
 
#include "xmpp-rosters-tools.h"
29
 
#include "xmpp-tools.h"
30
 
 
31
 
static int
32
 
find_user_func(gconstpointer user, gconstpointer jid)
33
 
{
34
 
        g_return_val_if_fail(user != NULL, -1);
35
 
        g_return_val_if_fail(jid != NULL, -1);
36
 
 
37
 
        return strcmp(((XMPP_ROSTER_USER_REC *)user)->jid, jid);
38
 
}
39
 
 
40
 
static int
41
 
find_username_func(gconstpointer user_pointer, gconstpointer name)
42
 
{
43
 
        XMPP_ROSTER_USER_REC *user = (XMPP_ROSTER_USER_REC *)user_pointer;
44
 
 
45
 
        g_return_val_if_fail(user_pointer != NULL, -1);
46
 
 
47
 
        if (user->name == NULL)
48
 
                return -1;
49
 
        return strcmp(user->name, name);
50
 
}
51
 
 
52
 
static int
53
 
find_resource_func(gconstpointer resource, gconstpointer name)
54
 
{
55
 
        char *res = ((XMPP_ROSTER_RESOURCE_REC *)resource)->name;
56
 
 
57
 
        g_return_val_if_fail(resource != NULL, -1);
58
 
 
59
 
        if(res == NULL && name == NULL)
60
 
                return 0;
61
 
        if (res == NULL || name == NULL)
62
 
                return -1;
63
 
        return strcmp(res, name);
64
 
}
65
 
 
66
 
static int
67
 
func_sort_user(gconstpointer user1_pointer, gconstpointer user2_pointer)
68
 
{
69
 
        GSList *resources1_list, *resources2_list;
70
 
        XMPP_ROSTER_USER_REC *user1, *user2;
71
 
        XMPP_ROSTER_RESOURCE_REC *fisrt_resources1, *fisrt_resources2;
72
 
 
73
 
        user1 = (XMPP_ROSTER_USER_REC *)user1_pointer;
74
 
        resources1_list =  user1->resources;
75
 
        user2 = (XMPP_ROSTER_USER_REC *)user2_pointer;
76
 
        resources2_list =  user2->resources;
77
 
 
78
 
        if (resources1_list == resources2_list
79
 
            || (user1->error == TRUE && user2->error == TRUE))
80
 
                goto by_name;
81
 
        if (user1->error || resources1_list == NULL)
82
 
                return 1;
83
 
        if (user2->error || resources2_list == NULL)
84
 
                return -1;
85
 
 
86
 
        fisrt_resources1 = (XMPP_ROSTER_RESOURCE_REC *)resources1_list->data;
87
 
        fisrt_resources2 = (XMPP_ROSTER_RESOURCE_REC *)resources2_list->data;
88
 
 
89
 
        if (fisrt_resources1->show == fisrt_resources2->show)
90
 
                goto by_name;
91
 
 
92
 
        return fisrt_resources2->show - fisrt_resources1->show;
93
 
 
94
 
by_name:
95
 
        if (user1->name == NULL && user2->name != NULL)
96
 
                return -1;
97
 
        if (user1->name != NULL && user2->name == NULL)
98
 
                return 1;
99
 
        if (user1->name != NULL && user2->name != NULL)
100
 
                 return strcmp(user1->name, user2->name);
101
 
 
102
 
        return strcmp(user1->jid, user2->jid);
103
 
}
104
 
 
105
 
XMPP_ROSTER_GROUP_REC *
106
 
find_group_from_user(XMPP_SERVER_REC *server, XMPP_ROSTER_USER_REC *user)
107
 
{
108
 
        GSList *group_list, *group_list_found;
109
 
 
110
 
        g_return_val_if_fail(IS_XMPP_SERVER(server), NULL);
111
 
 
112
 
        group_list = server->roster;
113
 
        group_list_found = NULL;
114
 
 
115
 
        while (group_list_found != NULL && group_list != NULL) {
116
 
                group_list_found = g_slist_find(group_list, user);
117
 
                group_list = group_list->next;
118
 
        }
119
 
 
120
 
        return (XMPP_ROSTER_GROUP_REC *)group_list->data;
121
 
}
122
 
 
123
 
XMPP_ROSTER_USER_REC *
124
 
xmpp_rosters_find_user(GSList *groups, const char *jid,
125
 
    XMPP_ROSTER_GROUP_REC **group, XMPP_ROSTER_RESOURCE_REC **resource)
126
 
{
127
 
        GSList *g, *gl, *ul, *rl;
128
 
        char *pos;
129
 
 
130
 
        if ((pos = xmpp_find_resource_sep(jid)) != NULL)
131
 
                *pos = '\0';
132
 
 
133
 
        ul = NULL;
134
 
        for (gl = groups; ul == NULL && gl != NULL; gl = gl->next) {
135
 
                ul = g_slist_find_custom(
136
 
                    ((XMPP_ROSTER_GROUP_REC *)gl->data)->users, jid,
137
 
                    (GCompareFunc)find_user_func);
138
 
                g = gl;
139
 
        }
140
 
 
141
 
        if (&*group != NULL)
142
 
                *group = ul != NULL ?
143
 
                    (XMPP_ROSTER_GROUP_REC *)g->data : NULL;
144
 
 
145
 
        if (&*resource != NULL)
146
 
                *resource = ul != NULL && pos != NULL ?
147
 
                        xmpp_rosters_find_resource(
148
 
                            (XMPP_ROSTER_USER_REC *)ul->data, pos+1) : NULL;
149
 
 
150
 
        if (pos != NULL)
151
 
                *pos = '/';
152
 
 
153
 
        return ul != NULL ?
154
 
            (XMPP_ROSTER_USER_REC *)ul->data : NULL;
155
 
}
156
 
 
157
 
XMPP_ROSTER_USER_REC *
158
 
find_username(GSList *groups, const char *name, XMPP_ROSTER_GROUP_REC **group)
159
 
{
160
 
        GSList *group_list, *group_tmp, *user_list;
161
 
 
162
 
        group_list = groups;
163
 
        group_tmp = NULL;
164
 
        user_list = NULL;
165
 
 
166
 
        while (user_list == NULL && group_list != NULL) {
167
 
                user_list = g_slist_find_custom(
168
 
                    ((XMPP_ROSTER_GROUP_REC *)group_list->data)->users, name,
169
 
                    (GCompareFunc)find_username_func);
170
 
 
171
 
                group_tmp = group_list;
172
 
                group_list = g_slist_next(group_list);
173
 
        }
174
 
 
175
 
        if (group != NULL && group_tmp != NULL)
176
 
                *group = group_tmp->data;
177
 
 
178
 
        return user_list ? (XMPP_ROSTER_USER_REC *)user_list->data : NULL;
179
 
}
180
 
 
181
 
XMPP_ROSTER_RESOURCE_REC *
182
 
xmpp_rosters_find_resource(XMPP_ROSTER_USER_REC *user, const char *resource)
183
 
{
184
 
        GSList *resource_list;
185
 
 
186
 
        g_return_val_if_fail(user != NULL, NULL);
187
 
 
188
 
        resource_list = g_slist_find_custom(user->resources, resource,
189
 
            (GCompareFunc)find_resource_func);
190
 
 
191
 
        return resource_list ?
192
 
            (XMPP_ROSTER_RESOURCE_REC *)resource_list->data : NULL;
193
 
}
194
 
 
195
 
XMPP_ROSTER_RESOURCE_REC *
196
 
xmpp_rosters_find_own_resource(XMPP_SERVER_REC *server, const char *resource)
197
 
{
198
 
        GSList *resource_list;
199
 
 
200
 
        g_return_val_if_fail(server != NULL, NULL);
201
 
 
202
 
        resource_list = g_slist_find_custom(server->resources, resource,
203
 
            (GCompareFunc)find_resource_func);
204
 
 
205
 
        return resource_list ?
206
 
            (XMPP_ROSTER_RESOURCE_REC *)resource_list->data : NULL;
207
 
}
208
 
 
209
 
char *
210
 
xmpp_rosters_resolve_name(XMPP_SERVER_REC *server, const char *name)
211
 
{
212
 
        XMPP_ROSTER_USER_REC *user;
213
 
        XMPP_ROSTER_RESOURCE_REC *resource;
214
 
        char *res, *str;
215
 
 
216
 
        g_return_val_if_fail(IS_XMPP_SERVER(server), NULL);
217
 
        g_return_val_if_fail(name != NULL, NULL);
218
 
 
219
 
        g_strstrip((char *)name);
220
 
 
221
 
        user = find_username(server->roster, name, NULL);
222
 
        if (user == NULL)
223
 
                user = xmpp_rosters_find_user(server->roster, name, NULL,
224
 
                    NULL);
225
 
 
226
 
        if (user != NULL) {
227
 
                if (!xmpp_have_resource(name)) {
228
 
                        /* if unspecified, use the highest resource */
229
 
                        if (user->resources != NULL) {
230
 
                                resource = user->resources->data;
231
 
                                if (resource->name != NULL)
232
 
                                        return g_strconcat(user->jid, "/",
233
 
                                            resource->name, NULL);
234
 
                        }
235
 
                        return g_strdup(user->jid);
236
 
                }
237
 
 
238
 
                res = xmpp_extract_resource(name);
239
 
                str = g_strconcat(user->jid, "/", res, NULL);
240
 
                g_free(res);
241
 
                return str;
242
 
        }
243
 
 
244
 
        return NULL;
245
 
}
246
 
 
247
 
gboolean
248
 
xmpp_rosters_show_user(XMPP_ROSTER_USER_REC *user)
249
 
{
250
 
        g_return_val_if_fail(user != NULL, FALSE);
251
 
 
252
 
        return (user->resources != NULL &&
253
 
            user->subscription == XMPP_SUBSCRIPTION_BOTH) ||
254
 
            (user->subscription != XMPP_SUBSCRIPTION_BOTH &&
255
 
            settings_get_bool("roster_show_offline_unsuscribed"))
256
 
            || settings_get_bool("roster_show_offline");
257
 
}
258
 
 
259
 
void
260
 
xmpp_rosters_reorder(XMPP_ROSTER_GROUP_REC *group)
261
 
{
262
 
        g_return_if_fail(group != NULL);
263
 
 
264
 
        group->users = g_slist_sort(group->users,
265
 
            (GCompareFunc)func_sort_user);
266
 
}
267
 
 
268
 
int
269
 
xmpp_presence_get_show(const char *show)
270
 
{
271
 
        if (show != NULL) {
272
 
                if (g_ascii_strcasecmp(show,
273
 
                    xmpp_presence_show[XMPP_PRESENCE_CHAT]) == 0)
274
 
                        return XMPP_PRESENCE_CHAT;
275
 
 
276
 
                else if (g_ascii_strcasecmp(show,
277
 
                    xmpp_presence_show[XMPP_PRESENCE_DND]) == 0)
278
 
                        return XMPP_PRESENCE_DND;
279
 
 
280
 
                else if (g_ascii_strcasecmp(show,
281
 
                    xmpp_presence_show[XMPP_PRESENCE_XA]) == 0)
282
 
                        return XMPP_PRESENCE_XA;
283
 
 
284
 
                else if (g_ascii_strcasecmp(show,
285
 
                    xmpp_presence_show[XMPP_PRESENCE_AWAY]) == 0)
286
 
                        return XMPP_PRESENCE_AWAY;
287
 
        }
288
 
        return XMPP_PRESENCE_AVAILABLE;
289
 
}