Mercurial > pidgin
comparison src/ft.c @ 9785:2356d2153c94
[gaim-migrate @ 10653]
Dave West made us check errno and give better file related errors for
file transfers.
He also added some information to the xfer dialog, like the protocol
and account name.
He also made the initial status of xfers added to the dialog be "waiting
for transfer to start"
committer: Tailor Script <tailor@pidgin.im>
author | Tim Ringenbach <marv@pidgin.im> |
---|---|
date | Thu, 19 Aug 2004 22:46:08 +0000 |
parents | 3cd8143b84b8 |
children | 1e9ecca6c97e |
comparison
equal
deleted
inserted
replaced
9784:d7cc09a9da4c | 9785:2356d2153c94 |
---|---|
105 | 105 |
106 if (xfer->ref == 0) | 106 if (xfer->ref == 0) |
107 gaim_xfer_destroy(xfer); | 107 gaim_xfer_destroy(xfer); |
108 } | 108 } |
109 | 109 |
110 static void gaim_xfer_show_file_error(const char *filename) | |
111 { | |
112 char *msg = NULL; | |
113 | |
114 switch(errno) | |
115 { | |
116 case ENOENT: | |
117 msg = g_strdup_printf(_("%s does not exist.\n"), filename); | |
118 break; | |
119 case EISDIR: | |
120 msg = g_strdup_printf(_("%s is a directory, not a file.\n"), filename); | |
121 break; | |
122 case ENOTDIR: | |
123 msg = g_strdup_printf( _("A component of %s is not a directory.\n"), filename); | |
124 break; | |
125 case ELOOP: | |
126 msg = g_strdup_printf( _("Too many symbolic links in path for %s\n"), filename); | |
127 break; | |
128 case EACCES: | |
129 msg = g_strdup_printf( _("Permission denied accessing %s\n"), filename); | |
130 break; | |
131 case ENAMETOOLONG: | |
132 msg = g_strdup_printf(_("File name too long: %s\n"), filename); | |
133 break; | |
134 case EROFS: | |
135 msg = g_strdup_printf(_("Cannot write %s: Read only filesystem\n"), filename); | |
136 break; | |
137 case ENOSPC: | |
138 msg = g_strdup_printf(_("Cannot write %s: No space on filesystem\n"), filename); | |
139 break; | |
140 case ETXTBSY: | |
141 msg = g_strdup_printf(_("Cannot write %s: File is in use\n"), filename); | |
142 break; | |
143 case EMFILE: | |
144 msg = g_strdup_printf(_("Cannot open %s: Gaim has too many files open\n"), filename); | |
145 break; | |
146 case ENFILE: | |
147 msg = g_strdup_printf(_("Cannot open %s: Your user or system has too many files open\n"), filename); | |
148 break; | |
149 case ENOMEM: | |
150 msg = g_strdup_printf(_("Cannot open %s: Not enough memory\n"), filename); | |
151 break; | |
152 default: | |
153 msg = NULL; | |
154 break; | |
155 } | |
156 | |
157 if( msg != NULL ) { | |
158 gaim_notify_error(NULL, NULL, msg, NULL); | |
159 g_free(msg); | |
160 } | |
161 } | |
162 | |
110 static void | 163 static void |
111 gaim_xfer_choose_file_ok_cb(void *user_data, const char *filename) | 164 gaim_xfer_choose_file_ok_cb(void *user_data, const char *filename) |
112 { | 165 { |
113 GaimXfer *xfer; | 166 GaimXfer *xfer; |
114 struct stat st; | 167 struct stat st; |
119 /* File not found. */ | 172 /* File not found. */ |
120 if (gaim_xfer_get_type(xfer) == GAIM_XFER_RECEIVE) { | 173 if (gaim_xfer_get_type(xfer) == GAIM_XFER_RECEIVE) { |
121 gaim_xfer_request_accepted(xfer, filename); | 174 gaim_xfer_request_accepted(xfer, filename); |
122 } | 175 } |
123 else { | 176 else { |
124 gaim_notify_error(NULL, NULL, | 177 gaim_xfer_show_file_error(filename); |
125 _("That file does not exist."), NULL); | |
126 | |
127 gaim_xfer_request_denied(xfer); | 178 gaim_xfer_request_denied(xfer); |
128 } | 179 } |
129 } | 180 } |
130 else if ((gaim_xfer_get_type(xfer) == GAIM_XFER_SEND) && | 181 else if ((gaim_xfer_get_type(xfer) == GAIM_XFER_SEND) && |
131 (st.st_size == 0)) { | 182 (st.st_size == 0)) { |
133 gaim_notify_error(NULL, NULL, | 184 gaim_notify_error(NULL, NULL, |
134 _("Cannot send a file of 0 bytes."), NULL); | 185 _("Cannot send a file of 0 bytes."), NULL); |
135 | 186 |
136 gaim_xfer_request_denied(xfer); | 187 gaim_xfer_request_denied(xfer); |
137 } | 188 } |
189 else if ((gaim_xfer_get_type(xfer) == GAIM_XFER_SEND) && | |
190 S_ISDIR(st.st_mode)) { | |
191 /* | |
192 * XXX - Sending a directory should be valid for some protocols. | |
193 */ | |
194 gaim_notify_error(NULL, NULL, | |
195 _("Cannot send a directory."), NULL); | |
196 | |
197 gaim_xfer_request_denied(xfer); | |
198 } | |
199 else if ((gaim_xfer_get_type(xfer) == GAIM_XFER_RECEIVE) && | |
200 S_ISDIR(st.st_mode)) { | |
201 char *msg = g_strdup_printf( | |
202 _("%s is not a regular file. Cowardly refusing to overwrite it.\n"), filename); | |
203 gaim_notify_error(NULL, NULL, msg, NULL); | |
204 g_free(msg); | |
205 gaim_xfer_request_denied(xfer); | |
206 } | |
138 else { | 207 else { |
139 if (S_ISDIR(st.st_mode)) { | 208 gaim_xfer_request_accepted(xfer, filename); |
140 /* | |
141 * XXX - Sending a directory should be valid for some protocols. | |
142 */ | |
143 gaim_xfer_request_denied(xfer); | |
144 } | |
145 else if (gaim_xfer_get_type(xfer) == GAIM_XFER_RECEIVE) { | |
146 gaim_xfer_request_accepted(xfer, filename); | |
147 } | |
148 else { | |
149 gaim_xfer_request_accepted(xfer, filename); | |
150 } | |
151 } | 209 } |
152 | 210 |
153 gaim_xfer_unref(xfer); | 211 gaim_xfer_unref(xfer); |
154 } | 212 } |
155 | 213 |
263 | 321 |
264 void | 322 void |
265 gaim_xfer_request_accepted(GaimXfer *xfer, const char *filename) | 323 gaim_xfer_request_accepted(GaimXfer *xfer, const char *filename) |
266 { | 324 { |
267 GaimXferType type; | 325 GaimXferType type; |
326 struct stat st; | |
268 | 327 |
269 if (xfer == NULL) | 328 if (xfer == NULL) |
270 return; | 329 return; |
271 | 330 |
272 type = gaim_xfer_get_type(xfer); | 331 type = gaim_xfer_get_type(xfer); |
276 xfer->ops.init(xfer); | 335 xfer->ops.init(xfer); |
277 return; | 336 return; |
278 } | 337 } |
279 | 338 |
280 if (type == GAIM_XFER_SEND) { | 339 if (type == GAIM_XFER_SEND) { |
281 struct stat sb; | |
282 | |
283 /* Check the filename. */ | 340 /* Check the filename. */ |
284 if (g_strrstr(filename, "..")) { | 341 if (g_strrstr(filename, "..")) { |
285 char *msg; | 342 char *msg; |
286 | 343 |
287 msg = g_strdup_printf(_("%s is not a valid filename.\n"), | 344 msg = g_strdup_printf(_("%s is not a valid filename.\n"), |
292 g_free(msg); | 349 g_free(msg); |
293 gaim_xfer_unref(xfer); | 350 gaim_xfer_unref(xfer); |
294 return; | 351 return; |
295 } | 352 } |
296 | 353 |
297 if (stat(filename, &sb) == -1) { | 354 if (stat(filename, &st) == -1) { |
298 char *msg; | 355 gaim_xfer_show_file_error(filename); |
299 | |
300 msg = g_strdup_printf(_("%s was not found.\n"), filename); | |
301 | |
302 gaim_xfer_error(type, xfer->who, msg); | |
303 | |
304 g_free(msg); | |
305 gaim_xfer_unref(xfer); | 356 gaim_xfer_unref(xfer); |
306 return; | 357 return; |
307 } | 358 } |
308 | 359 |
309 gaim_xfer_set_local_filename(xfer, filename); | 360 gaim_xfer_set_local_filename(xfer, filename); |
310 gaim_xfer_set_size(xfer, sb.st_size); | 361 gaim_xfer_set_size(xfer, st.st_size); |
311 } | 362 } |
312 else { | 363 else { |
313 /* TODO: Sanity checks and file overwrite checks. */ | 364 xfer->status = GAIM_XFER_STATUS_ACCEPTED; |
314 | |
315 gaim_xfer_set_local_filename(xfer, filename); | 365 gaim_xfer_set_local_filename(xfer, filename); |
316 } | 366 } |
317 | 367 |
318 xfer->ops.init(xfer); | 368 xfer->ops.init(xfer); |
319 gaim_xfer_add(xfer); | 369 gaim_xfer_add(xfer); |
708 static void | 758 static void |
709 begin_transfer(GaimXfer *xfer, GaimInputCondition cond) | 759 begin_transfer(GaimXfer *xfer, GaimInputCondition cond) |
710 { | 760 { |
711 GaimXferType type = gaim_xfer_get_type(xfer); | 761 GaimXferType type = gaim_xfer_get_type(xfer); |
712 | 762 |
713 /* | |
714 * We'll have already tried to open this earlier to make sure we can | |
715 * read/write here. Should be safe. | |
716 */ | |
717 xfer->dest_fp = fopen(gaim_xfer_get_local_filename(xfer), | 763 xfer->dest_fp = fopen(gaim_xfer_get_local_filename(xfer), |
718 type == GAIM_XFER_RECEIVE ? "wb" : "rb"); | 764 type == GAIM_XFER_RECEIVE ? "wb" : "rb"); |
719 | 765 |
720 /* Just in case, though. */ | |
721 if (xfer->dest_fp == NULL) { | 766 if (xfer->dest_fp == NULL) { |
722 gaim_xfer_cancel_local(xfer); /* ? */ | 767 gaim_xfer_show_file_error(gaim_xfer_get_local_filename(xfer)); |
768 gaim_xfer_cancel_local(xfer); | |
723 return; | 769 return; |
724 } | 770 } |
725 | 771 |
726 xfer->watcher = gaim_input_add(xfer->fd, cond, transfer_cb, xfer); | 772 xfer->watcher = gaim_input_add(xfer->fd, cond, transfer_cb, xfer); |
727 | 773 |