Mercurial > pidgin.yaz
annotate src/log.c @ 9613:1b13160bf5a4
[gaim-migrate @ 10456]
"Okay, now it's better. Still should close #997210. Note
the list below is mostly the same as my initial comment and
replaces the former information.
1) Prevent a crash if you sign off and try to dequeue
messages from the away dialog. This was because we tried to
use the destroyed GaimConnection in a couple places to get
the prpl's name for the HTML logger and other conversation
data. We look up the information via the account instead.
2) Prevent a possible crash if gaim_gtkconv_write_conv is
called with who as NULL.
3) Prevent (null) or an empty string from being logged as
the sender's name if the sender no longer has an alias
because the
account is signed off." --Kevin Stange
committer: Tailor Script <tailor@pidgin.im>
author | Luke Schierer <lschiere@pidgin.im> |
---|---|
date | Thu, 29 Jul 2004 03:11:00 +0000 |
parents | 9c78aaa4117e |
children | 70ff55c0939b |
rev | line source |
---|---|
7431 | 1 /** |
2 * @file log.c Logging API | |
3 * @ingroup core | |
4 * | |
5 * gaim | |
6 * | |
8046 | 7 * Gaim is the legal property of its developers, whose names are too numerous |
8 * to list here. Please refer to the COPYRIGHT file distributed with this | |
9 * source distribution. | |
7436 | 10 * |
7431 | 11 * This program is free software; you can redistribute it and/or modify |
12 * it under the terms of the GNU General Public License as published by | |
13 * the Free Software Foundation; either version 2 of the License, or | |
14 * (at your option) any later version. | |
15 * | |
16 * This program is distributed in the hope that it will be useful, | |
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
19 * GNU General Public License for more details. | |
20 * | |
21 * You should have received a copy of the GNU General Public License | |
22 * along with this program; if not, write to the Free Software | |
23 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA | |
4184 | 24 */ |
4195 | 25 |
7431 | 26 #include "account.h" |
5872
059d95c67cda
[gaim-migrate @ 6304]
Christian Hammond <chipx86@chipx86.com>
parents:
5839
diff
changeset
|
27 #include "debug.h" |
7431 | 28 #include "internal.h" |
5872
059d95c67cda
[gaim-migrate @ 6304]
Christian Hammond <chipx86@chipx86.com>
parents:
5839
diff
changeset
|
29 #include "log.h" |
5548 | 30 #include "prefs.h" |
5872
059d95c67cda
[gaim-migrate @ 6304]
Christian Hammond <chipx86@chipx86.com>
parents:
5839
diff
changeset
|
31 #include "util.h" |
7764 | 32 #include "stringref.h" |
5872
059d95c67cda
[gaim-migrate @ 6304]
Christian Hammond <chipx86@chipx86.com>
parents:
5839
diff
changeset
|
33 |
8096 | 34 static GSList *loggers = NULL; |
35 | |
7457 | 36 static GaimLogLogger html_logger; |
7431 | 37 static GaimLogLogger txt_logger; |
38 static GaimLogLogger old_logger; | |
5872
059d95c67cda
[gaim-migrate @ 6304]
Christian Hammond <chipx86@chipx86.com>
parents:
5839
diff
changeset
|
39 |
8635 | 40 struct _gaim_logsize_user { |
41 char *name; | |
42 GaimAccount *account; | |
43 }; | |
44 static GHashTable *logsize_users = NULL; | |
45 | |
46 | |
7431 | 47 /************************************************************************** |
48 * PUBLIC LOGGING FUNCTIONS *********************************************** | |
49 **************************************************************************/ | |
4184 | 50 |
7431 | 51 GaimLog *gaim_log_new(GaimLogType type, const char *name, GaimAccount *account, time_t time) |
52 { | |
53 GaimLog *log = g_new0(GaimLog, 1); | |
8635 | 54 log->name = g_strdup(gaim_normalize(account, name)); |
7431 | 55 log->account = account; |
56 log->time = time; | |
8573 | 57 log->type = type; |
8096 | 58 log->logger_data = NULL; |
7431 | 59 log->logger = gaim_log_logger_get(); |
7440 | 60 if (log->logger && log->logger->create) |
61 log->logger->create(log); | |
7431 | 62 return log; |
4184 | 63 } |
64 | |
7431 | 65 void gaim_log_free(GaimLog *log) |
4184 | 66 { |
7431 | 67 g_return_if_fail(log); |
68 if (log->logger && log->logger->finalize) | |
69 log->logger->finalize(log); | |
70 g_free(log->name); | |
71 g_free(log); | |
72 } | |
7436 | 73 |
74 void gaim_log_write(GaimLog *log, GaimMessageFlags type, | |
7431 | 75 const char *from, time_t time, const char *message) |
76 { | |
8635 | 77 struct _gaim_logsize_user lu; |
78 | |
7431 | 79 g_return_if_fail(log); |
80 g_return_if_fail(log->logger); | |
7442 | 81 g_return_if_fail(log->logger->write); |
7431 | 82 |
8635 | 83 if ((log->type == GAIM_LOG_IM && |
84 gaim_prefs_get_bool("/core/logging/log_ims")) || | |
85 (log->type == GAIM_LOG_CHAT && | |
86 gaim_prefs_get_bool("/core/logging/log_chats")) || | |
87 (log->type == GAIM_LOG_SYSTEM && | |
88 gaim_prefs_get_bool("/core/logging/log_system"))) { | |
7553 | 89 (log->logger->write)(log, type, from, time, message); |
8635 | 90 lu.name = g_strdup(gaim_normalize(log->account, log->name)); |
91 lu.account = log->account; | |
92 g_hash_table_remove(logsize_users, &lu); | |
93 g_free(lu.name); | |
94 } | |
4184 | 95 } |
96 | |
7431 | 97 char *gaim_log_read(GaimLog *log, GaimLogReadFlags *flags) |
4184 | 98 { |
7542 | 99 GaimLogReadFlags mflags; |
7431 | 100 g_return_val_if_fail(log && log->logger, NULL); |
7462 | 101 if (log->logger->read) { |
7535 | 102 char *ret = (log->logger->read)(log, flags ? flags : &mflags); |
7478
3c21f3084ff0
[gaim-migrate @ 8091]
Herman Bloggs <hermanator12002@yahoo.com>
parents:
7473
diff
changeset
|
103 gaim_str_strip_cr(ret); |
7462 | 104 return ret; |
105 } | |
7470 | 106 return (_("<b><font color=\"red\">The logger has no read function</font></b>")); |
4184 | 107 } |
7616 | 108 |
7556 | 109 int gaim_log_get_size(GaimLog *log) |
110 { | |
111 g_return_val_if_fail(log && log->logger, 0); | |
8096 | 112 |
7556 | 113 if (log->logger->size) |
114 return log->logger->size(log); | |
115 return 0; | |
116 } | |
117 | |
8635 | 118 static guint _gaim_logsize_user_hash(struct _gaim_logsize_user *lu) |
119 { | |
120 return g_str_hash(lu->name); | |
121 } | |
122 | |
123 static guint _gaim_logsize_user_equal(struct _gaim_logsize_user *lu1, | |
124 struct _gaim_logsize_user *lu2) | |
125 { | |
126 return ((!strcmp(lu1->name, lu2->name)) && lu1->account == lu2->account); | |
127 } | |
128 | |
129 static void _gaim_logsize_user_free_key(struct _gaim_logsize_user *lu) | |
130 { | |
131 g_free(lu->name); | |
132 g_free(lu); | |
133 } | |
134 | |
8898 | 135 int gaim_log_get_total_size(GaimLogType type, const char *name, GaimAccount *account) |
7556 | 136 { |
8635 | 137 int size; |
8096 | 138 GSList *n; |
8635 | 139 struct _gaim_logsize_user *lu; |
8096 | 140 |
8635 | 141 lu = g_new(struct _gaim_logsize_user, 1); |
142 lu->name = g_strdup(gaim_normalize(account, name)); | |
143 lu->account = account; | |
144 | |
145 if((size = GPOINTER_TO_INT(g_hash_table_lookup(logsize_users, lu)))) { | |
146 g_free(lu->name); | |
147 g_free(lu); | |
148 } else { | |
149 for (n = loggers; n; n = n->next) { | |
150 GaimLogLogger *logger = n->data; | |
7616 | 151 |
8635 | 152 if(logger->total_size){ |
8898 | 153 size += (logger->total_size)(type, name, account); |
8635 | 154 } else if(logger->list) { |
8898 | 155 GList *logs = (logger->list)(type, name, account); |
8635 | 156 int this_size = 0; |
157 | |
158 while (logs) { | |
159 GList *logs2 = logs->next; | |
160 GaimLog *log = (GaimLog*)(logs->data); | |
161 this_size += gaim_log_get_size(log); | |
162 gaim_log_free(log); | |
163 g_list_free_1(logs); | |
164 logs = logs2; | |
165 } | |
166 | |
167 size += this_size; | |
8096 | 168 } |
8635 | 169 } |
8096 | 170 |
8635 | 171 g_hash_table_replace(logsize_users, lu, GINT_TO_POINTER(size)); |
7556 | 172 } |
173 return size; | |
174 } | |
4184 | 175 |
7431 | 176 /**************************************************************************** |
177 * LOGGER FUNCTIONS ********************************************************* | |
178 ****************************************************************************/ | |
4184 | 179 |
7431 | 180 static GaimLogLogger *current_logger = NULL; |
7436 | 181 |
7431 | 182 static void logger_pref_cb(const char *name, GaimPrefType type, |
183 gpointer value, gpointer data) | |
184 { | |
185 GaimLogLogger *logger; | |
186 GSList *l = loggers; | |
187 while (l) { | |
188 logger = l->data; | |
189 if (!strcmp(logger->id, value)) { | |
190 gaim_log_logger_set(logger); | |
191 return; | |
4184 | 192 } |
7431 | 193 l = l->next; |
194 } | |
195 gaim_log_logger_set(&txt_logger); | |
196 } | |
4184 | 197 |
198 | |
8898 | 199 GaimLogLogger *gaim_log_logger_new( |
200 void(*create)(GaimLog *), | |
201 void(*write)(GaimLog *, GaimMessageFlags, const char *, time_t, const char *), | |
202 void(*finalize)(GaimLog *), | |
203 GList*(*list)(GaimLogType type, const char*, GaimAccount*), | |
204 char*(*read)(GaimLog*, GaimLogReadFlags*), | |
205 int(*size)(GaimLog*)) | |
7431 | 206 { |
207 GaimLogLogger *logger = g_new0(GaimLogLogger, 1); | |
7440 | 208 logger->create = create; |
7431 | 209 logger->write = write; |
210 logger->finalize = finalize; | |
211 logger->list = list; | |
212 logger->read = read; | |
7556 | 213 logger->size = size; |
7431 | 214 return logger; |
4184 | 215 } |
216 | |
7431 | 217 void gaim_log_logger_free(GaimLogLogger *logger) |
4184 | 218 { |
7431 | 219 g_free(logger); |
220 } | |
4184 | 221 |
7431 | 222 void gaim_log_logger_add (GaimLogLogger *logger) |
223 { | |
224 g_return_if_fail(logger); | |
225 if (g_slist_find(loggers, logger)) | |
226 return; | |
227 loggers = g_slist_append(loggers, logger); | |
228 } | |
229 | |
230 void gaim_log_logger_remove (GaimLogLogger *logger) | |
231 { | |
232 g_return_if_fail(logger); | |
233 g_slist_remove(loggers, logger); | |
4184 | 234 } |
235 | |
7431 | 236 void gaim_log_logger_set (GaimLogLogger *logger) |
4184 | 237 { |
7431 | 238 g_return_if_fail(logger); |
239 current_logger = logger; | |
7436 | 240 } |
4184 | 241 |
7431 | 242 GaimLogLogger *gaim_log_logger_get() |
243 { | |
244 return current_logger; | |
245 } | |
4184 | 246 |
7431 | 247 GList *gaim_log_logger_get_options(void) |
248 { | |
249 GSList *n; | |
250 GList *list = NULL; | |
251 GaimLogLogger *data; | |
4184 | 252 |
7431 | 253 for (n = loggers; n; n = n->next) { |
254 data = n->data; | |
255 if (!data->write) | |
256 continue; | |
7494 | 257 list = g_list_append(list, _(data->name)); |
7431 | 258 list = g_list_append(list, data->id); |
4184 | 259 } |
260 | |
7431 | 261 return list; |
262 } | |
263 | |
8573 | 264 gint gaim_log_compare(gconstpointer y, gconstpointer z) |
7431 | 265 { |
7436 | 266 const GaimLog *a = y; |
267 const GaimLog *b = z; | |
268 | |
7431 | 269 return b->time - a->time; |
270 } | |
271 | |
8898 | 272 GList *gaim_log_get_logs(GaimLogType type, const char *name, GaimAccount *account) |
7431 | 273 { |
274 GList *logs = NULL; | |
275 GSList *n; | |
276 for (n = loggers; n; n = n->next) { | |
277 GaimLogLogger *logger = n->data; | |
278 if (!logger->list) | |
279 continue; | |
8898 | 280 logs = g_list_concat(logs, logger->list(type, name, account)); |
7431 | 281 } |
7436 | 282 |
8573 | 283 return g_list_sort(logs, gaim_log_compare); |
284 } | |
285 | |
286 GList *gaim_log_get_system_logs(GaimAccount *account) | |
287 { | |
288 GList *logs = NULL; | |
289 GSList *n; | |
290 for (n = loggers; n; n = n->next) { | |
291 GaimLogLogger *logger = n->data; | |
292 if (!logger->list_syslog) | |
293 continue; | |
294 logs = g_list_concat(logs, logger->list_syslog(account)); | |
295 } | |
296 | |
297 return g_list_sort(logs, gaim_log_compare); | |
7431 | 298 } |
299 | |
300 void gaim_log_init(void) | |
7436 | 301 { |
7431 | 302 gaim_prefs_add_none("/core/logging"); |
7555 | 303 gaim_prefs_add_bool("/core/logging/log_ims", FALSE); |
304 gaim_prefs_add_bool("/core/logging/log_chats", FALSE); | |
8573 | 305 gaim_prefs_add_bool("/core/logging/log_system", FALSE); |
306 gaim_prefs_add_bool("/core/logging/log_signon_signoff", FALSE); | |
307 gaim_prefs_add_bool("/core/logging/log_idle_state", FALSE); | |
308 gaim_prefs_add_bool("/core/logging/log_away_state", FALSE); | |
309 gaim_prefs_add_bool("/core/logging/log_own_states", FALSE); | |
310 | |
7431 | 311 gaim_prefs_add_string("/core/logging/format", "txt"); |
7457 | 312 gaim_log_logger_add(&html_logger); |
7431 | 313 gaim_log_logger_add(&txt_logger); |
314 gaim_log_logger_add(&old_logger); | |
315 gaim_prefs_connect_callback("/core/logging/format", | |
316 logger_pref_cb, NULL); | |
317 gaim_prefs_trigger_callback("/core/logging/format"); | |
8635 | 318 |
319 logsize_users = g_hash_table_new_full((GHashFunc)_gaim_logsize_user_hash, | |
320 (GEqualFunc)_gaim_logsize_user_equal, | |
321 (GDestroyNotify)_gaim_logsize_user_free_key, NULL); | |
7431 | 322 } |
323 | |
324 /**************************************************************************** | |
325 * LOGGERS ****************************************************************** | |
326 ****************************************************************************/ | |
327 | |
7616 | 328 struct generic_logger_data { |
329 char *path; | |
330 FILE *file; | |
331 }; | |
332 | |
8898 | 333 static GList *log_lister_common(GaimLogType type, const char *name, GaimAccount *account, const char *ext, GaimLogLogger *logger) |
7431 | 334 { |
335 GDir *dir; | |
336 GList *list = NULL; | |
7628 | 337 const char *filename; |
8111 | 338 char *me; |
339 const char *prpl; | |
340 char *path; | |
341 | |
342 if(!account) | |
343 return NULL; | |
344 | |
8898 | 345 if (type == GAIM_LOG_CHAT) |
346 me = g_strdup_printf("%s.chat", gaim_normalize(account, gaim_account_get_username(account))); | |
347 else | |
348 me = g_strdup(gaim_normalize(account, gaim_account_get_username(account))); | |
4184 | 349 |
7956 | 350 /* does this seem like a bad way to get this component of the path to anyone else? --Nathan */ |
8111 | 351 prpl = GAIM_PLUGIN_PROTOCOL_INFO |
7956 | 352 (gaim_find_prpl(gaim_account_get_protocol_id(account)))->list_icon(account, NULL); |
9500 | 353 if(type == GAIM_LOG_SYSTEM) |
354 path = g_build_filename(gaim_user_dir(),"logs", prpl, me, name, NULL); | |
355 else | |
356 path = g_build_filename(gaim_user_dir(),"logs", prpl, me, gaim_normalize(account, name), NULL); | |
7447 | 357 g_free(me); |
358 | |
7431 | 359 if (!(dir = g_dir_open(path, 0, NULL))) { |
360 g_free(path); | |
361 return NULL; | |
362 } | |
8898 | 363 |
7431 | 364 while ((filename = g_dir_read_name(dir))) { |
8577 | 365 if (gaim_str_has_suffix(filename, ext) && |
366 strlen(filename) == 17 + strlen(ext)) { | |
7431 | 367 GaimLog *log; |
7616 | 368 struct generic_logger_data *data; |
8577 | 369 time_t stamp = gaim_str_to_time(filename, FALSE); |
7431 | 370 |
8898 | 371 log = gaim_log_new(type, name, account, stamp); |
7431 | 372 log->logger = logger; |
7616 | 373 log->logger_data = data = g_new0(struct generic_logger_data, 1); |
374 data->path = g_build_filename(path, filename, NULL); | |
7431 | 375 list = g_list_append(list, log); |
4184 | 376 } |
377 } | |
7431 | 378 g_dir_close(dir); |
7447 | 379 g_free(path); |
7431 | 380 return list; |
381 } | |
4184 | 382 |
7556 | 383 /* Only to be used with logs listed from log_lister_common */ |
7616 | 384 int log_sizer_common(GaimLog *log) |
7556 | 385 { |
386 struct stat st; | |
7616 | 387 struct generic_logger_data *data = log->logger_data; |
7556 | 388 |
7616 | 389 if (!data->path || stat(data->path, &st)) |
7556 | 390 st.st_size = 0; |
391 | |
392 return st.st_size; | |
393 } | |
394 | |
7431 | 395 #if 0 /* Maybe some other time. */ |
7443 | 396 /**************** |
7431 | 397 ** XML LOGGER ** |
398 ****************/ | |
399 | |
400 static const char *str_from_msg_type (GaimMessageFlags type) | |
401 { | |
7443 | 402 |
7431 | 403 return ""; |
7443 | 404 |
7431 | 405 } |
406 | |
7443 | 407 static void xml_logger_write(GaimLog *log, |
408 GaimMessageFlags type, | |
7431 | 409 const char *from, time_t time, const char *message) |
410 { | |
411 char date[64]; | |
412 char *xhtml = NULL; | |
413 if (!log->logger_data) { | |
414 /* This log is new. We could use the loggers 'new' function, but | |
415 * creating a new file there would result in empty files in the case | |
416 * that you open a convo with someone, but don't say anything. | |
417 */ | |
418 char *ud = gaim_user_dir(); | |
419 char *guy = g_strdup(gaim_normalize(log->account, gaim_account_get_username(log->account))); | |
420 const char *prpl = GAIM_PLUGIN_PROTOCOL_INFO | |
421 (gaim_find_prpl(gaim_account_get_protocol(log->account)))->list_icon(log->account, NULL); | |
422 char *dir; | |
423 FILE *file; | |
424 | |
8898 | 425 if (log->type == GAIM_LOG_CHAT) { |
426 char *chat = g_strdup_printf("%s.chat", guy); | |
427 g_free(guy); | |
428 guy = chat; | |
429 } | |
430 | |
7453 | 431 strftime(date, sizeof(date), "%Y-%m-%d.%H%M%S.xml", localtime(&log->time)); |
7443 | 432 |
433 dir = g_build_filename(ud, "logs", | |
7431 | 434 prpl, guy, gaim_normalize(log->account, log->name), NULL); |
7612 | 435 gaim_build_dir (dir, S_IRUSR | S_IWUSR | S_IXUSR); |
7447 | 436 g_free(guy); |
7443 | 437 |
7431 | 438 char *filename = g_build_filename(dir, date, NULL); |
439 g_free(dir); | |
7443 | 440 |
7431 | 441 log->logger_data = fopen(filename, "a"); |
442 if (!log->logger_data) { | |
443 gaim_debug(GAIM_DEBUG_ERROR, "log", "Could not create log file %s\n", filename); | |
7564 | 444 g_free(filename); |
7431 | 445 return; |
446 } | |
7564 | 447 g_free(filename); |
7431 | 448 fprintf(log->logger_data, "<?xml version='1.0' encoding='UTF-8' ?>\n" |
449 "<?xml-stylesheet href='file:///usr/src/web/htdocs/log-stylesheet.xsl' type='text/xml' ?>\n"); | |
7443 | 450 |
7453 | 451 strftime(date, sizeof(date), "%Y-%m-%d %H:%M:%S", localtime(&log->time)); |
7431 | 452 fprintf(log->logger_data, "<conversation time='%s' screenname='%s' protocol='%s'>\n", |
453 date, log->name, prpl); | |
454 } | |
7443 | 455 |
7453 | 456 strftime(date, sizeof(date), "%H:%M:%S", localtime(&time)); |
7431 | 457 gaim_markup_html_to_xhtml(message, &xhtml, NULL); |
458 if (from) | |
7443 | 459 fprintf(log->logger_data, "<message %s %s from='%s' time='%s'>%s</message>\n", |
460 str_from_msg_type(type), | |
7431 | 461 type & GAIM_MESSAGE_SEND ? "direction='sent'" : |
462 type & GAIM_MESSAGE_RECV ? "direction='received'" : "", | |
463 from, date, xhtml); | |
464 else | |
7443 | 465 fprintf(log->logger_data, "<message %s %s time='%s'>%s</message>\n", |
466 str_from_msg_type(type), | |
7431 | 467 type & GAIM_MESSAGE_SEND ? "direction='sent'" : |
468 type & GAIM_MESSAGE_RECV ? "direction='received'" : "", | |
7443 | 469 date, xhtml): |
7431 | 470 fflush(log->logger_data); |
471 g_free(xhtml); | |
7443 | 472 } |
473 | |
7431 | 474 static void xml_logger_finalize(GaimLog *log) |
475 { | |
476 if (log->logger_data) { | |
477 fprintf(log->logger_data, "</conversation>\n"); | |
478 fclose(log->logger_data); | |
479 log->logger_data = NULL; | |
480 } | |
481 } | |
7443 | 482 |
8898 | 483 static GList *xml_logger_list(GaimLogType type, const char *sn, GaimAccount *account) |
7431 | 484 { |
8898 | 485 return log_lister_common(type, sn, account, ".xml", &xml_logger); |
4184 | 486 } |
487 | |
7431 | 488 static GaimLogLogger xml_logger = { |
489 N_("XML"), "xml", | |
490 NULL, | |
491 xml_logger_write, | |
492 xml_logger_finalize, | |
493 xml_logger_list, | |
8096 | 494 NULL, |
7431 | 495 NULL |
496 }; | |
497 #endif | |
5563
9eb5b13fd412
[gaim-migrate @ 5965]
Christian Hammond <chipx86@chipx86.com>
parents:
5560
diff
changeset
|
498 |
7431 | 499 /**************************** |
7457 | 500 ** HTML LOGGER ************* |
501 ****************************/ | |
502 | |
503 static void html_logger_write(GaimLog *log, GaimMessageFlags type, | |
504 const char *from, time_t time, const char *message) | |
505 { | |
506 char date[64]; | |
7882 | 507 char *msg_fixed; |
7616 | 508 struct generic_logger_data *data = log->logger_data; |
9613 | 509 GaimPlugin *plugin = gaim_find_prpl(gaim_account_get_protocol_id(log->account)); |
510 const char *prpl_name = plugin->info->name; | |
511 | |
7618 | 512 if(!data) { |
7457 | 513 /* This log is new */ |
514 char *ud = gaim_user_dir(); | |
515 char *guy = g_strdup(gaim_normalize(log->account, gaim_account_get_username(log->account))); | |
7553 | 516 char *chat; |
9613 | 517 const char *prpl = GAIM_PLUGIN_PROTOCOL_INFO(plugin)->list_icon(log->account, NULL); |
7457 | 518 char *dir; |
519 char *filename; | |
520 | |
7553 | 521 if (log->type == GAIM_LOG_CHAT) { |
522 chat = g_strdup_printf("%s.chat", guy); | |
523 g_free(guy); | |
524 guy = chat; | |
525 } | |
526 | |
7457 | 527 strftime(date, sizeof(date), "%Y-%m-%d.%H%M%S.html", localtime(&log->time)); |
528 | |
529 dir = g_build_filename(ud, "logs", | |
530 prpl, guy, gaim_normalize(log->account, log->name), NULL); | |
7612 | 531 gaim_build_dir (dir, S_IRUSR | S_IWUSR | S_IXUSR); |
7457 | 532 g_free(guy); |
533 | |
534 filename = g_build_filename(dir, date, NULL); | |
535 g_free(dir); | |
536 | |
7616 | 537 log->logger_data = data = g_new0(struct generic_logger_data, 1); |
538 | |
539 data->file = fopen(filename, "a"); | |
540 if (!data->file) { | |
7623 | 541 gaim_debug(GAIM_DEBUG_ERROR, "log", |
542 "Could not create log file %s\n", filename); | |
7564 | 543 g_free(filename); |
7457 | 544 return; |
545 } | |
546 g_free(filename); | |
547 strftime(date, sizeof(date), "%Y-%m-%d %H:%M:%S", localtime(&log->time)); | |
7616 | 548 fprintf(data->file, "<html><head><title>"); |
549 fprintf(data->file, "Conversation with %s at %s on %s (%s)", | |
7457 | 550 log->name, date, gaim_account_get_username(log->account), prpl); |
7616 | 551 fprintf(data->file, "</title></head><body>"); |
552 fprintf(data->file, | |
7457 | 553 "<h3>Conversation with %s at %s on %s (%s)</h3>\n", |
554 log->name, date, gaim_account_get_username(log->account), prpl); | |
555 } | |
7623 | 556 |
557 /* if we can't write to the file, give up before we hurt ourselves */ | |
558 if(!data->file) | |
559 return; | |
560 | |
7882 | 561 gaim_markup_html_to_xhtml(message, &msg_fixed, NULL); |
562 | |
8577 | 563 if(log->type == GAIM_LOG_SYSTEM){ |
9592 | 564 strftime(date, sizeof(date), "%Y-%m-%d %H:%M:%S", localtime(&time)); |
8577 | 565 fprintf(data->file, "---- %s @ %s ----<br/>\n", msg_fixed, date); |
566 } else { | |
567 strftime(date, sizeof(date), "%H:%M:%S", localtime(&time)); | |
568 if (type & GAIM_MESSAGE_SYSTEM) | |
569 fprintf(data->file, "<font size=\"2\">(%s)</font><b> %s</b><br/>\n", date, msg_fixed); | |
570 else if (type & GAIM_MESSAGE_WHISPER) | |
571 fprintf(data->file, "<font color=\"#6C2585\"><font size=\"2\">(%s)</font><b> %s:</b></font> %s<br/>\n", | |
572 date, from, msg_fixed); | |
573 else if (type & GAIM_MESSAGE_AUTO_RESP) { | |
574 if (type & GAIM_MESSAGE_SEND) | |
575 fprintf(data->file, _("<font color=\"#16569E\"><font size=\"2\">(%s)</font> <b>%s <AUTO-REPLY>:</b></font> %s<br/>\n"), date, from, msg_fixed); | |
576 else if (type & GAIM_MESSAGE_RECV) | |
577 fprintf(data->file, _("<font color=\"#A82F2F\"><font size=\"2\">(%s)</font> <b>%s <AUTO-REPLY>:</b></font> %s<br/>\n"), date, from, msg_fixed); | |
578 } else if (type & GAIM_MESSAGE_RECV) { | |
579 if(gaim_message_meify(msg_fixed, -1)) | |
580 fprintf(data->file, "<font color=\"#6C2585\"><font size=\"2\">(%s)</font> <b>***%s</b></font> <font sml=\"%s\">%s</font><br/>\n", | |
9613 | 581 date, from, prpl_name, msg_fixed); |
8577 | 582 else |
583 fprintf(data->file, "<font color=\"#A82F2F\"><font size=\"2\">(%s)</font> <b>%s:</b></font> <font sml=\"%s\">%s</font><br/>\n", | |
9613 | 584 date, from, prpl_name, msg_fixed); |
8577 | 585 } else if (type & GAIM_MESSAGE_SEND) { |
586 if(gaim_message_meify(msg_fixed, -1)) | |
587 fprintf(data->file, "<font color=\"#6C2585\"><font size=\"2\">(%s)</font> <b>***%s</b></font> <font sml=\"%s\">%s</font><br/>\n", | |
9613 | 588 date, from, prpl_name, msg_fixed); |
8577 | 589 else |
590 fprintf(data->file, "<font color=\"#16569E\"><font size=\"2\">(%s)</font> <b>%s:</b></font> <font sml=\"%s\">%s</font><br/>\n", | |
9613 | 591 date, from, prpl_name, msg_fixed); |
8577 | 592 } |
7564 | 593 } |
8573 | 594 |
7882 | 595 g_free(msg_fixed); |
7616 | 596 fflush(data->file); |
7457 | 597 } |
598 | |
599 static void html_logger_finalize(GaimLog *log) | |
600 { | |
7616 | 601 struct generic_logger_data *data = log->logger_data; |
602 if (data) { | |
603 if(data->file) { | |
604 fprintf(data->file, "</body></html>"); | |
605 fclose(data->file); | |
606 } | |
607 g_free(data->path); | |
7752 | 608 g_free(data); |
7463 | 609 } |
7457 | 610 } |
611 | |
8898 | 612 static GList *html_logger_list(GaimLogType type, const char *sn, GaimAccount *account) |
7457 | 613 { |
8898 | 614 return log_lister_common(type, sn, account, ".html", &html_logger); |
7457 | 615 } |
616 | |
8573 | 617 static GList *html_logger_list_syslog(GaimAccount *account) |
618 { | |
8898 | 619 return log_lister_common(GAIM_LOG_SYSTEM, ".system", account, ".html", &html_logger); |
8573 | 620 } |
621 | |
7457 | 622 static char *html_logger_read(GaimLog *log, GaimLogReadFlags *flags) |
623 { | |
624 char *read, *minus_header; | |
7616 | 625 struct generic_logger_data *data = log->logger_data; |
7457 | 626 *flags = GAIM_LOG_READ_NO_NEWLINE; |
7616 | 627 if (!data || !data->path) |
628 return g_strdup(_("<font color=\"red\"><b>Unable to find log path!</b></font>")); | |
629 if (g_file_get_contents(data->path, &read, NULL, NULL)) { | |
7457 | 630 minus_header = strchr(read, '\n'); |
631 if (!minus_header) | |
632 minus_header = g_strdup(read); | |
633 else | |
634 minus_header = g_strdup(minus_header + 1); | |
635 g_free(read); | |
636 return minus_header; | |
637 } | |
8578 | 638 return g_strdup_printf(_("<font color=\"red\"><b>Could not read file: %s</b></font>"), data->path); |
7457 | 639 } |
640 | |
8573 | 641 static void html_logger_create(GaimLog *log) |
642 { | |
643 if(log->type == GAIM_LOG_SYSTEM){ | |
644 char date[64]; | |
645 const char *prpl = GAIM_PLUGIN_PROTOCOL_INFO | |
646 (gaim_find_prpl(gaim_account_get_protocol_id(log->account)))->list_icon(log->account, NULL); | |
647 char *ud = gaim_user_dir(); | |
648 char *dir = g_build_filename(ud, "logs", prpl, log->name, ".system", NULL); | |
649 char *filename; | |
650 struct generic_logger_data *data; | |
651 | |
652 gaim_build_dir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
653 strftime(date, sizeof(date), "%Y-%m-%d.%H%M%S.html", localtime(&log->time)); | |
654 filename = g_build_filename(dir, date, NULL); | |
655 g_free(dir); | |
656 | |
657 log->logger_data = data = g_new0(struct generic_logger_data, 1); | |
658 | |
659 data->file = fopen(filename, "a"); | |
660 if (!data->file) { | |
661 gaim_debug(GAIM_DEBUG_ERROR, "log", | |
662 "Could not create log file %s\n", filename); | |
663 g_free(filename); | |
664 return; | |
665 } | |
666 fprintf(data->file, "<html><head><title>"); | |
667 fprintf(data->file, "System Log for %s (%s)", | |
668 gaim_account_get_username(log->account), prpl); | |
669 fprintf(data->file, "</title></head><body>"); | |
670 g_free(filename); | |
671 } | |
672 } | |
673 | |
7457 | 674 static GaimLogLogger html_logger = { |
675 N_("HTML"), "html", | |
8573 | 676 html_logger_create, |
7457 | 677 html_logger_write, |
678 html_logger_finalize, | |
679 html_logger_list, | |
7556 | 680 html_logger_read, |
8096 | 681 log_sizer_common, |
8573 | 682 NULL, |
683 html_logger_list_syslog | |
7457 | 684 }; |
685 | |
686 | |
687 | |
688 | |
689 /**************************** | |
7431 | 690 ** PLAIN TEXT LOGGER ******* |
691 ****************************/ | |
4184 | 692 |
7436 | 693 static void txt_logger_write(GaimLog *log, |
694 GaimMessageFlags type, | |
7431 | 695 const char *from, time_t time, const char *message) |
696 { | |
697 char date[64]; | |
698 char *stripped = NULL; | |
7616 | 699 struct generic_logger_data *data = log->logger_data; |
700 if (!data) { | |
7431 | 701 /* This log is new. We could use the loggers 'new' function, but |
702 * creating a new file there would result in empty files in the case | |
703 * that you open a convo with someone, but don't say anything. | |
8573 | 704 * |
8898 | 705 * The log is also not a system log. Because if it is, data would |
706 * be created in txt_logger_create | |
7431 | 707 */ |
708 char *ud = gaim_user_dir(); | |
709 char *guy = g_strdup(gaim_normalize(log->account, gaim_account_get_username(log->account))); | |
7553 | 710 char *chat; |
7431 | 711 const char *prpl = GAIM_PLUGIN_PROTOCOL_INFO |
7956 | 712 (gaim_find_prpl(gaim_account_get_protocol_id(log->account)))->list_icon(log->account, NULL); |
7431 | 713 char *dir; |
8898 | 714 char *filename; |
7436 | 715 |
7553 | 716 if (log->type == GAIM_LOG_CHAT) { |
717 chat = g_strdup_printf("%s.chat", guy); | |
718 g_free(guy); | |
719 guy = chat; | |
720 } | |
8898 | 721 |
7453 | 722 strftime(date, sizeof(date), "%Y-%m-%d.%H%M%S.txt", localtime(&log->time)); |
7436 | 723 |
724 dir = g_build_filename(ud, "logs", | |
7431 | 725 prpl, guy, gaim_normalize(log->account, log->name), NULL); |
7612 | 726 gaim_build_dir (dir, S_IRUSR | S_IWUSR | S_IXUSR); |
7447 | 727 g_free(guy); |
7436 | 728 |
7473 | 729 filename = g_build_filename(dir, date, NULL); |
7431 | 730 g_free(dir); |
7436 | 731 |
7616 | 732 log->logger_data = data = g_new0(struct generic_logger_data, 1); |
733 | |
734 data->file = fopen(filename, "a"); | |
735 if (!data->file) { | |
7431 | 736 gaim_debug(GAIM_DEBUG_ERROR, "log", "Could not create log file %s\n", filename); |
7564 | 737 g_free(filename); |
7431 | 738 return; |
4184 | 739 } |
7447 | 740 g_free(filename); |
7453 | 741 strftime(date, sizeof(date), "%Y-%m-%d %H:%M:%S", localtime(&log->time)); |
7616 | 742 fprintf(data->file, "Conversation with %s at %s on %s (%s)\n", |
7431 | 743 log->name, date, gaim_account_get_username(log->account), prpl); |
744 } | |
7436 | 745 |
7623 | 746 /* if we can't write to the file, give up before we hurt ourselves */ |
747 if(!data->file) | |
748 return; | |
749 | |
8573 | 750 stripped = gaim_markup_strip_html(message); |
751 | |
752 if(log->type == GAIM_LOG_SYSTEM){ | |
9592 | 753 strftime(date, sizeof(date), "%Y-%m-%d %H:%M:%S", localtime(&time)); |
8573 | 754 fprintf(data->file, "---- %s @ %s ----\n", stripped, date); |
755 } else { | |
756 strftime(date, sizeof(date), "%H:%M:%S", localtime(&time)); | |
757 if (type & GAIM_MESSAGE_SEND || | |
758 type & GAIM_MESSAGE_RECV) { | |
759 if (type & GAIM_MESSAGE_AUTO_RESP) { | |
760 fprintf(data->file, _("(%s) %s <AUTO-REPLY>: %s\n"), date, | |
761 from, stripped); | |
762 } else { | |
763 if(gaim_message_meify(stripped, -1)) | |
764 fprintf(data->file, "(%s) ***%s %s\n", date, from, | |
765 stripped); | |
766 else | |
767 fprintf(data->file, "(%s) %s: %s\n", date, from, | |
768 stripped); | |
769 } | |
770 } else if (type & GAIM_MESSAGE_SYSTEM) | |
771 fprintf(data->file, "(%s) %s\n", date, stripped); | |
772 else if (type & GAIM_MESSAGE_NO_LOG) { | |
773 /* This shouldn't happen */ | |
774 g_free(stripped); | |
775 return; | |
776 } else if (type & GAIM_MESSAGE_WHISPER) | |
777 fprintf(data->file, "(%s) *%s* %s", date, from, stripped); | |
778 else | |
779 fprintf(data->file, "(%s) %s%s %s\n", date, from ? from : "", | |
780 from ? ":" : "", stripped); | |
781 } | |
782 | |
783 fflush(data->file); | |
784 g_free(stripped); | |
7431 | 785 } |
786 | |
787 static void txt_logger_finalize(GaimLog *log) | |
788 { | |
7616 | 789 struct generic_logger_data *data = log->logger_data; |
790 if (data) { | |
791 if(data->file) | |
792 fclose(data->file); | |
793 if(data->path) | |
794 g_free(data->path); | |
7752 | 795 g_free(data); |
7616 | 796 } |
7431 | 797 } |
798 | |
8898 | 799 static GList *txt_logger_list(GaimLogType type, const char *sn, GaimAccount *account) |
7431 | 800 { |
8898 | 801 return log_lister_common(type, sn, account, ".txt", &txt_logger); |
7431 | 802 } |
803 | |
8573 | 804 static GList *txt_logger_list_syslog(GaimAccount *account) |
805 { | |
8898 | 806 return log_lister_common(GAIM_LOG_SYSTEM, ".system", account, ".txt", &txt_logger); |
8573 | 807 } |
808 | |
7431 | 809 static char *txt_logger_read(GaimLog *log, GaimLogReadFlags *flags) |
810 { | |
8517 | 811 char *read, *minus_header, *minus_header2; |
7616 | 812 struct generic_logger_data *data = log->logger_data; |
7457 | 813 *flags = 0; |
7616 | 814 if (!data || !data->path) |
815 return g_strdup(_("<font color=\"red\"><b>Unable to find log path!</b></font>")); | |
816 if (g_file_get_contents(data->path, &read, NULL, NULL)) { | |
7431 | 817 minus_header = strchr(read, '\n'); |
818 if (!minus_header) | |
819 minus_header = g_strdup(read); | |
7436 | 820 else |
7431 | 821 minus_header = g_strdup(minus_header + 1); |
822 g_free(read); | |
8517 | 823 minus_header2 = gaim_escape_html(minus_header); |
824 g_free(minus_header); | |
825 return minus_header2; | |
7431 | 826 } |
8578 | 827 return g_strdup_printf(_("<font color=\"red\"><b>Could not read file: %s</b></font>"), data->path); |
7436 | 828 } |
7431 | 829 |
8573 | 830 static void txt_logger_create(GaimLog *log) |
831 { | |
832 if(log->type == GAIM_LOG_SYSTEM){ | |
833 char date[64]; | |
834 const char *prpl = GAIM_PLUGIN_PROTOCOL_INFO | |
835 (gaim_find_prpl(gaim_account_get_protocol_id(log->account)))->list_icon(log->account, NULL); | |
836 char *ud = gaim_user_dir(); | |
837 char *dir = g_build_filename(ud, "logs", prpl, log->name, ".system", NULL); | |
838 char *filename; | |
839 struct generic_logger_data *data; | |
840 | |
841 gaim_build_dir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
842 strftime(date, sizeof(date), "%Y-%m-%d.%H%M%S.txt", localtime(&log->time)); | |
843 filename = g_build_filename(dir, date, NULL); | |
844 g_free(dir); | |
845 | |
846 log->logger_data = data = g_new0(struct generic_logger_data, 1); | |
847 | |
848 data->file = fopen(filename, "a"); | |
849 if (!data->file) { | |
850 gaim_debug(GAIM_DEBUG_ERROR, "log", | |
851 "Could not create log file %s\n", filename); | |
852 g_free(filename); | |
853 return; | |
854 } | |
855 g_free(filename); | |
856 } | |
857 } | |
858 | |
7431 | 859 static GaimLogLogger txt_logger = { |
860 N_("Plain text"), "txt", | |
8573 | 861 txt_logger_create, |
7431 | 862 txt_logger_write, |
863 txt_logger_finalize, | |
864 txt_logger_list, | |
7556 | 865 txt_logger_read, |
8096 | 866 log_sizer_common, |
8573 | 867 NULL, |
868 txt_logger_list_syslog | |
7431 | 869 }; |
870 | |
871 /**************** | |
872 * OLD LOGGER *** | |
873 ****************/ | |
874 | |
875 /* The old logger doesn't write logs, only reads them. This is to include | |
876 * old logs in the log viewer transparently. | |
877 */ | |
878 | |
879 struct old_logger_data { | |
7764 | 880 GaimStringref *pathref; |
7431 | 881 int offset; |
882 int length; | |
883 }; | |
884 | |
8898 | 885 static GList *old_logger_list(GaimLogType type, const char *sn, GaimAccount *account) |
7431 | 886 { |
887 FILE *file; | |
888 char buf[BUF_LONG]; | |
889 struct tm tm; | |
7761 | 890 char month[4]; |
7431 | 891 struct old_logger_data *data = NULL; |
892 char *logfile = g_strdup_printf("%s.log", gaim_normalize(account, sn)); | |
7764 | 893 char *pathstr = g_build_filename(gaim_user_dir(), "logs", logfile, NULL); |
894 GaimStringref *pathref = gaim_stringref_new(pathstr); | |
7431 | 895 char *newlog; |
7761 | 896 int logfound = 0; |
897 int lastoff = 0; | |
898 int newlen; | |
7791 | 899 time_t lasttime = 0; |
7431 | 900 |
901 GaimLog *log = NULL; | |
902 GList *list = NULL; | |
903 | |
7473 | 904 g_free(logfile); |
7764 | 905 g_free(pathstr); |
7473 | 906 |
7764 | 907 if (!(file = fopen(gaim_stringref_value(pathref), "rb"))) { |
908 gaim_stringref_unref(pathref); | |
7431 | 909 return NULL; |
7447 | 910 } |
7436 | 911 |
7431 | 912 while (fgets(buf, BUF_LONG, file)) { |
913 if ((newlog = strstr(buf, "---- New C"))) { | |
914 int length; | |
915 int offset; | |
916 char convostart[32]; | |
917 char *temp = strchr(buf, '@'); | |
7436 | 918 |
7431 | 919 if (temp == NULL || strlen(temp) < 2) |
920 continue; | |
7436 | 921 |
7431 | 922 temp++; |
923 length = strcspn(temp, "-"); | |
924 if (length > 31) length = 31; | |
7436 | 925 |
7431 | 926 offset = ftell(file); |
7436 | 927 |
7761 | 928 if (logfound) { |
929 newlen = offset - lastoff - length; | |
7436 | 930 if(strstr(buf, "----</H3><BR>")) { |
7761 | 931 newlen -= |
932 sizeof("<HR><BR><H3 Align=Center> ---- New Conversation @ ") + | |
933 sizeof("----</H3><BR>") - 2; | |
7436 | 934 } else { |
7761 | 935 newlen -= |
936 sizeof("---- New Conversation @ ") + sizeof("----") - 2; | |
7436 | 937 } |
938 | |
7461 | 939 if(strchr(buf, '\r')) |
7770 | 940 newlen--; |
7461 | 941 |
7761 | 942 if (newlen != 0) { |
943 log = gaim_log_new(GAIM_LOG_IM, sn, account, -1); | |
944 log->logger = &old_logger; | |
945 log->time = lasttime; | |
946 data = g_new0(struct old_logger_data, 1); | |
947 data->offset = lastoff; | |
948 data->length = newlen; | |
7764 | 949 data->pathref = gaim_stringref_ref(pathref); |
7761 | 950 log->logger_data = data; |
7431 | 951 list = g_list_append(list, log); |
7761 | 952 } |
7431 | 953 } |
954 | |
7761 | 955 logfound = 1; |
956 lastoff = offset; | |
7436 | 957 |
7431 | 958 g_snprintf(convostart, length, "%s", temp); |
7676 | 959 sscanf(convostart, "%*s %s %d %d:%d:%d %d", |
960 month, &tm.tm_mday, &tm.tm_hour, &tm.tm_min, &tm.tm_sec, &tm.tm_year); | |
961 /* Ugly hack, in case current locale is not English */ | |
962 if (strcmp(month, "Jan") == 0) { | |
963 tm.tm_mon= 0; | |
964 } else if (strcmp(month, "Feb") == 0) { | |
965 tm.tm_mon = 1; | |
966 } else if (strcmp(month, "Mar") == 0) { | |
967 tm.tm_mon = 2; | |
968 } else if (strcmp(month, "Apr") == 0) { | |
969 tm.tm_mon = 3; | |
970 } else if (strcmp(month, "May") == 0) { | |
971 tm.tm_mon = 4; | |
972 } else if (strcmp(month, "Jun") == 0) { | |
973 tm.tm_mon = 5; | |
974 } else if (strcmp(month, "Jul") == 0) { | |
975 tm.tm_mon = 6; | |
976 } else if (strcmp(month, "Aug") == 0) { | |
977 tm.tm_mon = 7; | |
978 } else if (strcmp(month, "Sep") == 0) { | |
979 tm.tm_mon = 8; | |
980 } else if (strcmp(month, "Oct") == 0) { | |
981 tm.tm_mon = 9; | |
982 } else if (strcmp(month, "Nov") == 0) { | |
983 tm.tm_mon = 10; | |
984 } else if (strcmp(month, "Dec") == 0) { | |
985 tm.tm_mon = 11; | |
986 } | |
987 tm.tm_year -= 1900; | |
7761 | 988 lasttime = mktime(&tm); |
4184 | 989 } |
990 } | |
7613 | 991 |
7761 | 992 if (logfound) { |
993 if ((newlen = ftell(file) - lastoff) != 0) { | |
994 log = gaim_log_new(GAIM_LOG_IM, sn, account, -1); | |
995 log->logger = &old_logger; | |
996 log->time = lasttime; | |
997 data = g_new0(struct old_logger_data, 1); | |
998 data->offset = lastoff; | |
999 data->length = newlen; | |
7764 | 1000 data->pathref = gaim_stringref_ref(pathref); |
7761 | 1001 log->logger_data = data; |
7613 | 1002 list = g_list_append(list, log); |
7761 | 1003 } |
7613 | 1004 } |
1005 | |
7764 | 1006 gaim_stringref_unref(pathref); |
7431 | 1007 fclose(file); |
1008 return list; | |
4184 | 1009 } |
4359
5fb47ec9bfe4
[gaim-migrate @ 4625]
Christian Hammond <chipx86@chipx86.com>
parents:
4227
diff
changeset
|
1010 |
8898 | 1011 static int old_logger_total_size(GaimLogType type, const char *name, GaimAccount *account) |
8096 | 1012 { |
1013 char *logfile = g_strdup_printf("%s.log", gaim_normalize(account, name)); | |
1014 char *pathstr = g_build_filename(gaim_user_dir(), "logs", logfile, NULL); | |
1015 int size; | |
1016 struct stat st; | |
1017 | |
1018 if (stat(pathstr, &st)) | |
1019 size = 0; | |
1020 else | |
1021 size = st.st_size; | |
1022 | |
1023 g_free(logfile); | |
1024 g_free(pathstr); | |
1025 | |
1026 return size; | |
1027 } | |
1028 | |
7616 | 1029 static char * old_logger_read (GaimLog *log, GaimLogReadFlags *flags) |
4359
5fb47ec9bfe4
[gaim-migrate @ 4625]
Christian Hammond <chipx86@chipx86.com>
parents:
4227
diff
changeset
|
1030 { |
7431 | 1031 struct old_logger_data *data = log->logger_data; |
7764 | 1032 FILE *file = fopen(gaim_stringref_value(data->pathref), "rb"); |
7431 | 1033 char *read = g_malloc(data->length + 1); |
1034 fseek(file, data->offset, SEEK_SET); | |
1035 fread(read, data->length, 1, file); | |
8370 | 1036 fclose(file); |
7431 | 1037 read[data->length] = '\0'; |
7436 | 1038 *flags = 0; |
1039 if(strstr(read, "<BR>")) | |
1040 *flags |= GAIM_LOG_READ_NO_NEWLINE; | |
7431 | 1041 return read; |
1042 } | |
4359
5fb47ec9bfe4
[gaim-migrate @ 4625]
Christian Hammond <chipx86@chipx86.com>
parents:
4227
diff
changeset
|
1043 |
7616 | 1044 static int old_logger_size (GaimLog *log) |
7556 | 1045 { |
1046 struct old_logger_data *data = log->logger_data; | |
7616 | 1047 return data ? data->length : 0; |
1048 } | |
1049 | |
1050 static void old_logger_finalize(GaimLog *log) | |
1051 { | |
1052 struct old_logger_data *data = log->logger_data; | |
7764 | 1053 gaim_stringref_unref(data->pathref); |
7616 | 1054 g_free(data); |
7556 | 1055 } |
1056 | |
7431 | 1057 static GaimLogLogger old_logger = { |
1058 "old logger", "old", | |
7616 | 1059 NULL, NULL, |
1060 old_logger_finalize, | |
7431 | 1061 old_logger_list, |
7616 | 1062 old_logger_read, |
8096 | 1063 old_logger_size, |
8573 | 1064 old_logger_total_size, |
1065 NULL | |
7431 | 1066 }; |