zipruby 0.1.0 → 0.1.1
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of zipruby might be problematic. Click here for more details.
- data/ext/zipruby.h +1 -1
- data/ext/zipruby_archive.c +178 -21
- data/ext/zipruby_file.c +2 -2
- data/zipruby.c +180 -23
- metadata +1 -1
data/ext/zipruby.h
CHANGED
data/ext/zipruby_archive.c
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
#include <errno.h>
|
2
|
+
|
1
3
|
#include "zip.h"
|
2
4
|
#include "zipruby.h"
|
3
5
|
#include "zipruby_archive.h"
|
@@ -15,10 +17,13 @@ static VALUE zipruby_archive_get_stat(int argc, VALUE *argv, VALUE self);
|
|
15
17
|
static VALUE zipruby_archive_add_buffer(VALUE self, VALUE name, VALUE source);
|
16
18
|
static VALUE zipruby_archive_add_file(int argc, VALUE *argv, VALUE self);
|
17
19
|
static VALUE zipruby_archive_add_filep(int argc, VALUE *argv, VALUE self);
|
18
|
-
static VALUE zipruby_archive_add_zip(VALUE self, VALUE srcarchive);
|
19
20
|
static VALUE zipruby_archive_replace_buffer(VALUE self, VALUE index, VALUE source);
|
20
21
|
static VALUE zipruby_archive_replace_file(VALUE self, VALUE index, VALUE fname);
|
21
22
|
static VALUE zipruby_archive_replace_filep(VALUE self, VALUE index, VALUE file);
|
23
|
+
static VALUE zipruby_archive_add_or_replace_buffer(VALUE self, VALUE name, VALUE source);
|
24
|
+
static VALUE zipruby_archive_add_or_replace_file(int argc, VALUE *argv, VALUE self);
|
25
|
+
static VALUE zipruby_archive_add_or_replace_filep(int argc, VALUE *argv, VALUE self);
|
26
|
+
static VALUE zipruby_archive_update(VALUE self, VALUE srcarchive);
|
22
27
|
static VALUE zipruby_archive_get_comment(int argc, VALUE *argv, VALUE self);
|
23
28
|
static VALUE zipruby_archive_set_comment(VALUE self, VALUE comment);
|
24
29
|
static VALUE zipruby_archive_locate_name(int argc, VALUE *argv, VALUE self);
|
@@ -51,10 +56,13 @@ void Init_zipruby_archive() {
|
|
51
56
|
rb_define_method(Archive, "add_buffer", zipruby_archive_add_buffer, 2);
|
52
57
|
rb_define_method(Archive, "add_file", zipruby_archive_add_file, -1);
|
53
58
|
rb_define_method(Archive, "add_filep", zipruby_archive_add_filep, -1);
|
54
|
-
rb_define_method(Archive, "add_zip", zipruby_archive_add_zip, 1);
|
55
59
|
rb_define_method(Archive, "replace_buffer", zipruby_archive_replace_buffer, 2);
|
56
60
|
rb_define_method(Archive, "replace_file", zipruby_archive_replace_file, 2);
|
57
61
|
rb_define_method(Archive, "replace_filep", zipruby_archive_replace_filep, 2);
|
62
|
+
rb_define_method(Archive, "add_or_replace_buffer", zipruby_archive_add_or_replace_buffer, 2);
|
63
|
+
rb_define_method(Archive, "add_or_replace_file", zipruby_archive_add_or_replace_file, -1);
|
64
|
+
rb_define_method(Archive, "add_or_replace_filep", zipruby_archive_add_or_replace_filep, -1);
|
65
|
+
rb_define_method(Archive, "update", zipruby_archive_update, 1);
|
58
66
|
rb_define_method(Archive, "<<", zipruby_archive_add_filep, -1);
|
59
67
|
rb_define_method(Archive, "get_comment", zipruby_archive_get_comment, -1);
|
60
68
|
rb_define_method(Archive, "comment", zipruby_archive_get_comment, -1);
|
@@ -173,7 +181,7 @@ static VALUE zipruby_archive_get_name(int argc, VALUE *argv, VALUE self) {
|
|
173
181
|
Check_Archive(p_archive);
|
174
182
|
|
175
183
|
if ((name = zip_get_name(p_archive->archive, NUM2INT(index), i_flags)) == NULL) {
|
176
|
-
rb_raise(Error, "Get name failed: %s", zip_strerror(p_archive->archive));
|
184
|
+
rb_raise(Error, "Get name failed at %d: %s", index, zip_strerror(p_archive->archive));
|
177
185
|
}
|
178
186
|
|
179
187
|
return (name != NULL) ? rb_str_new2(name) : Qnil;
|
@@ -279,6 +287,24 @@ static VALUE zipruby_archive_replace_buffer(VALUE self, VALUE index, VALUE sourc
|
|
279
287
|
return Qnil;
|
280
288
|
}
|
281
289
|
|
290
|
+
/* */
|
291
|
+
static VALUE zipruby_archive_add_or_replace_buffer(VALUE self, VALUE name, VALUE source) {
|
292
|
+
struct zipruby_archive *p_archive;
|
293
|
+
int index;
|
294
|
+
|
295
|
+
Check_Type(name, T_STRING);
|
296
|
+
Data_Get_Struct(self, struct zipruby_archive, p_archive);
|
297
|
+
Check_Archive(p_archive);
|
298
|
+
|
299
|
+
index = zip_name_locate(p_archive->archive, StringValuePtr(name), ZIP_FL_NOCASE);
|
300
|
+
|
301
|
+
if (index >= 0) {
|
302
|
+
return zipruby_archive_replace_buffer(self, INT2NUM(index), source);
|
303
|
+
} else {
|
304
|
+
return zipruby_archive_add_buffer(self, name, source);
|
305
|
+
}
|
306
|
+
}
|
307
|
+
|
282
308
|
/* */
|
283
309
|
static VALUE zipruby_archive_add_file(int argc, VALUE *argv, VALUE self) {
|
284
310
|
VALUE name, fname;
|
@@ -287,18 +313,18 @@ static VALUE zipruby_archive_add_file(int argc, VALUE *argv, VALUE self) {
|
|
287
313
|
|
288
314
|
rb_scan_args(argc, argv, "11", &name, &fname);
|
289
315
|
|
290
|
-
|
291
316
|
if (NIL_P(fname)) {
|
292
317
|
fname = name;
|
293
318
|
name = Qnil;
|
294
319
|
}
|
295
320
|
|
321
|
+
Check_Type(fname, T_STRING);
|
322
|
+
|
296
323
|
if (NIL_P(name)) {
|
297
324
|
name = rb_funcall(rb_cFile, rb_intern("basename"), 1, fname);
|
298
325
|
}
|
299
326
|
|
300
327
|
Check_Type(name, T_STRING);
|
301
|
-
Check_Type(fname, T_STRING);
|
302
328
|
Data_Get_Struct(self, struct zipruby_archive, p_archive);
|
303
329
|
Check_Archive(p_archive);
|
304
330
|
|
@@ -340,6 +366,38 @@ static VALUE zipruby_archive_replace_file(VALUE self, VALUE index, VALUE fname)
|
|
340
366
|
return Qnil;
|
341
367
|
}
|
342
368
|
|
369
|
+
/* */
|
370
|
+
static VALUE zipruby_archive_add_or_replace_file(int argc, VALUE *argv, VALUE self) {
|
371
|
+
VALUE name, fname;
|
372
|
+
struct zipruby_archive *p_archive;
|
373
|
+
int index;
|
374
|
+
|
375
|
+
rb_scan_args(argc, argv, "11", &name, &fname);
|
376
|
+
|
377
|
+
if (NIL_P(fname)) {
|
378
|
+
fname = name;
|
379
|
+
name = Qnil;
|
380
|
+
}
|
381
|
+
|
382
|
+
Check_Type(fname, T_STRING);
|
383
|
+
|
384
|
+
if (NIL_P(name)) {
|
385
|
+
name = rb_funcall(rb_cFile, rb_intern("basename"), 1, fname);
|
386
|
+
}
|
387
|
+
|
388
|
+
Check_Type(name, T_STRING);
|
389
|
+
Data_Get_Struct(self, struct zipruby_archive, p_archive);
|
390
|
+
Check_Archive(p_archive);
|
391
|
+
|
392
|
+
index = zip_name_locate(p_archive->archive, StringValuePtr(name), ZIP_FL_NOCASE);
|
393
|
+
|
394
|
+
if (index >= 0) {
|
395
|
+
return zipruby_archive_replace_file(self, INT2NUM(index), fname);
|
396
|
+
} else {
|
397
|
+
return zipruby_archive_add_file(argc, argv, self);
|
398
|
+
}
|
399
|
+
}
|
400
|
+
|
343
401
|
/* */
|
344
402
|
static VALUE zipruby_archive_add_filep(int argc, VALUE *argv, VALUE self) {
|
345
403
|
VALUE name, file, source;
|
@@ -373,31 +431,40 @@ static VALUE zipruby_archive_replace_filep(VALUE self, VALUE index, VALUE file)
|
|
373
431
|
}
|
374
432
|
|
375
433
|
/* */
|
376
|
-
static VALUE
|
377
|
-
VALUE
|
434
|
+
static VALUE zipruby_archive_add_or_replace_filep(int argc, VALUE *argv, VALUE self) {
|
435
|
+
VALUE name, file;
|
378
436
|
struct zipruby_archive *p_archive;
|
379
|
-
|
380
|
-
int lenp, i_flags = 0;
|
437
|
+
int index;
|
381
438
|
|
382
|
-
rb_scan_args(argc, argv, "
|
439
|
+
rb_scan_args(argc, argv, "11", &name, &file);
|
383
440
|
|
384
|
-
if (
|
385
|
-
|
441
|
+
if (NIL_P(file)) {
|
442
|
+
file = name;
|
443
|
+
name = Qnil;
|
444
|
+
}
|
445
|
+
|
446
|
+
Check_Type(file, T_FILE);
|
447
|
+
|
448
|
+
if (NIL_P(name)) {
|
449
|
+
name = rb_funcall(rb_cFile, rb_intern("basename"), 1, rb_funcall(file, rb_intern("path"), 0));
|
386
450
|
}
|
387
451
|
|
452
|
+
Check_Type(name, T_STRING);
|
388
453
|
Data_Get_Struct(self, struct zipruby_archive, p_archive);
|
389
454
|
Check_Archive(p_archive);
|
390
455
|
|
391
|
-
|
392
|
-
comment = zip_get_archive_comment(p_archive->archive, &lenp, i_flags);
|
456
|
+
index = zip_name_locate(p_archive->archive, StringValuePtr(name), ZIP_FL_NOCASE);
|
393
457
|
|
394
|
-
|
458
|
+
if (index >= 0) {
|
459
|
+
return zipruby_archive_replace_filep(self, INT2NUM(index), file);
|
460
|
+
} else {
|
461
|
+
return zipruby_archive_add_filep(argc, argv, self);
|
462
|
+
}
|
395
463
|
}
|
396
464
|
|
397
465
|
/* */
|
398
|
-
static VALUE
|
466
|
+
static VALUE zipruby_archive_update(VALUE self, VALUE srcarchive) {
|
399
467
|
struct zipruby_archive *p_archive, *p_srcarchive;
|
400
|
-
struct zip_source *zsource;
|
401
468
|
int i, num_files;
|
402
469
|
|
403
470
|
if (!rb_obj_is_instance_of(srcarchive, Archive)) {
|
@@ -412,21 +479,111 @@ static VALUE zipruby_archive_add_zip(VALUE self, VALUE srcarchive) {
|
|
412
479
|
num_files = zip_get_num_files(p_srcarchive->archive);
|
413
480
|
|
414
481
|
for (i = 0; i < num_files; i++) {
|
415
|
-
|
416
|
-
|
482
|
+
struct zip_source *zsource;
|
483
|
+
struct zip_file *fzip;
|
484
|
+
struct zip_stat sb;
|
485
|
+
char *buf;
|
486
|
+
const char *name;
|
487
|
+
int index, error;
|
488
|
+
|
489
|
+
zip_stat_init(&sb);
|
490
|
+
|
491
|
+
if (zip_stat_index(p_srcarchive->archive, i, 0, &sb)) {
|
492
|
+
zip_unchange_all(p_archive->archive);
|
493
|
+
zip_unchange_archive(p_archive->archive);
|
494
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_srcarchive->archive));
|
495
|
+
}
|
496
|
+
|
497
|
+
if ((buf = malloc(sb.size)) == NULL) {
|
498
|
+
zip_unchange_all(p_archive->archive);
|
499
|
+
zip_unchange_archive(p_archive->archive);
|
500
|
+
rb_raise(rb_eRuntimeError, "Update archive failed: Cannot allocate memory");
|
501
|
+
}
|
502
|
+
|
503
|
+
fzip = zip_fopen_index(p_srcarchive->archive, i, 0);
|
504
|
+
|
505
|
+
if (fzip == NULL) {
|
506
|
+
free(buf);
|
507
|
+
zip_unchange_all(p_archive->archive);
|
508
|
+
zip_unchange_archive(p_archive->archive);
|
509
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_srcarchive->archive));
|
510
|
+
}
|
511
|
+
|
512
|
+
if (zip_fread(fzip, buf, sb.size) == -1) {
|
513
|
+
free(buf);
|
514
|
+
zip_fclose(fzip);
|
515
|
+
zip_unchange_all(p_archive->archive);
|
516
|
+
zip_unchange_archive(p_archive->archive);
|
517
|
+
rb_raise(Error, "Update archive failed: %s", zip_file_strerror(fzip));
|
518
|
+
}
|
519
|
+
|
520
|
+
if ((error = zip_fclose(fzip)) != 0) {
|
521
|
+
char errstr[ERRSTR_BUFSIZE];
|
522
|
+
free(buf);
|
523
|
+
zip_unchange_all(p_archive->archive);
|
524
|
+
zip_unchange_archive(p_archive->archive);
|
525
|
+
zip_error_to_str(errstr, ERRSTR_BUFSIZE, error, errno);
|
526
|
+
rb_raise(Error, "Update archive failed: %s", errstr);
|
527
|
+
}
|
528
|
+
|
529
|
+
if ((zsource = zip_source_buffer(p_archive->archive, buf, sb.size, 1)) == NULL) {
|
530
|
+
free(buf);
|
531
|
+
zip_unchange_all(p_archive->archive);
|
532
|
+
zip_unchange_archive(p_archive->archive);
|
533
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_archive->archive));
|
417
534
|
}
|
418
535
|
|
419
|
-
if (
|
536
|
+
if ((name = zip_get_name(p_srcarchive->archive, i, 0)) == NULL) {
|
420
537
|
zip_source_free(zsource);
|
421
538
|
zip_unchange_all(p_archive->archive);
|
422
539
|
zip_unchange_archive(p_archive->archive);
|
423
|
-
rb_raise(Error, "
|
540
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_srcarchive->archive));
|
541
|
+
}
|
542
|
+
|
543
|
+
index = zip_name_locate(p_archive->archive, name, ZIP_FL_NOCASE);
|
544
|
+
|
545
|
+
if (index >= 0) {
|
546
|
+
if (zip_replace(p_archive->archive, i, zsource) == -1) {
|
547
|
+
zip_source_free(zsource);
|
548
|
+
zip_unchange_all(p_archive->archive);
|
549
|
+
zip_unchange_archive(p_archive->archive);
|
550
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_archive->archive));
|
551
|
+
}
|
552
|
+
} else {
|
553
|
+
if (zip_add(p_archive->archive, name, zsource) == -1) {
|
554
|
+
zip_source_free(zsource);
|
555
|
+
zip_unchange_all(p_archive->archive);
|
556
|
+
zip_unchange_archive(p_archive->archive);
|
557
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_archive->archive));
|
558
|
+
}
|
424
559
|
}
|
425
560
|
}
|
426
561
|
|
427
562
|
return Qnil;
|
428
563
|
}
|
429
564
|
|
565
|
+
/* */
|
566
|
+
static VALUE zipruby_archive_get_comment(int argc, VALUE *argv, VALUE self) {
|
567
|
+
VALUE flags;
|
568
|
+
struct zipruby_archive *p_archive;
|
569
|
+
const char *comment;
|
570
|
+
int lenp, i_flags = 0;
|
571
|
+
|
572
|
+
rb_scan_args(argc, argv, "01", &flags);
|
573
|
+
|
574
|
+
if (!NIL_P(flags)) {
|
575
|
+
i_flags = NUM2INT(flags);
|
576
|
+
}
|
577
|
+
|
578
|
+
Data_Get_Struct(self, struct zipruby_archive, p_archive);
|
579
|
+
Check_Archive(p_archive);
|
580
|
+
|
581
|
+
// XXX: How is the error checked?
|
582
|
+
comment = zip_get_archive_comment(p_archive->archive, &lenp, i_flags);
|
583
|
+
|
584
|
+
return comment ? rb_str_new(comment, lenp) : Qnil;
|
585
|
+
}
|
586
|
+
|
430
587
|
/* */
|
431
588
|
static VALUE zipruby_archive_set_comment(VALUE self, VALUE comment) {
|
432
589
|
struct zipruby_archive *p_archive;
|
data/ext/zipruby_file.c
CHANGED
@@ -124,7 +124,7 @@ static VALUE zipruby_file_initialize(int argc, VALUE *argv, VALUE self) {
|
|
124
124
|
fzip = zip_fopen_index(p_archive->archive, i_index, i_flags);
|
125
125
|
|
126
126
|
if (fzip == NULL) {
|
127
|
-
rb_raise(Error, "Open file failed at %d", i_index, zip_strerror(p_archive->archive));
|
127
|
+
rb_raise(Error, "Open file failed at %d: %s", i_index, zip_strerror(p_archive->archive));
|
128
128
|
}
|
129
129
|
}
|
130
130
|
|
@@ -149,8 +149,8 @@ static VALUE zipruby_file_close(VALUE self) {
|
|
149
149
|
|
150
150
|
if ((error = zip_fclose(p_file->file)) != 0) {
|
151
151
|
char errstr[ERRSTR_BUFSIZE];
|
152
|
-
zip_error_to_str(errstr, ERRSTR_BUFSIZE, error, errno);
|
153
152
|
zip_unchange(p_file->archive, p_file->sb->index);
|
153
|
+
zip_error_to_str(errstr, ERRSTR_BUFSIZE, error, errno);
|
154
154
|
rb_raise(Error, "Close file failed: %s", errstr);
|
155
155
|
}
|
156
156
|
|
data/zipruby.c
CHANGED
@@ -17,6 +17,8 @@ void Init_zipruby() {
|
|
17
17
|
Init_zipruby_stat();
|
18
18
|
Init_zipruby_error();
|
19
19
|
}
|
20
|
+
#include <errno.h>
|
21
|
+
|
20
22
|
#include "zip.h"
|
21
23
|
#include "zipruby.h"
|
22
24
|
#include "zipruby_archive.h"
|
@@ -34,10 +36,13 @@ static VALUE zipruby_archive_get_stat(int argc, VALUE *argv, VALUE self);
|
|
34
36
|
static VALUE zipruby_archive_add_buffer(VALUE self, VALUE name, VALUE source);
|
35
37
|
static VALUE zipruby_archive_add_file(int argc, VALUE *argv, VALUE self);
|
36
38
|
static VALUE zipruby_archive_add_filep(int argc, VALUE *argv, VALUE self);
|
37
|
-
static VALUE zipruby_archive_add_zip(VALUE self, VALUE srcarchive);
|
38
39
|
static VALUE zipruby_archive_replace_buffer(VALUE self, VALUE index, VALUE source);
|
39
40
|
static VALUE zipruby_archive_replace_file(VALUE self, VALUE index, VALUE fname);
|
40
41
|
static VALUE zipruby_archive_replace_filep(VALUE self, VALUE index, VALUE file);
|
42
|
+
static VALUE zipruby_archive_add_or_replace_buffer(VALUE self, VALUE name, VALUE source);
|
43
|
+
static VALUE zipruby_archive_add_or_replace_file(int argc, VALUE *argv, VALUE self);
|
44
|
+
static VALUE zipruby_archive_add_or_replace_filep(int argc, VALUE *argv, VALUE self);
|
45
|
+
static VALUE zipruby_archive_update(VALUE self, VALUE srcarchive);
|
41
46
|
static VALUE zipruby_archive_get_comment(int argc, VALUE *argv, VALUE self);
|
42
47
|
static VALUE zipruby_archive_set_comment(VALUE self, VALUE comment);
|
43
48
|
static VALUE zipruby_archive_locate_name(int argc, VALUE *argv, VALUE self);
|
@@ -70,10 +75,13 @@ void Init_zipruby_archive() {
|
|
70
75
|
rb_define_method(Archive, "add_buffer", zipruby_archive_add_buffer, 2);
|
71
76
|
rb_define_method(Archive, "add_file", zipruby_archive_add_file, -1);
|
72
77
|
rb_define_method(Archive, "add_filep", zipruby_archive_add_filep, -1);
|
73
|
-
rb_define_method(Archive, "add_zip", zipruby_archive_add_zip, 1);
|
74
78
|
rb_define_method(Archive, "replace_buffer", zipruby_archive_replace_buffer, 2);
|
75
79
|
rb_define_method(Archive, "replace_file", zipruby_archive_replace_file, 2);
|
76
80
|
rb_define_method(Archive, "replace_filep", zipruby_archive_replace_filep, 2);
|
81
|
+
rb_define_method(Archive, "add_or_replace_buffer", zipruby_archive_add_or_replace_buffer, 2);
|
82
|
+
rb_define_method(Archive, "add_or_replace_file", zipruby_archive_add_or_replace_file, -1);
|
83
|
+
rb_define_method(Archive, "add_or_replace_filep", zipruby_archive_add_or_replace_filep, -1);
|
84
|
+
rb_define_method(Archive, "update", zipruby_archive_update, 1);
|
77
85
|
rb_define_method(Archive, "<<", zipruby_archive_add_filep, -1);
|
78
86
|
rb_define_method(Archive, "get_comment", zipruby_archive_get_comment, -1);
|
79
87
|
rb_define_method(Archive, "comment", zipruby_archive_get_comment, -1);
|
@@ -192,7 +200,7 @@ static VALUE zipruby_archive_get_name(int argc, VALUE *argv, VALUE self) {
|
|
192
200
|
Check_Archive(p_archive);
|
193
201
|
|
194
202
|
if ((name = zip_get_name(p_archive->archive, NUM2INT(index), i_flags)) == NULL) {
|
195
|
-
rb_raise(Error, "Get name failed: %s", zip_strerror(p_archive->archive));
|
203
|
+
rb_raise(Error, "Get name failed at %d: %s", index, zip_strerror(p_archive->archive));
|
196
204
|
}
|
197
205
|
|
198
206
|
return (name != NULL) ? rb_str_new2(name) : Qnil;
|
@@ -298,6 +306,24 @@ static VALUE zipruby_archive_replace_buffer(VALUE self, VALUE index, VALUE sourc
|
|
298
306
|
return Qnil;
|
299
307
|
}
|
300
308
|
|
309
|
+
/* */
|
310
|
+
static VALUE zipruby_archive_add_or_replace_buffer(VALUE self, VALUE name, VALUE source) {
|
311
|
+
struct zipruby_archive *p_archive;
|
312
|
+
int index;
|
313
|
+
|
314
|
+
Check_Type(name, T_STRING);
|
315
|
+
Data_Get_Struct(self, struct zipruby_archive, p_archive);
|
316
|
+
Check_Archive(p_archive);
|
317
|
+
|
318
|
+
index = zip_name_locate(p_archive->archive, StringValuePtr(name), ZIP_FL_NOCASE);
|
319
|
+
|
320
|
+
if (index >= 0) {
|
321
|
+
return zipruby_archive_replace_buffer(self, INT2NUM(index), source);
|
322
|
+
} else {
|
323
|
+
return zipruby_archive_add_buffer(self, name, source);
|
324
|
+
}
|
325
|
+
}
|
326
|
+
|
301
327
|
/* */
|
302
328
|
static VALUE zipruby_archive_add_file(int argc, VALUE *argv, VALUE self) {
|
303
329
|
VALUE name, fname;
|
@@ -306,18 +332,18 @@ static VALUE zipruby_archive_add_file(int argc, VALUE *argv, VALUE self) {
|
|
306
332
|
|
307
333
|
rb_scan_args(argc, argv, "11", &name, &fname);
|
308
334
|
|
309
|
-
|
310
335
|
if (NIL_P(fname)) {
|
311
336
|
fname = name;
|
312
337
|
name = Qnil;
|
313
338
|
}
|
314
339
|
|
340
|
+
Check_Type(fname, T_STRING);
|
341
|
+
|
315
342
|
if (NIL_P(name)) {
|
316
343
|
name = rb_funcall(rb_cFile, rb_intern("basename"), 1, fname);
|
317
344
|
}
|
318
345
|
|
319
346
|
Check_Type(name, T_STRING);
|
320
|
-
Check_Type(fname, T_STRING);
|
321
347
|
Data_Get_Struct(self, struct zipruby_archive, p_archive);
|
322
348
|
Check_Archive(p_archive);
|
323
349
|
|
@@ -359,6 +385,38 @@ static VALUE zipruby_archive_replace_file(VALUE self, VALUE index, VALUE fname)
|
|
359
385
|
return Qnil;
|
360
386
|
}
|
361
387
|
|
388
|
+
/* */
|
389
|
+
static VALUE zipruby_archive_add_or_replace_file(int argc, VALUE *argv, VALUE self) {
|
390
|
+
VALUE name, fname;
|
391
|
+
struct zipruby_archive *p_archive;
|
392
|
+
int index;
|
393
|
+
|
394
|
+
rb_scan_args(argc, argv, "11", &name, &fname);
|
395
|
+
|
396
|
+
if (NIL_P(fname)) {
|
397
|
+
fname = name;
|
398
|
+
name = Qnil;
|
399
|
+
}
|
400
|
+
|
401
|
+
Check_Type(fname, T_STRING);
|
402
|
+
|
403
|
+
if (NIL_P(name)) {
|
404
|
+
name = rb_funcall(rb_cFile, rb_intern("basename"), 1, fname);
|
405
|
+
}
|
406
|
+
|
407
|
+
Check_Type(name, T_STRING);
|
408
|
+
Data_Get_Struct(self, struct zipruby_archive, p_archive);
|
409
|
+
Check_Archive(p_archive);
|
410
|
+
|
411
|
+
index = zip_name_locate(p_archive->archive, StringValuePtr(name), ZIP_FL_NOCASE);
|
412
|
+
|
413
|
+
if (index >= 0) {
|
414
|
+
return zipruby_archive_replace_file(self, INT2NUM(index), fname);
|
415
|
+
} else {
|
416
|
+
return zipruby_archive_add_file(argc, argv, self);
|
417
|
+
}
|
418
|
+
}
|
419
|
+
|
362
420
|
/* */
|
363
421
|
static VALUE zipruby_archive_add_filep(int argc, VALUE *argv, VALUE self) {
|
364
422
|
VALUE name, file, source;
|
@@ -392,31 +450,40 @@ static VALUE zipruby_archive_replace_filep(VALUE self, VALUE index, VALUE file)
|
|
392
450
|
}
|
393
451
|
|
394
452
|
/* */
|
395
|
-
static VALUE
|
396
|
-
VALUE
|
453
|
+
static VALUE zipruby_archive_add_or_replace_filep(int argc, VALUE *argv, VALUE self) {
|
454
|
+
VALUE name, file;
|
397
455
|
struct zipruby_archive *p_archive;
|
398
|
-
|
399
|
-
int lenp, i_flags = 0;
|
456
|
+
int index;
|
400
457
|
|
401
|
-
rb_scan_args(argc, argv, "
|
458
|
+
rb_scan_args(argc, argv, "11", &name, &file);
|
402
459
|
|
403
|
-
if (
|
404
|
-
|
460
|
+
if (NIL_P(file)) {
|
461
|
+
file = name;
|
462
|
+
name = Qnil;
|
463
|
+
}
|
464
|
+
|
465
|
+
Check_Type(file, T_FILE);
|
466
|
+
|
467
|
+
if (NIL_P(name)) {
|
468
|
+
name = rb_funcall(rb_cFile, rb_intern("basename"), 1, rb_funcall(file, rb_intern("path"), 0));
|
405
469
|
}
|
406
470
|
|
471
|
+
Check_Type(name, T_STRING);
|
407
472
|
Data_Get_Struct(self, struct zipruby_archive, p_archive);
|
408
473
|
Check_Archive(p_archive);
|
409
474
|
|
410
|
-
|
411
|
-
comment = zip_get_archive_comment(p_archive->archive, &lenp, i_flags);
|
475
|
+
index = zip_name_locate(p_archive->archive, StringValuePtr(name), ZIP_FL_NOCASE);
|
412
476
|
|
413
|
-
|
477
|
+
if (index >= 0) {
|
478
|
+
return zipruby_archive_replace_filep(self, INT2NUM(index), file);
|
479
|
+
} else {
|
480
|
+
return zipruby_archive_add_filep(argc, argv, self);
|
481
|
+
}
|
414
482
|
}
|
415
483
|
|
416
484
|
/* */
|
417
|
-
static VALUE
|
485
|
+
static VALUE zipruby_archive_update(VALUE self, VALUE srcarchive) {
|
418
486
|
struct zipruby_archive *p_archive, *p_srcarchive;
|
419
|
-
struct zip_source *zsource;
|
420
487
|
int i, num_files;
|
421
488
|
|
422
489
|
if (!rb_obj_is_instance_of(srcarchive, Archive)) {
|
@@ -431,21 +498,111 @@ static VALUE zipruby_archive_add_zip(VALUE self, VALUE srcarchive) {
|
|
431
498
|
num_files = zip_get_num_files(p_srcarchive->archive);
|
432
499
|
|
433
500
|
for (i = 0; i < num_files; i++) {
|
434
|
-
|
435
|
-
|
501
|
+
struct zip_source *zsource;
|
502
|
+
struct zip_file *fzip;
|
503
|
+
struct zip_stat sb;
|
504
|
+
char *buf;
|
505
|
+
const char *name;
|
506
|
+
int index, error;
|
507
|
+
|
508
|
+
zip_stat_init(&sb);
|
509
|
+
|
510
|
+
if (zip_stat_index(p_srcarchive->archive, i, 0, &sb)) {
|
511
|
+
zip_unchange_all(p_archive->archive);
|
512
|
+
zip_unchange_archive(p_archive->archive);
|
513
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_srcarchive->archive));
|
514
|
+
}
|
515
|
+
|
516
|
+
if ((buf = malloc(sb.size)) == NULL) {
|
517
|
+
zip_unchange_all(p_archive->archive);
|
518
|
+
zip_unchange_archive(p_archive->archive);
|
519
|
+
rb_raise(rb_eRuntimeError, "Update archive failed: Cannot allocate memory");
|
520
|
+
}
|
521
|
+
|
522
|
+
fzip = zip_fopen_index(p_srcarchive->archive, i, 0);
|
523
|
+
|
524
|
+
if (fzip == NULL) {
|
525
|
+
free(buf);
|
526
|
+
zip_unchange_all(p_archive->archive);
|
527
|
+
zip_unchange_archive(p_archive->archive);
|
528
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_srcarchive->archive));
|
529
|
+
}
|
530
|
+
|
531
|
+
if (zip_fread(fzip, buf, sb.size) == -1) {
|
532
|
+
free(buf);
|
533
|
+
zip_fclose(fzip);
|
534
|
+
zip_unchange_all(p_archive->archive);
|
535
|
+
zip_unchange_archive(p_archive->archive);
|
536
|
+
rb_raise(Error, "Update archive failed: %s", zip_file_strerror(fzip));
|
537
|
+
}
|
538
|
+
|
539
|
+
if ((error = zip_fclose(fzip)) != 0) {
|
540
|
+
char errstr[ERRSTR_BUFSIZE];
|
541
|
+
free(buf);
|
542
|
+
zip_unchange_all(p_archive->archive);
|
543
|
+
zip_unchange_archive(p_archive->archive);
|
544
|
+
zip_error_to_str(errstr, ERRSTR_BUFSIZE, error, errno);
|
545
|
+
rb_raise(Error, "Update archive failed: %s", errstr);
|
436
546
|
}
|
437
547
|
|
438
|
-
if (
|
548
|
+
if ((zsource = zip_source_buffer(p_archive->archive, buf, sb.size, 1)) == NULL) {
|
549
|
+
free(buf);
|
550
|
+
zip_unchange_all(p_archive->archive);
|
551
|
+
zip_unchange_archive(p_archive->archive);
|
552
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_archive->archive));
|
553
|
+
}
|
554
|
+
|
555
|
+
if ((name = zip_get_name(p_srcarchive->archive, i, 0)) == NULL) {
|
439
556
|
zip_source_free(zsource);
|
440
557
|
zip_unchange_all(p_archive->archive);
|
441
558
|
zip_unchange_archive(p_archive->archive);
|
442
|
-
rb_raise(Error, "
|
559
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_srcarchive->archive));
|
560
|
+
}
|
561
|
+
|
562
|
+
index = zip_name_locate(p_archive->archive, name, ZIP_FL_NOCASE);
|
563
|
+
|
564
|
+
if (index >= 0) {
|
565
|
+
if (zip_replace(p_archive->archive, i, zsource) == -1) {
|
566
|
+
zip_source_free(zsource);
|
567
|
+
zip_unchange_all(p_archive->archive);
|
568
|
+
zip_unchange_archive(p_archive->archive);
|
569
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_archive->archive));
|
570
|
+
}
|
571
|
+
} else {
|
572
|
+
if (zip_add(p_archive->archive, name, zsource) == -1) {
|
573
|
+
zip_source_free(zsource);
|
574
|
+
zip_unchange_all(p_archive->archive);
|
575
|
+
zip_unchange_archive(p_archive->archive);
|
576
|
+
rb_raise(Error, "Update archive failed: %s", zip_strerror(p_archive->archive));
|
577
|
+
}
|
443
578
|
}
|
444
579
|
}
|
445
580
|
|
446
581
|
return Qnil;
|
447
582
|
}
|
448
583
|
|
584
|
+
/* */
|
585
|
+
static VALUE zipruby_archive_get_comment(int argc, VALUE *argv, VALUE self) {
|
586
|
+
VALUE flags;
|
587
|
+
struct zipruby_archive *p_archive;
|
588
|
+
const char *comment;
|
589
|
+
int lenp, i_flags = 0;
|
590
|
+
|
591
|
+
rb_scan_args(argc, argv, "01", &flags);
|
592
|
+
|
593
|
+
if (!NIL_P(flags)) {
|
594
|
+
i_flags = NUM2INT(flags);
|
595
|
+
}
|
596
|
+
|
597
|
+
Data_Get_Struct(self, struct zipruby_archive, p_archive);
|
598
|
+
Check_Archive(p_archive);
|
599
|
+
|
600
|
+
// XXX: How is the error checked?
|
601
|
+
comment = zip_get_archive_comment(p_archive->archive, &lenp, i_flags);
|
602
|
+
|
603
|
+
return comment ? rb_str_new(comment, lenp) : Qnil;
|
604
|
+
}
|
605
|
+
|
449
606
|
/* */
|
450
607
|
static VALUE zipruby_archive_set_comment(VALUE self, VALUE comment) {
|
451
608
|
struct zipruby_archive *p_archive;
|
@@ -779,7 +936,7 @@ static VALUE zipruby_file_initialize(int argc, VALUE *argv, VALUE self) {
|
|
779
936
|
fzip = zip_fopen_index(p_archive->archive, i_index, i_flags);
|
780
937
|
|
781
938
|
if (fzip == NULL) {
|
782
|
-
rb_raise(Error, "Open file failed at %d", i_index, zip_strerror(p_archive->archive));
|
939
|
+
rb_raise(Error, "Open file failed at %d: %s", i_index, zip_strerror(p_archive->archive));
|
783
940
|
}
|
784
941
|
}
|
785
942
|
|
@@ -804,8 +961,8 @@ static VALUE zipruby_file_close(VALUE self) {
|
|
804
961
|
|
805
962
|
if ((error = zip_fclose(p_file->file)) != 0) {
|
806
963
|
char errstr[ERRSTR_BUFSIZE];
|
807
|
-
zip_error_to_str(errstr, ERRSTR_BUFSIZE, error, errno);
|
808
964
|
zip_unchange(p_file->archive, p_file->sb->index);
|
965
|
+
zip_error_to_str(errstr, ERRSTR_BUFSIZE, error, errno);
|
809
966
|
rb_raise(Error, "Close file failed: %s", errstr);
|
810
967
|
}
|
811
968
|
|