48 |
49 | #define GM_EXPORT __attribute__((visibility("default")))
50 |
51 | /*!
52 | *
53 | * Based on "AppleSingle/AppleDouble Formats for Foreign Files Developer's Note"
54 | *
55 | * Notes:
56 | * DoubleEntryFileDatesInfo
57 | * File creation, modification, backup, and access times as number of seconds
58 | * before or after 12:00 AM Jan 1 2000 GMT as SInt32.
59 | * DoubleEntryFinderInfo
60 | * 16 bytes of FinderInfo followed by 16 bytes of extended FinderInfo.
61 | * New FinderInfo should be zero'd out. For a directory, when the Finder
62 | * encounters an entry with the init'd bit cleared, it will initialize the
63 | * frView field of the to a value indicating how the contents of the
64 | * directory should be shown. Recommend to set frView to value of 256.
65 | * DoubleEntryMacFileInfo
66 | * This is a 32 bit flag that stores locked (bit 0) and protected (bit 1).
67 | *
68 | */
69 | typedef enum {
70 | DoubleEntryInvalid = 0,
71 | DoubleEntryDataFork = 1,
72 | DoubleEntryResourceFork = 2,
73 | DoubleEntryRealName = 3,
74 | DoubleEntryComment = 4,
75 | DoubleEntryBlackAndWhiteIcon = 5,
76 | DoubleEntryColorIcon = 6,
77 | DoubleEntryFileDatesInfo = 8, // See notes
78 | DoubleEntryFinderInfo = 9, // See notes
79 | DoubleEntryMacFileInfo = 10, // See notes
80 | DoubleEntryProDosFileInfo = 11,
81 | DoubleEntryMSDosFileinfo = 12,
82 | DoubleEntryShortName = 13,
83 | DoubleEntryAFPFileInfo = 14,
84 | DoubleEntryDirectoryID = 15,
85 | } GMAppleDoubleEntryID;
86 |
87 | /*!
88 | * @class
89 | * @discussion This class represents a single entry in an AppleDouble file.
90 | */
91 | GM_EXPORT @interface GMAppleDoubleEntry : NSObject {
92 | @private
93 | GMAppleDoubleEntryID entryID_;
94 | NSData* data_; // Format depends on entryID_
95 | }
96 | /*!
97 | * @abstract Initializes an AppleDouble entry with ID and data.
98 | * @param entryID A valid entry identifier
99 | * @param data Raw data for the entry
100 | */
101 | - (id)initWithEntryID:(GMAppleDoubleEntryID)entryID data:(NSData *)data;
102 |
103 | /*! @abstract The entry ID */
104 | - (GMAppleDoubleEntryID)entryID;
105 |
106 | /*! @abstract The entry data */
107 | - (NSData *)data;
108 | @end
109 |
110 | /*!
111 | * @class
112 | * @discussion This class can be used to construct raw AppleDouble data.
113 | */
114 | GM_EXPORT @interface GMAppleDouble : NSObject {
115 | @private
116 | NSMutableArray* entries_;
117 | }
118 |
119 | /*! @abstract An autoreleased empty GMAppleDouble file */
120 | + (GMAppleDouble *)appleDouble;
121 |
122 | /*!
123 | * @abstract An autoreleased GMAppleDouble file.
124 | * @discussion The GMAppleDouble is pre-filled with entries from the raw
125 | * AppleDouble file data.
126 | * @param data Raw AppleDouble file data.
127 | */
128 | + (GMAppleDouble *)appleDoubleWithData:(NSData *)data;
129 |
130 | /*!
131 | * @abstract Adds an entry to the AppleDouble file.
132 | * @param entry The entry to add
133 | */
134 | - (void)addEntry:(GMAppleDoubleEntry *)entry;
135 |
136 | /*!
137 | * @abstract Adds an entry to the AppleDouble file with ID and data.
138 | * @param entryID The ID of the entry to add
139 | * @param data The raw data for the entry to add (retained)
140 | */
141 | - (void)addEntryWithID:(GMAppleDoubleEntryID)entryID data:(NSData *)data;
142 |
143 | /*!
144 | * @abstract Adds entries based on the provided raw AppleDouble file data.
145 | * @discussion This will attempt to parse the given data as an AppleDouble file
146 | * and add all entries found.
147 | * @param data Raw AppleDouble file data
148 | * @param data The raw data for the entry to add (retained)
149 | * @result YES if the provided data was parsed correctly.
150 | */
151 | - (BOOL)addEntriesFromAppleDoubleData:(NSData *)data;
152 |
153 | /*!
154 | * @abstract The set of GMAppleDoubleEntry present in this GMAppleDouble.
155 | * @result An array of GMAppleDoubleEntry.
156 | */
157 | - (NSArray *)entries;
158 |
159 | /*!
160 | * @abstract Constructs raw data for the AppleDouble file.
161 | * @result The raw data for an AppleDouble file represented by this GMAppleDouble.
162 | */
163 | - (NSData *)data;
164 |
165 | @end
166 |
167 | #undef GM_EXPORT
--------------------------------------------------------------------------------
/External/ZipKit/MacFUSE/GMAppleDouble.m:
--------------------------------------------------------------------------------
1 | // ================================================================
2 | // Copyright (c) 2007, Google Inc.
3 | // All rights reserved.
4 | //
5 | // Redistribution and use in source and binary forms, with or without
6 | // modification, are permitted provided that the following conditions are
7 | // met:
8 | //
9 | // * Redistributions of source code must retain the above copyright
10 | // notice, this list of conditions and the following disclaimer.
11 | // * Redistributions in binary form must reproduce the above
12 | // copyright notice, this list of conditions and the following disclaimer
13 | // in the documentation and/or other materials provided with the
14 | // distribution.
15 | // * Neither the name of Google Inc. nor the names of its
16 | // contributors may be used to endorse or promote products derived from
17 | // this software without specific prior written permission.
18 | //
19 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20 | // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
21 | // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
22 | // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
23 | // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24 | // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
25 | // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 | // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 | // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 | // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29 | // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 | // ================================================================
31 | //
32 | // GMAppleDouble.m
33 | // MacFUSE
34 | //
35 | // Created by ted on 12/29/07.
36 | //
37 | #import "GMAppleDouble.h"
38 | #import "libkern/OSByteOrder.h"
39 |
40 | #define GM_APPLE_DOUBLE_HEADER_MAGIC 0x00051607
41 | #define GM_APPLE_DOUBLE_HEADER_VERSION 0x00020000
42 |
43 | typedef struct {
44 | UInt32 magicNumber; // Should be 0x00051607
45 | UInt32 versionNumber; // Should be 0x00020000
46 | char filler[16]; // Zero-filled bytes.
47 | UInt16 numberOfEntries; // Number of entries.
48 | } __attribute__((packed)) DoubleHeader;
49 |
50 | typedef struct {
51 | UInt32 entryID; // Defines what entry is (0 is invalid)
52 | UInt32 offset; // Offset from beginning of file to entry data.
53 | UInt32 length; // Length of entry data in bytes.
54 | } __attribute__((packed)) DoubleEntryHeader;
55 |
56 | @implementation GMAppleDoubleEntry
57 |
58 | + (GMAppleDoubleEntry *)entryWithID:(GMAppleDoubleEntryID)entryID
59 | data:(NSData *)data {
60 | return [[[GMAppleDoubleEntry alloc]
61 | initWithEntryID:entryID data:data] autorelease];
62 | }
63 |
64 | - (id)initWithEntryID:(GMAppleDoubleEntryID)entryID
65 | data:(NSData *)data {
66 | if ((self = [super init])) {
67 | if (entryID == DoubleEntryInvalid || data == nil) {
68 | [self release];
69 | return nil;
70 | }
71 | entryID_ = entryID;
72 | data_ = [data retain];
73 | }
74 | return self;
75 | }
76 |
77 | - (void)dealloc {
78 | [data_ release];
79 | [super dealloc];
80 | }
81 |
82 | - (GMAppleDoubleEntryID)entryID {
83 | return entryID_;
84 | }
85 | - (NSData *)data {
86 | return data_;
87 | }
88 |
89 | @end
90 |
91 | @implementation GMAppleDouble
92 |
93 | + (GMAppleDouble *)appleDouble {
94 | return [[[GMAppleDouble alloc] init] autorelease];
95 | }
96 |
97 | + (GMAppleDouble *)appleDoubleWithData:(NSData *)data {
98 | GMAppleDouble* appleDouble = [[[GMAppleDouble alloc] init] autorelease];
99 | if ([appleDouble addEntriesFromAppleDoubleData:data]) {
100 | return appleDouble;
101 | }
102 | return nil;
103 | }
104 |
105 | - (id)init {
106 | if ((self = [super init])) {
107 | entries_ = [[NSMutableArray alloc] init];
108 | }
109 | return self;
110 | }
111 |
112 | - (void)dealloc {
113 | [entries_ release];
114 | [super dealloc];
115 | }
116 |
117 | - (void)addEntry:(GMAppleDoubleEntry *)entry {
118 | [entries_ addObject:entry];
119 | }
120 |
121 | - (void)addEntryWithID:(GMAppleDoubleEntryID)entryID data:(NSData *)data {
122 | GMAppleDoubleEntry* entry = [GMAppleDoubleEntry entryWithID:entryID data:data];
123 | [self addEntry:entry];
124 | }
125 |
126 | - (BOOL)addEntriesFromAppleDoubleData:(NSData *)data {
127 | const int len = [data length];
128 | DoubleHeader header;
129 | if (len < sizeof(header)) {
130 | return NO; // To small to even fit our header.
131 | }
132 | [data getBytes:&header length:sizeof(header)];
133 | if (OSSwapBigToHostInt32(header.magicNumber) != GM_APPLE_DOUBLE_HEADER_MAGIC ||
134 | OSSwapBigToHostInt32(header.versionNumber) != GM_APPLE_DOUBLE_HEADER_VERSION) {
135 | return NO; // Invalid header.
136 | }
137 | int count = OSSwapBigToHostInt16(header.numberOfEntries);
138 | int offset = sizeof(DoubleHeader);
139 | if (len < (offset + (count * sizeof(DoubleEntryHeader)))) {
140 | return NO; // Not enough data to hold all the DoubleEntryHeader.
141 | }
142 | for (int i = 0; i < count; ++i, offset += sizeof(DoubleEntryHeader)) {
143 | // Extract header
144 | DoubleEntryHeader entryHeader;
145 | NSRange range = NSMakeRange(offset, sizeof(entryHeader));
146 | [data getBytes:&entryHeader range:range];
147 |
148 | // Extract data
149 | range = NSMakeRange(OSSwapBigToHostInt32(entryHeader.offset),
150 | OSSwapBigToHostInt32(entryHeader.length));
151 | if (len < (range.location + range.length)) {
152 | return NO; // Given data too small to contain this entry.
153 | }
154 | NSData* entryData = [data subdataWithRange:range];
155 | [self addEntryWithID:OSSwapBigToHostInt32(entryHeader.entryID) data:entryData];
156 | }
157 |
158 | return YES;
159 | }
160 |
161 | - (NSArray *)entries {
162 | return entries_;
163 | }
164 |
165 | - (NSData *)data {
166 | NSMutableData* entryListData = [NSMutableData data];
167 | NSMutableData* entryData = [NSMutableData data];
168 | int dataStartOffset =
169 | sizeof(DoubleHeader) + [entries_ count] * sizeof(DoubleEntryHeader);
170 | for (int i = 0; i < [entries_ count]; ++i) {
171 | GMAppleDoubleEntry* entry = [entries_ objectAtIndex:i];
172 |
173 | DoubleEntryHeader entryHeader;
174 | memset(&entryHeader, 0, sizeof(entryHeader));
175 | entryHeader.entryID = OSSwapHostToBigInt32((UInt32)[entry entryID]);
176 | entryHeader.offset =
177 | OSSwapHostToBigInt32((UInt32)(dataStartOffset + [entryData length]));
178 | entryHeader.length = OSSwapHostToBigInt32((UInt32)[[entry data] length]);
179 | [entryListData appendBytes:&entryHeader length:sizeof(entryHeader)];
180 | [entryData appendData:[entry data]];
181 | }
182 |
183 | NSMutableData* data = [NSMutableData data];
184 |
185 | DoubleHeader header;
186 | memset(&header, 0, sizeof(header));
187 | header.magicNumber = OSSwapHostToBigConstInt32(GM_APPLE_DOUBLE_HEADER_MAGIC);
188 | header.versionNumber = OSSwapHostToBigConstInt32(GM_APPLE_DOUBLE_HEADER_VERSION);
189 | header.numberOfEntries = OSSwapHostToBigInt16((UInt16)[entries_ count]);
190 | [data appendBytes:&header length:sizeof(header)];
191 | [data appendData:entryListData];
192 | [data appendData:entryData];
193 | return data;
194 | }
195 |
196 | @end
197 |
--------------------------------------------------------------------------------
/External/ZipKit/NSData+ZKAdditions.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSData+ZKAdditions.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 |
10 | @interface NSData (ZKAdditions)
11 |
12 | - (UInt16) zk_hostInt16OffsetBy:(NSUInteger *)offset;
13 | - (UInt32) zk_hostInt32OffsetBy:(NSUInteger *)offset;
14 | - (UInt64) zk_hostInt64OffsetBy:(NSUInteger *)offset;
15 | - (BOOL) zk_hostBoolOffsetBy:(NSUInteger *) offset;
16 | - (NSString *) zk_stringOffsetBy:(NSUInteger *)offset length:(NSUInteger)length;
17 | - (NSUInteger) zk_crc32;
18 | - (NSUInteger) zk_crc32:(NSUInteger)crc;
19 | - (NSData *) zk_inflate;
20 | - (NSData *) zk_deflate;
21 |
22 | @end
23 |
24 | @interface NSMutableData (ZKAdditions)
25 |
26 | + (NSMutableData *) zk_dataWithLittleInt16:(UInt16)value;
27 | + (NSMutableData *) zk_dataWithLittleInt32:(UInt32)value;
28 | + (NSMutableData *) zk_dataWithLittleInt64:(UInt64)value;
29 |
30 | - (void) zk_appendLittleInt16:(UInt16)value;
31 | - (void) zk_appendLittleInt32:(UInt32)value;
32 | - (void) zk_appendLittleInt64:(UInt64)value;
33 | - (void) zk_appendLittleBool:(BOOL) value;
34 | - (void) zk_appendPrecomposedUTF8String:(NSString *)value;
35 |
36 | @end
--------------------------------------------------------------------------------
/External/ZipKit/NSData+ZKAdditions.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSData+ZKAdditions.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "NSData+ZKAdditions.h"
9 | #import "NSFileManager+ZKAdditions.h"
10 | #import "ZKCDHeader.h"
11 | #import "ZKCDTrailer.h"
12 | #import "ZKLFHeader.h"
13 | #import "zlib.h"
14 |
15 | @implementation NSData (ZKAdditions)
16 |
17 | - (UInt16) zk_hostInt16OffsetBy:(NSUInteger *)offset {
18 | UInt16 value;
19 | NSUInteger length = sizeof(value);
20 | [self getBytes:&value range:NSMakeRange(*offset, length)];
21 | *offset += length;
22 | return CFSwapInt16LittleToHost(value);
23 | }
24 |
25 | - (UInt32) zk_hostInt32OffsetBy:(NSUInteger *)offset {
26 | UInt32 value;
27 | NSUInteger length = sizeof(value);
28 | [self getBytes:&value range:NSMakeRange(*offset, length)];
29 | *offset += length;
30 | return CFSwapInt32LittleToHost(value);
31 | }
32 |
33 | - (UInt64) zk_hostInt64OffsetBy:(NSUInteger *)offset {
34 | UInt64 value;
35 | NSUInteger length = sizeof(value);
36 | [self getBytes:&value range:NSMakeRange(*offset, length)];
37 | *offset += length;
38 | return CFSwapInt64LittleToHost(value);
39 | }
40 |
41 | - (BOOL) zk_hostBoolOffsetBy:(NSUInteger *)offset {
42 | UInt32 value = [self zk_hostInt32OffsetBy:offset];
43 | return value != 0;
44 | }
45 |
46 | - (NSString *) zk_stringOffsetBy:(NSUInteger *)offset length:(NSUInteger)length {
47 | NSString *value = nil;
48 | NSData *subData = [self subdataWithRange:NSMakeRange(*offset, length)];
49 | if (length > 0)
50 | value = [[[NSString alloc] initWithData:subData encoding:NSUTF8StringEncoding] autorelease];
51 | if (!value) {
52 | // No valid utf8 encoding, replace everything non-ascii with '?'
53 | NSMutableData *md = [subData mutableCopyWithZone:nil];
54 | unsigned char *mdd = [md mutableBytes];
55 | if ([md length] > 0) {
56 | for (unsigned int i = 0; i < [md length]; i++)
57 | if (mdd[i] > 127)
58 | mdd[i] = '?';
59 | value = [[[NSString alloc] initWithData:md encoding:NSUTF8StringEncoding] autorelease];
60 | }
61 | [md release];
62 | }
63 | *offset += length;
64 | return value;
65 | }
66 |
67 | - (NSUInteger) zk_crc32 {
68 | return [self zk_crc32:0];
69 | }
70 |
71 | - (NSUInteger) zk_crc32:(NSUInteger)crc {
72 | return crc32(crc, [self bytes], [self length]);
73 | }
74 |
75 | - (NSData *) zk_inflate {
76 | NSUInteger full_length = [self length];
77 | NSUInteger half_length = full_length / 2;
78 |
79 | NSMutableData *inflatedData = [NSMutableData dataWithLength:full_length + half_length];
80 | BOOL done = NO;
81 | int status;
82 |
83 | z_stream strm;
84 |
85 | strm.next_in = (Bytef *)[self bytes];
86 | strm.avail_in = [self length];
87 | strm.total_out = 0;
88 | strm.zalloc = Z_NULL;
89 | strm.zfree = Z_NULL;
90 |
91 | if (inflateInit2(&strm, -MAX_WBITS) != Z_OK) return nil;
92 | while (!done) {
93 | if (strm.total_out >= [inflatedData length])
94 | [inflatedData increaseLengthBy:half_length];
95 | strm.next_out = [inflatedData mutableBytes] + strm.total_out;
96 | strm.avail_out = [inflatedData length] - strm.total_out;
97 | status = inflate(&strm, Z_SYNC_FLUSH);
98 | if (status == Z_STREAM_END) done = YES;
99 | else if (status != Z_OK) break;
100 | }
101 | if (inflateEnd(&strm) == Z_OK && done)
102 | [inflatedData setLength:strm.total_out];
103 | else
104 | inflatedData = nil;
105 | return inflatedData;
106 | }
107 |
108 | - (NSData *) zk_deflate {
109 | z_stream strm;
110 |
111 | strm.zalloc = Z_NULL;
112 | strm.zfree = Z_NULL;
113 | strm.opaque = Z_NULL;
114 | strm.total_out = 0;
115 | strm.next_in = (Bytef *)[self bytes];
116 | strm.avail_in = [self length];
117 |
118 | NSMutableData *deflatedData = [NSMutableData dataWithLength:16384];
119 | if (deflateInit2(&strm, Z_BEST_COMPRESSION, Z_DEFLATED, -MAX_WBITS, 8, Z_DEFAULT_STRATEGY) != Z_OK) return nil;
120 | do {
121 | if (strm.total_out >= [deflatedData length])
122 | [deflatedData increaseLengthBy:16384];
123 | strm.next_out = [deflatedData mutableBytes] + strm.total_out;
124 | strm.avail_out = [deflatedData length] - strm.total_out;
125 | deflate(&strm, Z_FINISH);
126 | } while (strm.avail_out == 0);
127 | deflateEnd(&strm);
128 | [deflatedData setLength:strm.total_out];
129 |
130 | return deflatedData;
131 | }
132 |
133 | @end
134 |
135 | @implementation NSMutableData (ZKAdditions)
136 |
137 | + (NSMutableData *) zk_dataWithLittleInt16:(UInt16)value {
138 | NSMutableData *data = [self data];
139 | [data zk_appendLittleInt16:value];
140 | return data;
141 | }
142 |
143 | + (NSMutableData *) zk_dataWithLittleInt32:(UInt32)value {
144 | NSMutableData *data = [self data];
145 | [data zk_appendLittleInt32:value];
146 | return data;
147 | }
148 |
149 | + (NSMutableData *) zk_dataWithLittleInt64:(UInt64)value {
150 | NSMutableData *data = [self data];
151 | [data zk_appendLittleInt64:value];
152 | return data;
153 | }
154 |
155 | - (void) zk_appendLittleInt16:(UInt16)value {
156 | UInt16 swappedValue = CFSwapInt16HostToLittle(value);
157 | [self appendBytes:&swappedValue length:sizeof(swappedValue)];
158 | }
159 |
160 | - (void) zk_appendLittleInt32:(UInt32)value {
161 | UInt32 swappedValue = CFSwapInt32HostToLittle(value);
162 | [self appendBytes:&swappedValue length:sizeof(swappedValue)];
163 | }
164 |
165 | - (void) zk_appendLittleInt64:(UInt64)value {
166 | UInt64 swappedValue = CFSwapInt64HostToLittle(value);
167 | [self appendBytes:&swappedValue length:sizeof(swappedValue)];
168 | }
169 |
170 | - (void) zk_appendLittleBool:(BOOL)value {
171 | return [self zk_appendLittleInt32:(value ? 1:0)];
172 | }
173 |
174 | - (void) zk_appendPrecomposedUTF8String:(NSString *)value {
175 | return [self appendData:[[value precomposedStringWithCanonicalMapping] dataUsingEncoding:NSUTF8StringEncoding]];
176 | }
177 |
178 | @end
179 |
--------------------------------------------------------------------------------
/External/ZipKit/NSDate+ZKAdditions.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSDate+ZKAdditions.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 |
10 | @interface NSDate (ZKAdditions)
11 |
12 | + (NSDate *) zk_dateWithDosDate:(NSUInteger) dosDate;
13 | - (NSUInteger) zk_dosDate;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/External/ZipKit/NSDate+ZKAdditions.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSDate+ZKAdditions.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "NSDate+ZKAdditions.h"
9 |
10 | @implementation NSDate (ZKAdditions)
11 |
12 | + (NSDate *)zk_dateWithDosDate : (NSUInteger)dosDate {
13 | NSUInteger date = (NSUInteger)(dosDate >> 16);
14 | NSDateComponents *comps = [[NSDateComponents new] autorelease];
15 | comps.year = ((date & 0x0FE00) / 0x0200) + 1980;
16 | comps.month = (date & 0x1E0) / 0x20;
17 | comps.day = date & 0x1f;
18 | comps.hour = (dosDate & 0xF800) / 0x800;
19 | comps.minute = (dosDate & 0x7E0) / 0x20;
20 | comps.second = 2 * (dosDate & 0x1f);
21 | return [[NSCalendar currentCalendar] dateFromComponents:comps];
22 | }
23 |
24 | - (NSUInteger) zk_dosDate {
25 | NSUInteger options = NSYearCalendarUnit | NSMonthCalendarUnit | NSDayCalendarUnit |
26 | NSHourCalendarUnit | NSMinuteCalendarUnit | NSSecondCalendarUnit;
27 | NSDateComponents *comps = [[NSCalendar currentCalendar] components:options fromDate:self];
28 | return ((comps.day + 32 * comps.month + 512 * (comps.year - 1980)) << 16) | (comps.second / 2 + 32 * comps.minute + 2048 * comps.hour);
29 | }
30 |
31 | @end
--------------------------------------------------------------------------------
/External/ZipKit/NSDictionary+ZKAdditions.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSDictionary+ZKAdditions.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 |
10 | @interface NSDictionary (ZKAdditions)
11 |
12 | + (NSDictionary *) zk_totalSizeAndCountDictionaryWithSize:(unsigned long long) size andItemCount:(unsigned long long) count;
13 | - (unsigned long long) zk_totalFileSize;
14 | - (unsigned long long) zk_itemCount;
15 |
16 | @end
--------------------------------------------------------------------------------
/External/ZipKit/NSDictionary+ZKAdditions.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSDictionary+ZKAdditions.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "NSDictionary+ZKAdditions.h"
9 |
10 | NSString* const ZKTotalFileSize = @"ZKTotalFileSize";
11 | NSString* const ZKItemCount = @"ZKItemCount";
12 |
13 | @implementation NSDictionary (ZKAdditions)
14 |
15 | + (NSDictionary *) zk_totalSizeAndCountDictionaryWithSize:(unsigned long long) size andItemCount:(unsigned long long) count {
16 | return [NSDictionary dictionaryWithObjectsAndKeys:
17 | [NSNumber numberWithUnsignedLongLong:size], ZKTotalFileSize,
18 | [NSNumber numberWithUnsignedLongLong:count], ZKItemCount, nil];
19 | }
20 |
21 | - (unsigned long long) zk_totalFileSize {
22 | return [[self objectForKey:ZKTotalFileSize] unsignedLongLongValue];
23 | }
24 |
25 | - (unsigned long long) zk_itemCount {
26 | return [[self objectForKey:ZKItemCount] unsignedLongLongValue];
27 | }
28 |
29 | @end
--------------------------------------------------------------------------------
/External/ZipKit/NSFileHandle+ZKAdditions.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSFileHandle+ZKAdditions.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 |
10 | @interface NSFileHandle (ZKAdditions)
11 |
12 | + (NSFileHandle *) zk_newFileHandleForWritingAtPath:(NSString *)path;
13 |
14 | @end
--------------------------------------------------------------------------------
/External/ZipKit/NSFileHandle+ZKAdditions.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSFileHandle+ZKAdditions.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "NSFileHandle+ZKAdditions.h"
9 |
10 | @implementation NSFileHandle (ZKAdditions)
11 |
12 | + (NSFileHandle *)zk_newFileHandleForWritingAtPath:(NSString *)path {
13 | NSFileManager *fm = [NSFileManager new];
14 | if (![fm fileExistsAtPath:path]) {
15 | [fm createDirectoryAtPath:[path stringByDeletingLastPathComponent] withIntermediateDirectories:YES attributes:nil error:nil];
16 | [fm createFileAtPath:path contents:nil attributes:nil];
17 | }
18 | NSFileHandle *fileHandle = [self fileHandleForWritingAtPath:path];
19 | [fm release];
20 | return fileHandle;
21 | }
22 |
23 | @end
--------------------------------------------------------------------------------
/External/ZipKit/NSFileManager+ZKAdditions.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSFileManager+ZKAdditions.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 | #import "ZKDefs.h"
10 |
11 | @interface NSFileManager (ZKAdditions)
12 |
13 | - (BOOL) zk_isSymLinkAtPath:(NSString *) path;
14 | - (BOOL) zk_isDirAtPath:(NSString *) path;
15 |
16 | - (unsigned long long) zk_dataSizeAtFilePath:(NSString *) path;
17 | - (NSDictionary *) zkTotalSizeAndItemCountAtPath:(NSString *) path usingResourceFork:(BOOL) rfFlag;
18 | #if ZK_TARGET_OS_MAC
19 | - (void) zk_combineAppleDoubleInDirectory:(NSString *) path;
20 | #endif
21 |
22 | - (NSDate *) zk_modificationDateForPath:(NSString *) path;
23 | - (NSUInteger) zk_posixPermissionsAtPath:(NSString *) path;
24 | - (NSUInteger) zk_externalFileAttributesAtPath:(NSString *) path;
25 | - (NSUInteger) zk_externalFileAttributesFor:(NSDictionary *) fileAttributes;
26 |
27 | - (NSUInteger) zk_crcForPath:(NSString *) path;
28 | - (NSUInteger) zk_crcForPath:(NSString *) path invoker:(id) invoker;
29 | - (NSUInteger) zk_crcForPath:(NSString *) path invoker:(id)invoker;
30 | - (NSUInteger) zk_crcForPath:(NSString *)path invoker:(id)invoker throttleThreadSleepTime:(NSTimeInterval) throttleThreadSleepTime;
31 |
32 | @end
--------------------------------------------------------------------------------
/External/ZipKit/NSFileManager+ZKAdditions.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSFileManager+ZKAdditions.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "NSFileManager+ZKAdditions.h"
9 | #import "NSData+ZKAdditions.h"
10 | #import "NSDictionary+ZKAdditions.h"
11 |
12 | #if ZK_TARGET_OS_MAC
13 | #import "GMAppleDouble+ZKAdditions.h"
14 | #endif
15 |
16 | const NSUInteger ZKMaxEntriesPerFetch = 40;
17 |
18 | @implementation NSFileManager (ZKAdditions)
19 |
20 | - (BOOL) zk_isSymLinkAtPath:(NSString *) path {
21 | return [[[self attributesOfItemAtPath:path error:nil] fileType] isEqualToString:NSFileTypeSymbolicLink];
22 | }
23 |
24 | - (BOOL) zk_isDirAtPath:(NSString *) path {
25 | BOOL isDir;
26 | BOOL pathExists = [self fileExistsAtPath:path isDirectory:&isDir];
27 | return pathExists && isDir;
28 | }
29 |
30 | - (unsigned long long) zk_dataSizeAtFilePath:(NSString *) path {
31 | return [[self attributesOfItemAtPath:path error:nil] fileSize];
32 | }
33 |
34 | #if ZK_TARGET_OS_MAC
35 | - (void) totalsAtDirectoryFSRef:(FSRef*) fsRef usingResourceFork:(BOOL) rfFlag
36 | totalSize:(unsigned long long *) size
37 | itemCount:(unsigned long long *) count {
38 | FSIterator iterator;
39 | OSErr fsErr = FSOpenIterator(fsRef, kFSIterateFlat, &iterator);
40 | if (fsErr == noErr) {
41 | ItemCount actualFetched;
42 | FSRef fetchedRefs[ZKMaxEntriesPerFetch];
43 | FSCatalogInfo fetchedInfos[ZKMaxEntriesPerFetch];
44 | while (fsErr == noErr) {
45 | fsErr = FSGetCatalogInfoBulk(iterator, ZKMaxEntriesPerFetch, &actualFetched, NULL,
46 | kFSCatInfoDataSizes | kFSCatInfoRsrcSizes | kFSCatInfoNodeFlags,
47 | fetchedInfos, fetchedRefs, NULL, NULL);
48 | if ((fsErr == noErr) || (fsErr == errFSNoMoreItems)) {
49 | (*count) += actualFetched;
50 | for (ItemCount i = 0; i < actualFetched; i++) {
51 | if (fetchedInfos[i].nodeFlags & kFSNodeIsDirectoryMask)
52 | [self totalsAtDirectoryFSRef:&fetchedRefs[i] usingResourceFork:rfFlag totalSize:size itemCount:count];
53 | else
54 | (*size) += fetchedInfos [i].dataLogicalSize + (rfFlag ? fetchedInfos [i].rsrcLogicalSize : 0);
55 | }
56 | }
57 | }
58 | FSCloseIterator(iterator);
59 | }
60 | return ;
61 | }
62 | #endif
63 |
64 | - (NSDictionary *) zkTotalSizeAndItemCountAtPath:(NSString *) path usingResourceFork:(BOOL) rfFlag {
65 | unsigned long long size = 0;
66 | unsigned long long count = 0;
67 | #if ZK_TARGET_OS_MAC
68 | FSRef fsRef;
69 | Boolean isDirectory;
70 | OSStatus status = FSPathMakeRef((const unsigned char*)[path fileSystemRepresentation], &fsRef, &isDirectory);
71 | if (status != noErr)
72 | return nil;
73 | if (isDirectory) {
74 | [self totalsAtDirectoryFSRef:&fsRef usingResourceFork:rfFlag totalSize:&size itemCount:&count];
75 | } else {
76 | count = 1;
77 | FSCatalogInfo info;
78 | OSErr fsErr = FSGetCatalogInfo(&fsRef, kFSCatInfoDataSizes | kFSCatInfoRsrcSizes, &info, NULL, NULL, NULL);
79 | if (fsErr == noErr)
80 | size = info.dataLogicalSize + (rfFlag ? info.rsrcLogicalSize : 0);
81 | }
82 | #else
83 | // TODO: maybe fix this for non-Mac targets
84 | size = 0;
85 | count = 0;
86 | #endif
87 | return [NSDictionary zk_totalSizeAndCountDictionaryWithSize:size andItemCount:count];
88 | }
89 |
90 | #if ZK_TARGET_OS_MAC
91 | - (void) zk_combineAppleDoubleInDirectory:(NSString *) path {
92 | if (![self zk_isDirAtPath:path])
93 | return;
94 | NSArray *dirContents = [self contentsOfDirectoryAtPath:path error:nil];
95 | for (NSString *entry in dirContents) {
96 | NSString *subPath = [path stringByAppendingPathComponent:entry];
97 | if (![self zk_isSymLinkAtPath:subPath]) {
98 | if ([self zk_isDirAtPath:subPath])
99 | [self zk_combineAppleDoubleInDirectory:subPath];
100 | else {
101 | // if the file is an AppleDouble file (i.e., it begins with "._") in the __MACOSX hierarchy,
102 | // find its corresponding data fork and combine them
103 | if ([subPath rangeOfString:ZKMacOSXDirectory].location != NSNotFound) {
104 | NSString *fileName = [subPath lastPathComponent];
105 | NSRange ZKDotUnderscoreRange = [fileName rangeOfString:ZKDotUnderscore];
106 | if (ZKDotUnderscoreRange.location == 0 && ZKDotUnderscoreRange.length == 2) {
107 | NSMutableArray *pathComponents =
108 | (NSMutableArray *)[[[subPath stringByDeletingLastPathComponent] stringByAppendingPathComponent:
109 | [fileName substringFromIndex:2]] pathComponents];
110 | for (NSString *pathComponent in pathComponents) {
111 | if ([ZKMacOSXDirectory isEqualToString:pathComponent]) {
112 | [pathComponents removeObject:pathComponent];
113 | break;
114 | }
115 | }
116 | NSData *appleDoubleData = [NSData dataWithContentsOfFile:subPath];
117 | [GMAppleDouble zk_restoreAppleDoubleData:appleDoubleData toPath:[NSString pathWithComponents:pathComponents]];
118 | }
119 | }
120 | }
121 | }
122 | }
123 | }
124 | #endif
125 |
126 | - (NSDate *) zk_modificationDateForPath:(NSString *) path {
127 | return [[self attributesOfItemAtPath:path error:nil] fileModificationDate];
128 | }
129 |
130 | - (NSUInteger) zk_posixPermissionsAtPath:(NSString *) path {
131 | return [[self attributesOfItemAtPath:path error:nil] filePosixPermissions];
132 | }
133 |
134 | - (NSUInteger) zk_externalFileAttributesAtPath:(NSString *) path {
135 | return [self zk_externalFileAttributesFor:[self attributesOfItemAtPath:path error:nil]];
136 | }
137 |
138 | - (NSUInteger) zk_externalFileAttributesFor:(NSDictionary *) fileAttributes {
139 | NSUInteger externalFileAttributes = 0;
140 | @try {
141 | BOOL isSymLink = [[fileAttributes fileType] isEqualToString:NSFileTypeSymbolicLink];
142 | BOOL isDir = [[fileAttributes fileType] isEqualToString:NSFileTypeDirectory];
143 | NSUInteger posixPermissions = [fileAttributes filePosixPermissions];
144 | externalFileAttributes = posixPermissions << 16 | (isSymLink ? 0xA0004000 : (isDir ? 0x40004000 : 0x80004000));
145 | } @catch(NSException * e) {
146 | externalFileAttributes = 0;
147 | }
148 | return externalFileAttributes;
149 | }
150 |
151 | - (NSUInteger) zk_crcForPath:(NSString *) path {
152 | return [self zk_crcForPath:path invoker:nil throttleThreadSleepTime:0.0];
153 | }
154 |
155 | - (NSUInteger) zk_crcForPath:(NSString *) path invoker:(id)invoker {
156 | return [self zk_crcForPath:path invoker:invoker throttleThreadSleepTime:0.0];
157 | }
158 |
159 | - (NSUInteger) zk_crcForPath:(NSString *)path invoker:(id)invoker throttleThreadSleepTime:(NSTimeInterval) throttleThreadSleepTime {
160 | NSUInteger crc32 = 0;
161 | path = [path stringByExpandingTildeInPath];
162 | BOOL isDirectory;
163 | if ([self fileExistsAtPath:path isDirectory:&isDirectory] && !isDirectory) {
164 | BOOL irtsIsCancelled = [invoker respondsToSelector:@selector(isCancelled)];
165 | const NSUInteger crcBlockSize = 1048576;
166 | NSFileHandle *fileHandle = [NSFileHandle fileHandleForReadingAtPath:path];
167 | NSData *block = [fileHandle readDataOfLength:crcBlockSize] ;
168 | while ([block length] > 0) {
169 | crc32 = [block zk_crc32:crc32];
170 | if (irtsIsCancelled) {
171 | if ([invoker isCancelled]) {
172 | [fileHandle closeFile];
173 | return 0;
174 | }
175 | }
176 | block = [fileHandle readDataOfLength:crcBlockSize];
177 | [NSThread sleepForTimeInterval:throttleThreadSleepTime];
178 | }
179 | [fileHandle closeFile];
180 | } else
181 | crc32 = 0;
182 | return crc32;
183 | }
184 |
185 | @end
186 |
--------------------------------------------------------------------------------
/External/ZipKit/NSString+ZKAdditions.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSString+ZKAdditions.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 |
10 | @interface NSString (ZKAdditions)
11 |
12 | - (NSUInteger) zk_precomposedUTF8Length;
13 | - (BOOL) zk_isResourceForkPath;
14 |
15 | @end
--------------------------------------------------------------------------------
/External/ZipKit/NSString+ZKAdditions.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSString+ZKAdditions.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "NSString+ZKAdditions.h"
9 | #import "ZKDefs.h"
10 |
11 | @implementation NSString (ZKAdditions)
12 |
13 | - (NSUInteger) zk_precomposedUTF8Length {
14 | return [[self precomposedStringWithCanonicalMapping] lengthOfBytesUsingEncoding:NSUTF8StringEncoding];
15 | }
16 |
17 | - (BOOL) zk_isResourceForkPath {
18 | return [[[self pathComponents] objectAtIndex:0] isEqualToString:ZKMacOSXDirectory];
19 | }
20 |
21 |
22 | @end
--------------------------------------------------------------------------------
/External/ZipKit/ZKArchive.h:
--------------------------------------------------------------------------------
1 | //
2 | // ZKArchive.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 08/05/09.
6 | //
7 |
8 | #import
9 |
10 | @class ZKCDTrailer;
11 |
12 | @interface ZKArchive : NSObject {
13 | @private
14 | // invoker should be an NSOperation or NSThread; if [invoker isCancelled], inflation or deflation will be aborted
15 | id __weak _invoker;
16 | id __weak _delegate;
17 | NSString *_archivePath;
18 | NSMutableArray *_centralDirectory;
19 | NSFileManager *_fileManager;
20 | ZKCDTrailer *_cdTrailer;
21 | NSTimeInterval _throttleThreadSleepTime;
22 |
23 | @protected
24 | // cached respondsToSelector: checks
25 | BOOL drtsDelegateWantsSizes;
26 | BOOL drtsDidBeginZip;
27 | BOOL drtsDidBeginUnzip;
28 | BOOL drtsWillZipPath;
29 | BOOL drtsWillUnzipPath;
30 | BOOL drtsDidEndZip;
31 | BOOL drtsDidEndUnzip;
32 | BOOL drtsDidCancel;
33 | BOOL drtsDidFail;
34 | BOOL drtsDidUpdateTotalSize;
35 | BOOL drtsDidUpdateTotalCount;
36 | BOOL drtsDidUpdateBytesWritten;
37 |
38 | BOOL irtsIsCancelled;
39 | }
40 |
41 | + (BOOL) validArchiveAtPath:(NSString *) path;
42 | + (NSString *) uniquify:(NSString *) path;
43 | - (void) calculateSizeAndItemCount:(NSDictionary *) userInfo;
44 | - (NSString *) uniqueExpansionDirectoryIn:(NSString *) enclosingFolder;
45 | - (void) cleanUpExpansionDirectory:(NSString *) expansionDirectory;
46 |
47 | - (BOOL) delegateWantsSizes;
48 |
49 | - (void) didBeginZip;
50 | - (void) didBeginUnzip;
51 | - (void) willZipPath:(NSString *)path;
52 | - (void) willUnzipPath:(NSString *)path;
53 | - (void) didEndZip;
54 | - (void) didEndUnzip;
55 | - (void) didCancel;
56 | - (void) didFail;
57 | - (void) didUpdateTotalSize:(NSNumber *) size;
58 | - (void) didUpdateTotalCount:(NSNumber *) count;
59 | - (void) didUpdateBytesWritten:(NSNumber *) byteCount;
60 |
61 | @property (assign, nonatomic) id __weak invoker;
62 | @property (assign, nonatomic) id __weak delegate;
63 | @property (copy) NSString *archivePath;
64 | @property (retain) NSMutableArray *centralDirectory;
65 | @property (retain) NSFileManager *fileManager;
66 | @property (retain) ZKCDTrailer *cdTrailer;
67 | @property (assign) NSTimeInterval throttleThreadSleepTime;
68 | @property (copy) NSString *comment;
69 |
70 | @end
--------------------------------------------------------------------------------
/External/ZipKit/ZKArchive.m:
--------------------------------------------------------------------------------
1 | //
2 | // ZKArchive.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 08/05/09.
6 | //
7 |
8 | #import "ZKArchive.h"
9 | #import "NSDictionary+ZKAdditions.h"
10 | #import "NSFileManager+ZKAdditions.h"
11 | #import "ZKCDTrailer.h"
12 | #import "ZKDefs.h"
13 |
14 | @interface NSObject (ZipKitDelegate)
15 | - (void) onZKArchiveDidBeginZip:(ZKArchive *) archive;
16 | - (void) onZKArchiveDidBeginUnzip:(ZKArchive *) archive;
17 | - (void) onZKArchive:(ZKArchive *) archive willZipPath:(NSString *) path;
18 | - (void) onZKArchive:(ZKArchive *) archive willUnzipPath:(NSString *) path;
19 | - (void) onZKArchive:(ZKArchive *) archive didUpdateTotalSize:(unsigned long long) size;
20 | - (void) onZKArchive:(ZKArchive *) archive didUpdateTotalCount:(unsigned long long) count;
21 | - (void) onZKArchive:(ZKArchive *) archive didUpdateBytesWritten:(unsigned long long) byteCount;
22 | - (void) onZKArchiveDidEndZip:(ZKArchive *) archive;
23 | - (void) onZKArchiveDidEndUnzip:(ZKArchive *) archive;
24 | - (void) onZKArchiveDidCancel:(ZKArchive *) archive;
25 | - (void) onZKArchiveDidFail:(ZKArchive *) archive;
26 | - (BOOL) zkDelegateWantsSizes;
27 | @end
28 |
29 | #pragma mark -
30 |
31 | @implementation ZKArchive
32 |
33 | #pragma mark -
34 | #pragma mark Utility
35 |
36 | + (BOOL) validArchiveAtPath:(NSString *) path {
37 | // check that the first few bytes of the file are a local file header
38 | NSFileHandle *fileHandle = [NSFileHandle fileHandleForReadingAtPath:path];
39 | NSData *fileHeader = [fileHandle readDataOfLength:4];
40 | [fileHandle closeFile];
41 | UInt32 headerValue;
42 | [fileHeader getBytes:&headerValue];
43 | return (CFSwapInt32LittleToHost(headerValue) == ZKLFHeaderMagicNumber);
44 | }
45 |
46 | + (NSString *) uniquify:(NSString *) path {
47 | // avoid name collisions by adding a sequence number if needed
48 | NSString * uniquePath = [NSString stringWithString:path];
49 | NSString *dir = [path stringByDeletingLastPathComponent];
50 | NSString *fileNameBase = [[path lastPathComponent] stringByDeletingPathExtension];
51 | NSString *ext = [path pathExtension];
52 | NSUInteger i = 2;
53 | NSFileManager *fm = [[NSFileManager new] autorelease];
54 | while ([fm fileExistsAtPath:uniquePath]) {
55 | uniquePath = [dir stringByAppendingPathComponent:[NSString stringWithFormat:@"%@ %u", fileNameBase, i++]];
56 | if (ext && [ext length] > 0)
57 | uniquePath = [uniquePath stringByAppendingPathExtension:ext];
58 | }
59 | return uniquePath;
60 | }
61 |
62 | - (void) calculateSizeAndItemCount:(NSDictionary *) userInfo {
63 | NSArray *paths = [userInfo objectForKey:ZKPathsKey];
64 | BOOL rfFlag = [[userInfo objectForKey:ZKusingResourceForkKey] boolValue];
65 | unsigned long long size = 0;
66 | unsigned long long count = 0;
67 | NSFileManager *fmgr = [[NSFileManager new] autorelease];
68 | NSDictionary *dict = nil;
69 | for (NSString *path in paths) {
70 | dict = [fmgr zkTotalSizeAndItemCountAtPath:path usingResourceFork:rfFlag];
71 | size += [dict zk_totalFileSize];
72 | count += [dict zk_itemCount];
73 | }
74 | [self performSelectorOnMainThread:@selector(didUpdateTotalSize:)
75 | withObject:[NSNumber numberWithUnsignedLongLong:size] waitUntilDone:NO];
76 | [self performSelectorOnMainThread:@selector(didUpdateTotalCount:)
77 | withObject:[NSNumber numberWithUnsignedLongLong:count] waitUntilDone:NO];
78 | }
79 |
80 | - (NSString *) uniqueExpansionDirectoryIn:(NSString *) enclosingFolder {
81 | NSString *expansionDirectory = [enclosingFolder stringByAppendingPathComponent:ZKExpansionDirectoryName];
82 | NSUInteger i = 1;
83 | while ([self.fileManager fileExistsAtPath:expansionDirectory]) {
84 | expansionDirectory = [enclosingFolder stringByAppendingPathComponent:
85 | [NSString stringWithFormat:@"%@ %u", ZKExpansionDirectoryName, i++]];
86 | }
87 | return expansionDirectory;
88 | }
89 |
90 | - (void) cleanUpExpansionDirectory:(NSString *) expansionDirectory {
91 | NSString *enclosingFolder = [expansionDirectory stringByDeletingLastPathComponent];
92 | NSArray *dirContents = [self.fileManager contentsOfDirectoryAtPath:expansionDirectory error:nil];
93 | for (NSString *item in dirContents) {
94 | if (![item isEqualToString:ZKMacOSXDirectory]) {
95 | NSString *subPath = [expansionDirectory stringByAppendingPathComponent:item];
96 | NSString *dest = [enclosingFolder stringByAppendingPathComponent:item];
97 | NSUInteger i = 2;
98 | while ([self.fileManager fileExistsAtPath:dest]) {
99 | NSString *ext = [item pathExtension];
100 | dest = [enclosingFolder stringByAppendingPathComponent:[NSString stringWithFormat:@"%@ %u",
101 | [item stringByDeletingPathExtension], i++]];
102 | if (ext && [ext length] > 0)
103 | dest = [dest stringByAppendingPathExtension:ext];
104 | }
105 | [self.fileManager moveItemAtPath:subPath toPath:dest error:nil];
106 | }
107 | }
108 | [self.fileManager removeItemAtPath:expansionDirectory error:nil];
109 |
110 | }
111 |
112 | #pragma mark -
113 | #pragma mark Accessors
114 |
115 | - (NSString *) comment {
116 | return self.cdTrailer.comment;
117 | }
118 | - (void) setComment:(NSString *)comment {
119 | self.cdTrailer.comment = comment;
120 | }
121 |
122 | #pragma mark -
123 | #pragma mark Delegate
124 |
125 | - (void) setInvoker:(id)i {
126 | _invoker = i;
127 | if (_invoker) {
128 | irtsIsCancelled = [self.invoker respondsToSelector:@selector(isCancelled)];
129 | } else {
130 | irtsIsCancelled = NO;
131 | }
132 | }
133 |
134 | - (void) setDelegate:(id)d {
135 | _delegate = d;
136 | if (_delegate) {
137 | drtsDelegateWantsSizes = [_delegate respondsToSelector:@selector(zkDelegateWantsSizes)];
138 | drtsDidBeginZip = [_delegate respondsToSelector:@selector(onZKArchiveDidBeginZip:)];
139 | drtsDidBeginUnzip = [_delegate respondsToSelector:@selector(onZKArchiveDidBeginUnzip:)];
140 | drtsWillZipPath = [_delegate respondsToSelector:@selector(onZKArchive:willZipPath:)];
141 | drtsWillUnzipPath = [_delegate respondsToSelector:@selector(onZKArchive:willUnzipPath:)];
142 | drtsDidEndZip = [_delegate respondsToSelector:@selector(onZKArchiveDidEndZip:)];
143 | drtsDidEndUnzip = [_delegate respondsToSelector:@selector(onZKArchiveDidEndUnzip:)];
144 | drtsDidCancel = [_delegate respondsToSelector:@selector(onZKArchiveDidCancel:)];
145 | drtsDidFail = [_delegate respondsToSelector:@selector(onZKArchiveDidFail:)];
146 | drtsDidUpdateTotalSize = [_delegate respondsToSelector:@selector(onZKArchive:didUpdateTotalSize:)];
147 | drtsDidUpdateTotalCount = [_delegate respondsToSelector:@selector(onZKArchive:didUpdateTotalCount:)];
148 | drtsDidUpdateBytesWritten = [_delegate respondsToSelector:@selector(onZKArchive:didUpdateBytesWritten:)];
149 | } else {
150 | drtsDelegateWantsSizes = NO;
151 | drtsDidBeginZip = NO;
152 | drtsDidBeginUnzip = NO;
153 | drtsWillZipPath = NO;
154 | drtsWillUnzipPath = NO;
155 | drtsDidEndZip = NO;
156 | drtsDidEndUnzip = NO;
157 | drtsDidCancel = NO;
158 | drtsDidFail = NO;
159 | drtsDidUpdateTotalSize = NO;
160 | drtsDidUpdateTotalCount = NO;
161 | drtsDidUpdateBytesWritten = NO;
162 | }
163 | }
164 |
165 | - (BOOL) delegateWantsSizes {
166 | BOOL delegateWantsSizes = NO;
167 | if (drtsDelegateWantsSizes) {
168 | delegateWantsSizes = [self.delegate zkDelegateWantsSizes];
169 | }
170 | return delegateWantsSizes;
171 | }
172 |
173 | - (void) didBeginZip {
174 | if (drtsDidBeginZip)
175 | [self.delegate onZKArchiveDidBeginZip:self];
176 | }
177 |
178 | - (void) didBeginUnzip {
179 | if (drtsDidBeginUnzip)
180 | [self.delegate onZKArchiveDidBeginUnzip:self];
181 | }
182 |
183 | - (void) willZipPath:(NSString *) path {
184 | if (drtsWillZipPath)
185 | [self.delegate onZKArchive:self willZipPath:path];
186 | }
187 |
188 | - (void) willUnzipPath:(NSString *) path {
189 | if (drtsWillUnzipPath)
190 | [self.delegate onZKArchive:self willUnzipPath:path];
191 | }
192 |
193 | - (void) didEndZip {
194 | if (drtsDidEndZip)
195 | [self.delegate onZKArchiveDidEndZip:self];
196 | }
197 |
198 | - (void) didEndUnzip {
199 | if (drtsDidEndUnzip)
200 | [self.delegate onZKArchiveDidEndUnzip:self];
201 | }
202 |
203 | - (void) didCancel {
204 | if (drtsDidCancel)
205 | [self.delegate onZKArchiveDidCancel:self];
206 | }
207 |
208 | - (void) didFail {
209 | if (drtsDidFail)
210 | [self.delegate onZKArchiveDidFail:self];
211 | }
212 |
213 | - (void) didUpdateTotalSize:(NSNumber *) size {
214 | if (drtsDidUpdateTotalSize)
215 | [self.delegate onZKArchive:self didUpdateTotalSize:[size unsignedLongLongValue]];
216 | }
217 |
218 | - (void) didUpdateTotalCount:(NSNumber *) count {
219 | if (drtsDidUpdateTotalCount)
220 | [self.delegate onZKArchive:self didUpdateTotalCount:[count unsignedLongLongValue]];
221 | }
222 |
223 | - (void) didUpdateBytesWritten:(NSNumber *) byteCount {
224 | if (drtsDidUpdateBytesWritten)
225 | [self.delegate onZKArchive:self didUpdateBytesWritten:[byteCount unsignedLongLongValue]];
226 | }
227 |
228 | #pragma mark -
229 | #pragma mark Setup
230 |
231 | - (id) init {
232 | if (self = [super init]) {
233 | self.invoker = nil;
234 | self.delegate = nil;
235 | self.archivePath = nil;
236 | self.centralDirectory = [NSMutableArray array];
237 | self.fileManager = [[NSFileManager new] autorelease];
238 | self.cdTrailer = [[ZKCDTrailer new] autorelease];
239 | self.throttleThreadSleepTime = 0.0;
240 | }
241 | return self;
242 | }
243 |
244 | - (void) dealloc {
245 | self.invoker = nil;
246 | self.delegate = nil;
247 | self.archivePath = nil;
248 | self.centralDirectory = nil;
249 | self.fileManager = nil;
250 | self.cdTrailer = nil;
251 | [super dealloc];
252 | }
253 |
254 | - (NSString *) description {
255 | return [NSString stringWithFormat: @"%@\n\ttrailer:%@\n\tcentral directory:%@", self.archivePath, self.cdTrailer, self.centralDirectory];
256 | }
257 |
258 | @synthesize invoker = _invoker, delegate = _delegate, archivePath = _archivePath, centralDirectory = _centralDirectory, fileManager = _fileManager, cdTrailer = _cdTrailer, throttleThreadSleepTime = _throttleThreadSleepTime;
259 | @dynamic comment;
260 |
261 | @end
262 |
--------------------------------------------------------------------------------
/External/ZipKit/ZKCDHeader.h:
--------------------------------------------------------------------------------
1 | //
2 | // ZKCDHeader.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 |
10 | @interface ZKCDHeader : NSObject {
11 | @private
12 | NSUInteger magicNumber;
13 | NSUInteger versionMadeBy;
14 | NSUInteger versionNeededToExtract;
15 | NSUInteger generalPurposeBitFlag;
16 | NSUInteger compressionMethod;
17 | NSDate *lastModDate;
18 | NSUInteger crc;
19 | unsigned long long compressedSize;
20 | unsigned long long uncompressedSize;
21 | NSUInteger filenameLength;
22 | NSUInteger extraFieldLength;
23 | NSUInteger commentLength;
24 | NSUInteger diskNumberStart;
25 | NSUInteger internalFileAttributes;
26 | NSUInteger externalFileAttributes;
27 | unsigned long long localHeaderOffset;
28 | NSString *filename;
29 | NSData *extraField;
30 | NSString *comment;
31 | NSMutableData *cachedData;
32 | }
33 |
34 | + (ZKCDHeader *) recordWithData:(NSData *)data atOffset:(NSUInteger)offset;
35 | + (ZKCDHeader *) recordWithArchivePath:(NSString *)path atOffset:(unsigned long long)offset;
36 | - (void) parseZip64ExtraField;
37 | - (NSData *) zip64ExtraField;
38 | - (NSData *) data;
39 | - (NSUInteger) length;
40 | - (BOOL) useZip64Extensions;
41 | - (NSNumber *) posixPermissions;
42 | - (BOOL) isDirectory;
43 | - (BOOL) isSymLink;
44 | - (BOOL) isResourceFork;
45 |
46 | @property (assign) NSUInteger magicNumber;
47 | @property (assign) NSUInteger versionMadeBy;
48 | @property (assign) NSUInteger versionNeededToExtract;
49 | @property (assign) NSUInteger generalPurposeBitFlag;
50 | @property (assign) NSUInteger compressionMethod;
51 | @property (retain) NSDate *lastModDate;
52 | @property (assign) NSUInteger crc;
53 | @property (assign) unsigned long long compressedSize;
54 | @property (assign) unsigned long long uncompressedSize;
55 | @property (assign) NSUInteger filenameLength;
56 | @property (assign) NSUInteger extraFieldLength;
57 | @property (assign) NSUInteger commentLength;
58 | @property (assign) NSUInteger diskNumberStart;
59 | @property (assign) NSUInteger internalFileAttributes;
60 | @property (assign) NSUInteger externalFileAttributes;
61 | @property (assign) unsigned long long localHeaderOffset;
62 | @property (copy) NSString *filename;
63 | @property (retain) NSData *extraField;
64 | @property (copy) NSString *comment;
65 | @property (retain) NSMutableData *cachedData;
66 |
67 | @end
--------------------------------------------------------------------------------
/External/ZipKit/ZKCDHeader.m:
--------------------------------------------------------------------------------
1 | //
2 | // ZKCDHeader.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "ZKCDHeader.h"
9 | #import "NSDate+ZKAdditions.h"
10 | #import "NSData+ZKAdditions.h"
11 | #import "NSString+ZKAdditions.h"
12 | #import "ZKDefs.h"
13 | #import "zlib.h"
14 |
15 | @implementation ZKCDHeader
16 |
17 | - (id) init {
18 | if (self = [super init]) {
19 | self.magicNumber = ZKCDHeaderMagicNumber;
20 | self.versionNeededToExtract = 20;
21 | self.versionMadeBy = 789;
22 | self.generalPurposeBitFlag = 0;
23 | self.compressionMethod = Z_DEFLATED;
24 | self.lastModDate = [NSDate date];
25 | self.crc = 0;
26 | self.compressedSize = 0;
27 | self.uncompressedSize = 0;
28 | self.filenameLength = 0;
29 | self.extraFieldLength = 0;
30 | self.commentLength = 0;
31 | self.diskNumberStart = 0;
32 | self.internalFileAttributes = 0;
33 | self.externalFileAttributes = 0;
34 | self.localHeaderOffset = 0;
35 | self.extraField = nil;
36 | self.comment = nil;
37 |
38 | [self addObserver:self forKeyPath:@"compressedSize" options:NSKeyValueObservingOptionNew context:nil];
39 | [self addObserver:self forKeyPath:@"uncompressedSize" options:NSKeyValueObservingOptionNew context:nil];
40 | [self addObserver:self forKeyPath:@"localHeaderOffset" options:NSKeyValueObservingOptionNew context:nil];
41 | [self addObserver:self forKeyPath:@"extraField" options:NSKeyValueObservingOptionNew context:nil];
42 | [self addObserver:self forKeyPath:@"filename" options:NSKeyValueObservingOptionNew context:nil];
43 | [self addObserver:self forKeyPath:@"comment" options:NSKeyValueObservingOptionNew context:nil];
44 | }
45 | return self;
46 | }
47 |
48 | - (void) removeObservers {
49 | [self removeObserver:self forKeyPath:@"compressedSize"];
50 | [self removeObserver:self forKeyPath:@"uncompressedSize"];
51 | [self removeObserver:self forKeyPath:@"localHeaderOffset"];
52 | [self removeObserver:self forKeyPath:@"extraField"];
53 | [self removeObserver:self forKeyPath:@"filename"];
54 | [self removeObserver:self forKeyPath:@"comment"];
55 | }
56 |
57 | - (void) dealloc {
58 | [self removeObservers];
59 | self.cachedData = nil;
60 | self.lastModDate = nil;
61 | self.filename = nil;
62 | self.extraField = nil;
63 | self.comment = nil;
64 | [super dealloc];
65 | }
66 |
67 | - (void) finalize {
68 | self.cachedData = nil;
69 | [self removeObservers];
70 | [super finalize];
71 | }
72 |
73 | - (void) observeValueForKeyPath:(NSString *) keyPath ofObject:(id) object change:(NSDictionary *) change context:(void *) context {
74 | if ([keyPath isEqualToString:@"compressedSize"]
75 | || [keyPath isEqualToString:@"uncompressedSize"]
76 | || [keyPath isEqualToString:@"localHeaderOffset"]) {
77 | self.versionNeededToExtract = ([self useZip64Extensions] ? 45 : 20);
78 | } else if ([keyPath isEqualToString:@"extraField"] && self.extraFieldLength < 1) {
79 | self.extraFieldLength = [self.extraField length];
80 | } else if ([keyPath isEqualToString:@"filename"] && self.filenameLength < 1) {
81 | self.filenameLength = [self.filename zk_precomposedUTF8Length];
82 | } else if ([keyPath isEqualToString:@"comment"] && self.commentLength < 1) {
83 | self.commentLength = [self.comment zk_precomposedUTF8Length];
84 | }
85 | }
86 |
87 | + (ZKCDHeader *) recordWithData:(NSData *)data atOffset:(NSUInteger)offset {
88 | if (!data) return nil;
89 | NSUInteger mn = [data zk_hostInt32OffsetBy:&offset];
90 | if (mn != ZKCDHeaderMagicNumber) return nil;
91 | ZKCDHeader *record = [[ZKCDHeader new] autorelease];
92 | record.magicNumber = mn;
93 | record.versionMadeBy = [data zk_hostInt16OffsetBy:&offset];
94 | record.versionNeededToExtract = [data zk_hostInt16OffsetBy:&offset];
95 | record.generalPurposeBitFlag = [data zk_hostInt16OffsetBy:&offset];
96 | record.compressionMethod = [data zk_hostInt16OffsetBy:&offset];
97 | record.lastModDate = [NSDate zk_dateWithDosDate:[data zk_hostInt32OffsetBy:&offset]];
98 | record.crc = [data zk_hostInt32OffsetBy:&offset];
99 | record.compressedSize = [data zk_hostInt32OffsetBy:&offset];
100 | record.uncompressedSize = [data zk_hostInt32OffsetBy:&offset];
101 | record.filenameLength = [data zk_hostInt16OffsetBy:&offset];
102 | record.extraFieldLength = [data zk_hostInt16OffsetBy:&offset];
103 | record.commentLength = [data zk_hostInt16OffsetBy:&offset];
104 | record.diskNumberStart = [data zk_hostInt16OffsetBy:&offset];
105 | record.internalFileAttributes = [data zk_hostInt16OffsetBy:&offset];
106 | record.externalFileAttributes = [data zk_hostInt32OffsetBy:&offset];
107 | record.localHeaderOffset = [data zk_hostInt32OffsetBy:&offset];
108 | if ([data length] > ZKCDHeaderFixedDataLength) {
109 | if (record.filenameLength)
110 | record.filename = [data zk_stringOffsetBy:&offset length:record.filenameLength];
111 | if (record.extraFieldLength) {
112 | record.extraField = [data subdataWithRange:NSMakeRange(offset, record.extraFieldLength)];
113 | offset += record.extraFieldLength;
114 | [record parseZip64ExtraField];
115 | }
116 | if (record.commentLength)
117 | record.comment = [data zk_stringOffsetBy:&offset length:record.commentLength];
118 | }
119 | return record;
120 | }
121 |
122 | + (ZKCDHeader *) recordWithArchivePath:(NSString *)path atOffset:(unsigned long long)offset {
123 | NSFileHandle *file = [NSFileHandle fileHandleForReadingAtPath:path];
124 | [file seekToFileOffset:offset];
125 | NSData *fixedData = [file readDataOfLength:ZKCDHeaderFixedDataLength];
126 | ZKCDHeader *record = [self recordWithData:fixedData atOffset:0];
127 | if (record.filenameLength > 0) {
128 | NSData *data = [file readDataOfLength:record.filenameLength];
129 | record.filename = [[[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding] autorelease];
130 | }
131 | if (record.extraFieldLength > 0) {
132 | record.extraField = [file readDataOfLength:record.extraFieldLength];
133 | [record parseZip64ExtraField];
134 | }
135 | if (record.commentLength > 0) {
136 | NSData *data = [file readDataOfLength:record.commentLength];
137 | record.comment = [[[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding] autorelease];
138 | } else
139 | record.comment = nil;
140 |
141 | [file closeFile];
142 | return record;
143 | }
144 |
145 | - (NSData *) data {
146 | if (!self.cachedData || ([self.cachedData length] < ZKCDHeaderFixedDataLength)) {
147 | self.extraField = [self zip64ExtraField];
148 |
149 | self.cachedData = [NSMutableData zk_dataWithLittleInt32:self.magicNumber];
150 | [self.cachedData zk_appendLittleInt16:self.versionMadeBy];
151 | [self.cachedData zk_appendLittleInt16:self.versionNeededToExtract];
152 | [self.cachedData zk_appendLittleInt16:self.generalPurposeBitFlag];
153 | [self.cachedData zk_appendLittleInt16:self.compressionMethod];
154 | [self.cachedData zk_appendLittleInt32:[self.lastModDate zk_dosDate]];
155 | [self.cachedData zk_appendLittleInt32:self.crc];
156 | if ([self useZip64Extensions]) {
157 | [self.cachedData zk_appendLittleInt32:0xFFFFFFFF];
158 | [self.cachedData zk_appendLittleInt32:0xFFFFFFFF];
159 | } else {
160 | [self.cachedData zk_appendLittleInt32:self.compressedSize];
161 | [self.cachedData zk_appendLittleInt32:self.uncompressedSize];
162 | }
163 | [self.cachedData zk_appendLittleInt16:[self.filename zk_precomposedUTF8Length]];
164 | [self.cachedData zk_appendLittleInt16:[self.extraField length]];
165 | [self.cachedData zk_appendLittleInt16:[self.comment zk_precomposedUTF8Length]];
166 | [self.cachedData zk_appendLittleInt16:self.diskNumberStart];
167 | [self.cachedData zk_appendLittleInt16:self.internalFileAttributes];
168 | [self.cachedData zk_appendLittleInt32:self.externalFileAttributes];
169 | if ([self useZip64Extensions])
170 | [self.cachedData zk_appendLittleInt32:0xFFFFFFFF];
171 | else
172 | [self.cachedData zk_appendLittleInt32:self.localHeaderOffset];
173 | [self.cachedData zk_appendPrecomposedUTF8String:self.filename];
174 | [self.cachedData appendData:self.extraField];
175 | [self.cachedData zk_appendPrecomposedUTF8String:self.comment];
176 | }
177 | return self.cachedData;
178 | }
179 |
180 | - (void) parseZip64ExtraField {
181 | NSUInteger offset = 0, tag, length;
182 | while (offset < self.extraFieldLength) {
183 | tag = [self.extraField zk_hostInt16OffsetBy:&offset];
184 | length = [self.extraField zk_hostInt16OffsetBy:&offset];
185 | if (tag == 0x0001) {
186 | if (length >= 8)
187 | self.uncompressedSize = [self.extraField zk_hostInt64OffsetBy:&offset];
188 | if (length >= 16)
189 | self.compressedSize = [self.extraField zk_hostInt64OffsetBy:&offset];
190 | if (length >= 24)
191 | self.localHeaderOffset = [self.extraField zk_hostInt64OffsetBy:&offset];
192 | break;
193 | } else {
194 | offset += length;
195 | }
196 | }
197 | }
198 |
199 | - (NSData *) zip64ExtraField {
200 | NSMutableData *zip64ExtraField = nil;
201 | if ([self useZip64Extensions]) {
202 | zip64ExtraField = [NSMutableData zk_dataWithLittleInt16:0x0001];
203 | [zip64ExtraField zk_appendLittleInt16:24];
204 | [zip64ExtraField zk_appendLittleInt64:self.uncompressedSize];
205 | [zip64ExtraField zk_appendLittleInt64:self.compressedSize];
206 | [zip64ExtraField zk_appendLittleInt64:self.localHeaderOffset];
207 | }
208 | return zip64ExtraField;
209 | }
210 |
211 | - (NSUInteger) length {
212 | if (!self.extraField || [self.extraField length] == 0)
213 | self.extraField = [self zip64ExtraField];
214 | return ZKCDHeaderFixedDataLength + self.filenameLength + self.commentLength + [self.extraField length];
215 | }
216 |
217 | - (BOOL) useZip64Extensions {
218 | return (self.uncompressedSize >= 0xFFFFFFFF) || (self.compressedSize >= 0xFFFFFFFF) || (self.localHeaderOffset >= 0xFFFFFFFF);
219 | }
220 |
221 | - (NSString *) description {
222 | return [NSString stringWithFormat:@"%@ modified %@, %qu bytes (%qu compressed), @ %qu",
223 | self.filename, self.lastModDate, self.uncompressedSize, self.compressedSize, self.localHeaderOffset];
224 | }
225 |
226 | - (NSNumber *) posixPermissions {
227 | // if posixPermissions are 0, e.g. on Windows-produced archives, then default them to rwxr-wr-w a la Archive Utility
228 | return [NSNumber numberWithUnsignedInteger:(self.externalFileAttributes >> 16 & 0x1FF) ?: 0755U];
229 | }
230 |
231 | - (BOOL) isDirectory {
232 | uLong type = self.externalFileAttributes >> 29 & 0x1F;
233 | return (0x02 == type) && ![self isSymLink];
234 | }
235 |
236 | - (BOOL) isSymLink {
237 | uLong type = self.externalFileAttributes >> 29 & 0x1F;
238 | return (0x05 == type);
239 | }
240 |
241 | - (BOOL) isResourceFork {
242 | return [self.filename zk_isResourceForkPath];
243 | }
244 |
245 | @synthesize magicNumber, versionNeededToExtract, versionMadeBy, generalPurposeBitFlag, compressionMethod, lastModDate, crc, compressedSize, uncompressedSize, filenameLength, extraFieldLength, commentLength, diskNumberStart, internalFileAttributes, externalFileAttributes, localHeaderOffset, filename, extraField, comment, cachedData;
246 |
247 | @end
248 |
--------------------------------------------------------------------------------
/External/ZipKit/ZKCDTrailer.h:
--------------------------------------------------------------------------------
1 | //
2 | // ZKCDTrailer.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 |
10 | @interface ZKCDTrailer : NSObject {
11 | @private
12 | NSUInteger magicNumber;
13 | NSUInteger thisDiskNumber;
14 | NSUInteger diskNumberWithStartOfCentralDirectory;
15 | NSUInteger numberOfCentralDirectoryEntriesOnThisDisk;
16 | NSUInteger totalNumberOfCentralDirectoryEntries;
17 | unsigned long long sizeOfCentralDirectory;
18 | unsigned long long offsetOfStartOfCentralDirectory;
19 | NSUInteger commentLength;
20 | NSString *comment;
21 | }
22 |
23 | + (ZKCDTrailer *) recordWithData:(NSData *)data atOffset:(NSUInteger) offset;
24 | + (ZKCDTrailer *) recordWithData:(NSData *)data;
25 | + (ZKCDTrailer *) recordWithArchivePath:(NSString *) path;
26 | - (NSData *) data;
27 | - (NSUInteger) length;
28 | - (BOOL) useZip64Extensions;
29 |
30 | @property (assign) NSUInteger magicNumber;
31 | @property (assign) NSUInteger thisDiskNumber;
32 | @property (assign) NSUInteger diskNumberWithStartOfCentralDirectory;
33 | @property (assign) NSUInteger numberOfCentralDirectoryEntriesOnThisDisk;
34 | @property (assign) NSUInteger totalNumberOfCentralDirectoryEntries;
35 | @property (assign) unsigned long long sizeOfCentralDirectory;
36 | @property (assign) unsigned long long offsetOfStartOfCentralDirectory;
37 | @property (assign) NSUInteger commentLength;
38 | @property (copy) NSString *comment;
39 |
40 | @end
--------------------------------------------------------------------------------
/External/ZipKit/ZKCDTrailer.m:
--------------------------------------------------------------------------------
1 | //
2 | // ZKCDTrailer.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "ZKCDTrailer.h"
9 | #import "NSData+ZKAdditions.h"
10 | #import "NSString+ZKAdditions.h"
11 | #import "ZKDefs.h"
12 | #import "zlib.h"
13 |
14 | @implementation ZKCDTrailer
15 |
16 | - (id) init {
17 | if (self = [super init]) {
18 | [self addObserver:self forKeyPath:@"comment" options:NSKeyValueObservingOptionNew context:nil];
19 |
20 | self.magicNumber = ZKCDTrailerMagicNumber;
21 | self.thisDiskNumber = 0;
22 | self.diskNumberWithStartOfCentralDirectory = 0;
23 | self.numberOfCentralDirectoryEntriesOnThisDisk = 0;
24 | self.totalNumberOfCentralDirectoryEntries = 0;
25 | self.sizeOfCentralDirectory = 0;
26 | self.offsetOfStartOfCentralDirectory = 0;
27 | self.comment = @"Archive created with ZipKit";
28 | }
29 | return self;
30 | }
31 |
32 | - (void) removeObservers {
33 | [self removeObserver:self forKeyPath:@"comment"];
34 | }
35 |
36 | - (void) finalize {
37 | [self removeObservers];
38 | [super finalize];
39 | }
40 |
41 | - (void) dealloc {
42 | [self removeObservers];
43 | self.comment = nil;
44 | [super dealloc];
45 | }
46 |
47 |
48 | - (void) observeValueForKeyPath:(NSString *) keyPath ofObject:(id) object change:(NSDictionary *) change context:(void *) context {
49 | if ([keyPath isEqualToString:@"comment"] && self.commentLength < 1) {
50 | self.commentLength = [self.comment zk_precomposedUTF8Length];
51 | }
52 | }
53 |
54 | + (ZKCDTrailer *) recordWithData:(NSData *)data atOffset:(NSUInteger) offset {
55 | NSUInteger mn = [data zk_hostInt32OffsetBy:&offset];
56 | if (mn != ZKCDTrailerMagicNumber) return nil;
57 | ZKCDTrailer *record = [[ZKCDTrailer new] autorelease];
58 | record.magicNumber = mn;
59 | record.thisDiskNumber = [data zk_hostInt16OffsetBy:&offset];
60 | record.diskNumberWithStartOfCentralDirectory = [data zk_hostInt16OffsetBy:&offset];
61 | record.numberOfCentralDirectoryEntriesOnThisDisk = [data zk_hostInt16OffsetBy:&offset];
62 | record.totalNumberOfCentralDirectoryEntries = [data zk_hostInt16OffsetBy:&offset];
63 | record.sizeOfCentralDirectory = [data zk_hostInt32OffsetBy:&offset];
64 | record.offsetOfStartOfCentralDirectory = [data zk_hostInt32OffsetBy:&offset];
65 | record.commentLength = [data zk_hostInt16OffsetBy:&offset];
66 | if (record.commentLength > 0)
67 | record.comment = [data zk_stringOffsetBy:&offset length:record.commentLength];
68 | else
69 | record.comment = nil;
70 | return record;
71 | }
72 |
73 | + (ZKCDTrailer *) recordWithData:(NSData *)data {
74 | UInt32 trailerCheck = 0;
75 | NSInteger offset = [data length] - sizeof(trailerCheck);
76 | while (trailerCheck != ZKCDTrailerMagicNumber && offset > 0) {
77 | NSUInteger o = offset;
78 | trailerCheck = [data zk_hostInt32OffsetBy:&o];
79 | offset--;
80 | }
81 | if (offset < 1)
82 | return nil;
83 | ZKCDTrailer *record = [self recordWithData:data atOffset:++offset];
84 | return record;
85 | }
86 |
87 | + (ZKCDTrailer *) recordWithArchivePath:(NSString *)path {
88 | NSFileHandle *file = [NSFileHandle fileHandleForReadingAtPath:path];
89 | unsigned long long fileOffset = [file seekToEndOfFile];
90 | for (UInt32 trailerCheck = 0; trailerCheck != ZKCDTrailerMagicNumber && fileOffset > 0; fileOffset--) {
91 | [file seekToFileOffset:fileOffset];
92 | NSData *data = [file readDataOfLength:sizeof(UInt32)];
93 | [data getBytes:&trailerCheck length:sizeof(UInt32)];
94 | }
95 | if (fileOffset < 1) {
96 | [file closeFile];
97 | return nil;
98 | }
99 | fileOffset++;
100 | [file seekToFileOffset:fileOffset];
101 | NSData *data = [file readDataToEndOfFile];
102 | [file closeFile];
103 | ZKCDTrailer *record = [self recordWithData:data atOffset:(NSUInteger) 0];
104 | return record;
105 | }
106 |
107 | - (NSData *) data {
108 | NSMutableData *data = [NSMutableData zk_dataWithLittleInt32:self.magicNumber];
109 | [data zk_appendLittleInt16:self.thisDiskNumber];
110 | [data zk_appendLittleInt16:self.diskNumberWithStartOfCentralDirectory];
111 | [data zk_appendLittleInt16:self.numberOfCentralDirectoryEntriesOnThisDisk];
112 | [data zk_appendLittleInt16:self.totalNumberOfCentralDirectoryEntries];
113 | if ([self useZip64Extensions]) {
114 | [data zk_appendLittleInt32:0xFFFFFFFF];
115 | [data zk_appendLittleInt32:0xFFFFFFFF];
116 | } else {
117 | [data zk_appendLittleInt32:self.sizeOfCentralDirectory];
118 | [data zk_appendLittleInt32:self.offsetOfStartOfCentralDirectory];
119 | }
120 | [data zk_appendLittleInt16:[self.comment zk_precomposedUTF8Length]];
121 | [data zk_appendPrecomposedUTF8String:self.comment];
122 | return data;
123 | }
124 |
125 | - (NSUInteger) length {
126 | return ZKCDTrailerFixedDataLength + [self.comment length];
127 | }
128 |
129 | - (BOOL) useZip64Extensions {
130 | return (self.sizeOfCentralDirectory >= 0xFFFFFFFF) || (self.offsetOfStartOfCentralDirectory >= 0xFFFFFFFF);
131 | }
132 |
133 | - (NSString *) description {
134 | return [NSString stringWithFormat:@"%u entries (%qu bytes) @: %qu",
135 | self.totalNumberOfCentralDirectoryEntries,
136 | self.sizeOfCentralDirectory,
137 | self.offsetOfStartOfCentralDirectory];
138 | }
139 |
140 | @synthesize magicNumber, thisDiskNumber, diskNumberWithStartOfCentralDirectory, numberOfCentralDirectoryEntriesOnThisDisk, totalNumberOfCentralDirectoryEntries, sizeOfCentralDirectory, offsetOfStartOfCentralDirectory, commentLength, comment;
141 |
142 | @end
143 |
--------------------------------------------------------------------------------
/External/ZipKit/ZKCDTrailer64.h:
--------------------------------------------------------------------------------
1 | //
2 | // ZKCDTrailer64.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 |
10 | @interface ZKCDTrailer64 : NSObject {
11 | @private
12 | NSUInteger magicNumber;
13 | unsigned long long sizeOfTrailer;
14 | NSUInteger versionMadeBy;
15 | NSUInteger versionNeededToExtract;
16 | NSUInteger thisDiskNumber;
17 | NSUInteger diskNumberWithStartOfCentralDirectory;
18 | unsigned long long numberOfCentralDirectoryEntriesOnThisDisk;
19 | unsigned long long totalNumberOfCentralDirectoryEntries;
20 | unsigned long long sizeOfCentralDirectory;
21 | unsigned long long offsetOfStartOfCentralDirectory;
22 | }
23 |
24 | + (ZKCDTrailer64 *) recordWithData:(NSData *)data atOffset:(NSUInteger)offset;
25 | + (ZKCDTrailer64 *) recordWithArchivePath:(NSString *)path atOffset:(unsigned long long)offset;
26 |
27 | - (NSData *) data;
28 | - (NSUInteger) length;
29 |
30 | @property (assign) NSUInteger magicNumber;
31 | @property (assign) unsigned long long sizeOfTrailer;
32 | @property (assign) NSUInteger versionMadeBy;
33 | @property (assign) NSUInteger versionNeededToExtract;
34 | @property (assign) NSUInteger thisDiskNumber;
35 | @property (assign) NSUInteger diskNumberWithStartOfCentralDirectory;
36 | @property (assign) unsigned long long numberOfCentralDirectoryEntriesOnThisDisk;
37 | @property (assign) unsigned long long totalNumberOfCentralDirectoryEntries;
38 | @property (assign) unsigned long long sizeOfCentralDirectory;
39 | @property (assign) unsigned long long offsetOfStartOfCentralDirectory;
40 |
41 | @end
--------------------------------------------------------------------------------
/External/ZipKit/ZKCDTrailer64.m:
--------------------------------------------------------------------------------
1 | //
2 | // ZKCDTrailer64.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "ZKCDTrailer64.h"
9 | #import "NSData+ZKAdditions.h"
10 | #import "ZKDefs.h"
11 |
12 | @implementation ZKCDTrailer64
13 |
14 | - (id) init {
15 | if (self = [super init]) {
16 | self.magicNumber = ZKCDTrailer64MagicNumber;
17 | self.sizeOfTrailer = 44;
18 | self.versionMadeBy = 789;
19 | self.versionNeededToExtract = 45;
20 | self.thisDiskNumber = 0;
21 | self.diskNumberWithStartOfCentralDirectory = 0;
22 | }
23 | return self;
24 | }
25 |
26 | + (ZKCDTrailer64 *) recordWithData:(NSData *)data atOffset:(NSUInteger)offset {
27 | if (!data) return nil;
28 | NSUInteger mn = [data zk_hostInt32OffsetBy:&offset];
29 | if (mn != ZKCDTrailer64MagicNumber) return nil;
30 | ZKCDTrailer64 *record = [[ZKCDTrailer64 new] autorelease];
31 | record.magicNumber = mn;
32 | record.sizeOfTrailer = [data zk_hostInt64OffsetBy:&offset];
33 | record.versionMadeBy = [data zk_hostInt16OffsetBy:&offset];
34 | record.versionNeededToExtract = [data zk_hostInt16OffsetBy:&offset];
35 | record.thisDiskNumber = [data zk_hostInt32OffsetBy:&offset];
36 | record.diskNumberWithStartOfCentralDirectory = [data zk_hostInt32OffsetBy:&offset];
37 | record.numberOfCentralDirectoryEntriesOnThisDisk = [data zk_hostInt64OffsetBy:&offset];
38 | record.totalNumberOfCentralDirectoryEntries = [data zk_hostInt64OffsetBy:&offset];
39 | record.sizeOfCentralDirectory = [data zk_hostInt64OffsetBy:&offset];
40 | record.offsetOfStartOfCentralDirectory = [data zk_hostInt64OffsetBy:&offset];
41 | return record;
42 | }
43 |
44 | + (ZKCDTrailer64 *) recordWithArchivePath:(NSString *)path atOffset:(unsigned long long)offset {
45 | NSFileHandle *file = [NSFileHandle fileHandleForReadingAtPath:path];
46 | [file seekToFileOffset:offset];
47 | NSData *data = [file readDataOfLength:ZKCDTrailer64FixedDataLength];
48 | [file closeFile];
49 | ZKCDTrailer64 *record = [self recordWithData:data atOffset:0];
50 | return record;
51 | }
52 |
53 | - (NSData *) data {
54 | NSMutableData *data = [NSMutableData zk_dataWithLittleInt32:self.magicNumber];
55 | [data zk_appendLittleInt64:self.sizeOfTrailer];
56 | [data zk_appendLittleInt16:self.versionMadeBy];
57 | [data zk_appendLittleInt16:self.versionNeededToExtract];
58 | [data zk_appendLittleInt32:self.thisDiskNumber];
59 | [data zk_appendLittleInt32:self.diskNumberWithStartOfCentralDirectory];
60 | [data zk_appendLittleInt64:self.numberOfCentralDirectoryEntriesOnThisDisk];
61 | [data zk_appendLittleInt64:self.totalNumberOfCentralDirectoryEntries];
62 | [data zk_appendLittleInt64:self.sizeOfCentralDirectory];
63 | [data zk_appendLittleInt64:self.offsetOfStartOfCentralDirectory];
64 | return data;
65 | }
66 |
67 | - (NSUInteger) length {
68 | return ZKCDTrailer64FixedDataLength;
69 | }
70 |
71 | - (NSString *) description {
72 | return [NSString stringWithFormat:@"%qu entries @ offset of CD: %qu (%qu bytes)",
73 | self.numberOfCentralDirectoryEntriesOnThisDisk,
74 | self.offsetOfStartOfCentralDirectory,
75 | self.sizeOfCentralDirectory];
76 | }
77 |
78 | @synthesize magicNumber, sizeOfTrailer, versionMadeBy, versionNeededToExtract, thisDiskNumber, diskNumberWithStartOfCentralDirectory, numberOfCentralDirectoryEntriesOnThisDisk, totalNumberOfCentralDirectoryEntries, sizeOfCentralDirectory, offsetOfStartOfCentralDirectory;
79 |
80 | @end
81 |
--------------------------------------------------------------------------------
/External/ZipKit/ZKCDTrailer64Locator.h:
--------------------------------------------------------------------------------
1 | //
2 | // ZKCDTrailer64Locator.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 |
10 | @interface ZKCDTrailer64Locator : NSObject {
11 | @private
12 | NSUInteger magicNumber;
13 | NSUInteger diskNumberWithStartOfCentralDirectory;
14 | unsigned long long offsetOfStartOfCentralDirectoryTrailer64;
15 | NSUInteger numberOfDisks;
16 | }
17 |
18 | + (ZKCDTrailer64Locator *) recordWithData:(NSData *)data atOffset:(NSUInteger) offset;
19 | + (ZKCDTrailer64Locator *) recordWithArchivePath:(NSString *)path andCDTrailerLength:(NSUInteger)cdTrailerLength;
20 |
21 | - (NSData *) data;
22 | - (NSUInteger) length;
23 |
24 | @property (assign) NSUInteger magicNumber;
25 | @property (assign) NSUInteger diskNumberWithStartOfCentralDirectory;
26 | @property (assign) unsigned long long offsetOfStartOfCentralDirectoryTrailer64;
27 | @property (assign) NSUInteger numberOfDisks;
28 |
29 | @end
--------------------------------------------------------------------------------
/External/ZipKit/ZKCDTrailer64Locator.m:
--------------------------------------------------------------------------------
1 | //
2 | // ZKCDTrailer64Locator.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "ZKCDTrailer64Locator.h"
9 | #import "NSData+ZKAdditions.h"
10 | #import "ZKDefs.h"
11 |
12 | @implementation ZKCDTrailer64Locator
13 |
14 | - (id) init {
15 | if (self = [super init]) {
16 | self.magicNumber = ZKCDTrailer64LocatorMagicNumber;
17 | self.diskNumberWithStartOfCentralDirectory = 0;
18 | self.numberOfDisks = 1;
19 | }
20 | return self;
21 | }
22 |
23 | + (ZKCDTrailer64Locator *) recordWithData:(NSData *)data atOffset:(NSUInteger) offset {
24 | NSUInteger mn = [data zk_hostInt32OffsetBy:&offset];
25 | if (mn != ZKCDTrailer64LocatorMagicNumber) return nil;
26 | ZKCDTrailer64Locator *record = [[ZKCDTrailer64Locator new] autorelease];
27 | record.magicNumber = mn;
28 | record.diskNumberWithStartOfCentralDirectory = [data zk_hostInt32OffsetBy:&offset];
29 | record.offsetOfStartOfCentralDirectoryTrailer64 = [data zk_hostInt64OffsetBy:&offset];
30 | record.numberOfDisks = [data zk_hostInt32OffsetBy:&offset];
31 | return record;
32 | }
33 |
34 | + (ZKCDTrailer64Locator *) recordWithArchivePath:(NSString *)path andCDTrailerLength:(NSUInteger)cdTrailerLength {
35 | NSFileHandle *file = [NSFileHandle fileHandleForReadingAtPath:path];
36 | unsigned long long fileOffset = [file seekToEndOfFile] - cdTrailerLength - ZKCDTrailer64LocatorFixedDataLength;
37 | [file seekToFileOffset:fileOffset];
38 | NSData *data = [file readDataOfLength:ZKCDTrailer64LocatorFixedDataLength];
39 | [file closeFile];
40 | ZKCDTrailer64Locator *record = [self recordWithData:data atOffset:0];
41 | return record;
42 | }
43 |
44 | - (NSData *) data {
45 | NSMutableData *data = [NSMutableData zk_dataWithLittleInt32:self.magicNumber];
46 | [data zk_appendLittleInt32:self.diskNumberWithStartOfCentralDirectory];
47 | [data zk_appendLittleInt64:self.offsetOfStartOfCentralDirectoryTrailer64];
48 | [data zk_appendLittleInt32:self.numberOfDisks];
49 | return data;
50 | }
51 |
52 | - (NSUInteger) length {
53 | return ZKCDTrailer64LocatorFixedDataLength;
54 | }
55 |
56 | - (NSString *) description {
57 | return [NSString stringWithFormat:@"offset of CD64: %qu", self.offsetOfStartOfCentralDirectoryTrailer64];
58 | }
59 |
60 | @synthesize magicNumber, diskNumberWithStartOfCentralDirectory, offsetOfStartOfCentralDirectoryTrailer64, numberOfDisks;
61 |
62 | @end
63 |
--------------------------------------------------------------------------------
/External/ZipKit/ZKDataArchive.h:
--------------------------------------------------------------------------------
1 | //
2 | // ZKDataArchive.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 07/05/09.
6 | //
7 |
8 | #import
9 | #import "ZKArchive.h"
10 |
11 | @class ZKCDHeader;
12 |
13 | @interface ZKDataArchive : ZKArchive {
14 | NSMutableData *_data;
15 | NSMutableArray *_inflatedFiles;
16 | }
17 |
18 | + (ZKDataArchive *) archiveWithArchivePath:(NSString *) path;
19 | + (ZKDataArchive *) archiveWithArchiveData:(NSMutableData *) archiveData;
20 | - (NSUInteger) inflateAll;
21 | - (NSData *) inflateFile:(ZKCDHeader *) cdHeader attributes:(NSDictionary **) fileAttributes;
22 | - (NSUInteger) inflateInFolder:(NSString *)enclosingFolder withFolderName:(NSString *)folderName usingResourceFork:(BOOL) rfFlag;
23 |
24 | - (NSInteger) deflateFiles:(NSArray *) paths relativeToPath:(NSString *) basePath usingResourceFork:(BOOL) flag;
25 | - (NSInteger) deflateDirectory:(NSString *) dirPath relativeToPath:(NSString *) basePath usingResourceFork:(BOOL) flag;
26 | - (NSInteger) deflateFile:(NSString *) path relativeToPath:(NSString *) basePath usingResourceFork:(BOOL) rfFlag;
27 | - (NSInteger) deflateData:(NSData *)data withFilename:(NSString *) filename andAttributes:(NSDictionary *) fileAttributes;
28 |
29 | @property (retain) NSMutableData *data;
30 | @property (retain) NSMutableArray *inflatedFiles;
31 |
32 | @end
--------------------------------------------------------------------------------
/External/ZipKit/ZKDataArchive.m:
--------------------------------------------------------------------------------
1 | //
2 | // ZKDataArchive.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 07/05/09.
6 | //
7 |
8 | #import "ZKDataArchive.h"
9 | #import "ZKCDHeader.h"
10 | #import "ZKCDTrailer.h"
11 | #import "ZKLFHeader.h"
12 | #import "NSData+ZKAdditions.h"
13 | #import "NSFileManager+ZKAdditions.h"
14 | #import "NSString+ZKAdditions.h"
15 | #import "ZKDefs.h"
16 | #import "zlib.h"
17 |
18 | #if ZK_TARGET_OS_MAC
19 | #import "GMAppleDouble+ZKAdditions.h"
20 | #endif
21 |
22 | @implementation ZKDataArchive
23 |
24 | + (ZKDataArchive *) archiveWithArchivePath:(NSString *) path {
25 | return [self archiveWithArchiveData:[NSMutableData dataWithContentsOfFile:path]];
26 | }
27 |
28 | + (ZKDataArchive *) archiveWithArchiveData:(NSMutableData *) archiveData {
29 | ZKDataArchive *archive = [[ZKDataArchive new] autorelease];
30 | archive.data = archiveData;
31 | archive.cdTrailer = [ZKCDTrailer recordWithData:archive.data];
32 | if (archive.cdTrailer) {
33 | unsigned long long offset = archive.cdTrailer.offsetOfStartOfCentralDirectory;
34 | for (NSUInteger i = 0; i < archive.cdTrailer.totalNumberOfCentralDirectoryEntries; i++) {
35 | ZKCDHeader *cdHeader = [ZKCDHeader recordWithData:archive.data atOffset:offset];
36 | [archive.centralDirectory addObject:cdHeader];
37 | offset += [cdHeader length];
38 | }
39 | } else {
40 | archive = nil;
41 | }
42 | return archive;
43 | }
44 |
45 | #pragma mark -
46 | #pragma mark Inflation
47 |
48 | - (NSUInteger) inflateAll {
49 | [self.inflatedFiles removeAllObjects];
50 | NSDictionary *fileAttributes = nil;
51 | NSData *inflatedData = nil;
52 | for (ZKCDHeader *cdHeader in self.centralDirectory) {
53 | inflatedData = [self inflateFile:cdHeader attributes:&fileAttributes];
54 | if (!inflatedData)
55 | return zkFailed;
56 |
57 | if ([cdHeader isSymLink] || [cdHeader isDirectory]) {
58 | [self.inflatedFiles addObject:[NSDictionary dictionaryWithObjectsAndKeys:
59 | fileAttributes, ZKFileAttributesKey,
60 | [[[NSString alloc] initWithData:inflatedData encoding:NSUTF8StringEncoding] autorelease], ZKPathKey,
61 | nil]];
62 | } else {
63 | [self.inflatedFiles addObject:[NSDictionary dictionaryWithObjectsAndKeys:
64 | inflatedData, ZKFileDataKey,
65 | fileAttributes, ZKFileAttributesKey,
66 | cdHeader.filename, ZKPathKey,
67 | nil]];
68 | }
69 | }
70 | return zkSucceeded;
71 | }
72 |
73 | - (NSData *) inflateFile:(ZKCDHeader *) cdHeader attributes:(NSDictionary **) fileAttributes {
74 | // if (self.delegate) {
75 | // if ([NSThread isMainThread])
76 | // [self willUnzipPath:cdHeader.filename];
77 | // else
78 | // [self performSelectorOnMainThread:@selector(willUnzipPath:) withObject:cdHeader.filename waitUntilDone:NO];
79 | // }
80 | BOOL isDirectory = [cdHeader isDirectory];
81 |
82 | ZKLFHeader *lfHeader = [ZKLFHeader recordWithData:self.data atOffset:cdHeader.localHeaderOffset];
83 |
84 | NSData *deflatedData = nil;
85 | if (!isDirectory)
86 | deflatedData = [self.data subdataWithRange:
87 | NSMakeRange(cdHeader.localHeaderOffset + [lfHeader length], cdHeader.compressedSize)];
88 |
89 | NSData *inflatedData = nil;
90 | NSString *fileType = nil;
91 | if ([cdHeader isSymLink]) {
92 | inflatedData = deflatedData; // UTF-8 encoded symlink destination path
93 | fileType = NSFileTypeSymbolicLink;
94 | } else if (isDirectory) {
95 | inflatedData = [cdHeader.filename dataUsingEncoding:NSUTF8StringEncoding];
96 | fileType = NSFileTypeDirectory;
97 | } else {
98 | if (cdHeader.compressionMethod == Z_NO_COMPRESSION)
99 | inflatedData = deflatedData;
100 | else
101 | inflatedData = [deflatedData zk_inflate];
102 | fileType = NSFileTypeRegular;
103 | }
104 |
105 | if (inflatedData)
106 | *fileAttributes = [NSDictionary dictionaryWithObjectsAndKeys:
107 | [cdHeader posixPermissions], NSFilePosixPermissions,
108 | [cdHeader lastModDate], NSFileCreationDate,
109 | [cdHeader lastModDate], NSFileModificationDate,
110 | fileType, NSFileType, nil];
111 | else
112 | *fileAttributes = nil;
113 |
114 | return inflatedData;
115 | }
116 |
117 | - (NSUInteger) inflateInFolder:(NSString *)enclosingFolder withFolderName:(NSString *)folderName usingResourceFork:(BOOL) rfFlag {
118 | if ([self inflateAll] != zkSucceeded)
119 | return zkFailed;
120 | if ([self.inflatedFiles count] < 1)
121 | return zkSucceeded;
122 |
123 | if (![self.fileManager fileExistsAtPath:enclosingFolder])
124 | return zkFailed;
125 |
126 | NSString *expansionDirectory = [self uniqueExpansionDirectoryIn:enclosingFolder];
127 | [self.fileManager createDirectoryAtPath:expansionDirectory withIntermediateDirectories:YES attributes:nil error:nil];
128 | for (NSDictionary *file in self.inflatedFiles) {
129 | NSDictionary *fileAttributes = [file objectForKey:ZKFileAttributesKey];
130 | NSData *inflatedData = [file objectForKey:ZKFileDataKey];
131 | NSString *path = [expansionDirectory stringByAppendingPathComponent:[file objectForKey:ZKPathKey]];
132 | [self.fileManager createDirectoryAtPath:[path stringByDeletingLastPathComponent]
133 | withIntermediateDirectories:YES attributes:nil error:nil];
134 | if ([[fileAttributes fileType] isEqualToString:NSFileTypeRegular])
135 | [inflatedData writeToFile:path atomically:YES];
136 | else if ([[fileAttributes fileType] isEqualToString:NSFileTypeDirectory])
137 | [self.fileManager createDirectoryAtPath:path
138 | withIntermediateDirectories:YES attributes:nil error:nil];
139 | else if ([[fileAttributes fileType] isEqualToString:NSFileTypeSymbolicLink]) {
140 | NSString *symLinkDestinationPath = [[[NSString alloc] initWithData:inflatedData
141 | encoding:NSUTF8StringEncoding] autorelease];
142 | [self.fileManager createSymbolicLinkAtPath:path
143 | withDestinationPath:symLinkDestinationPath error:nil];
144 | }
145 | [self.fileManager setAttributes:fileAttributes ofItemAtPath:path error:nil];
146 | }
147 |
148 | #if ZK_TARGET_OS_MAC
149 | if (rfFlag)
150 | [self.fileManager zk_combineAppleDoubleInDirectory:expansionDirectory];
151 | #endif
152 | [self cleanUpExpansionDirectory:expansionDirectory];
153 |
154 | return zkSucceeded;
155 | }
156 |
157 |
158 |
159 | #pragma mark -
160 | #pragma mark Deflation
161 |
162 | - (NSInteger) deflateFiles:(NSArray *) paths relativeToPath:(NSString *) basePath usingResourceFork:(BOOL) rfFlag {
163 | NSInteger rc = zkSucceeded;
164 | for (NSString *path in paths) {
165 | if ([self.fileManager zk_isDirAtPath:path] && ![self.fileManager zk_isSymLinkAtPath:path]) {
166 | rc = [self deflateDirectory:path relativeToPath:basePath usingResourceFork:rfFlag];
167 | if (rc != zkSucceeded)
168 | break;
169 | } else {
170 | rc = [self deflateFile:path relativeToPath:basePath usingResourceFork:rfFlag];
171 | if (rc != zkSucceeded)
172 | break;
173 | }
174 | }
175 | return rc;
176 | }
177 |
178 | - (NSInteger) deflateDirectory:(NSString *) dirPath relativeToPath:(NSString *) basePath usingResourceFork:(BOOL) rfFlag {
179 | NSInteger rc = [self deflateFile:dirPath relativeToPath:basePath usingResourceFork:rfFlag];
180 | if (rc == zkSucceeded) {
181 | NSDirectoryEnumerator *e = [self.fileManager enumeratorAtPath:dirPath];
182 | for (NSString *path in e) {
183 | rc = [self deflateFile:[dirPath stringByAppendingPathComponent:path] relativeToPath:basePath usingResourceFork:rfFlag];
184 | if (rc != zkSucceeded)
185 | break;
186 | }
187 | }
188 | return rc;
189 | }
190 |
191 | - (NSInteger) deflateFile:(NSString *) path relativeToPath:(NSString *) basePath usingResourceFork:(BOOL) rfFlag {
192 | BOOL isDir = [self.fileManager zk_isDirAtPath:path];
193 | BOOL isSymlink = [self.fileManager zk_isSymLinkAtPath:path];
194 | BOOL isFile = (!isSymlink && !isDir);
195 |
196 | // if (self.delegate) {
197 | // if ([NSThread isMainThread])
198 | // [self willZipPath:path];
199 | // else
200 | // [self performSelectorOnMainThread:@selector(willZipPath:) withObject:path waitUntilDone:NO];
201 | // }
202 |
203 | // append a trailing slash to directory paths
204 | if (isDir && !isSymlink && ![[path substringFromIndex:([path length] - 1)] isEqualToString:@"/"])
205 | path = [path stringByAppendingString:@"/"];
206 |
207 | // construct a relative path for storage in the archive directory by removing basePath from the beginning of path
208 | NSString *relativePath = path;
209 | if (basePath && [basePath length] > 0) {
210 | if (![basePath hasSuffix:@"/"])
211 | basePath = [basePath stringByAppendingString:@"/"];
212 | NSRange r = [path rangeOfString:basePath];
213 | if (r.location != NSNotFound)
214 | relativePath = [path substringFromIndex:r.length];
215 | }
216 |
217 | if (isFile) {
218 | NSData *fileData = [NSData dataWithContentsOfFile:path];
219 | NSDictionary *fileAttributes = [self.fileManager attributesOfItemAtPath:path error:nil];
220 | NSInteger rc = [self deflateData:fileData withFilename:relativePath andAttributes:fileAttributes];
221 | #if ZK_TARGET_OS_MAC
222 | if (rc == zkSucceeded && rfFlag) {
223 | NSData *appleDoubleData = [GMAppleDouble zk_appleDoubleDataForPath:path];
224 | if (appleDoubleData) {
225 | NSString *appleDoublePath = [[ZKMacOSXDirectory stringByAppendingPathComponent:
226 | [relativePath stringByDeletingLastPathComponent]]
227 | stringByAppendingPathComponent:
228 | [ZKDotUnderscore stringByAppendingString:[relativePath lastPathComponent]]];
229 | rc = [self deflateData:appleDoubleData withFilename:appleDoublePath andAttributes:fileAttributes];
230 | }
231 | }
232 | #endif
233 | return rc;
234 | }
235 |
236 | // create the local file header for the file
237 | ZKLFHeader *lfHeaderData = [[ZKLFHeader new] autorelease];
238 | lfHeaderData.uncompressedSize = 0;
239 | lfHeaderData.lastModDate = [self.fileManager zk_modificationDateForPath:path];
240 | lfHeaderData.filename = relativePath;
241 | lfHeaderData.filenameLength = [lfHeaderData.filename zk_precomposedUTF8Length];
242 | lfHeaderData.crc = 0;
243 | lfHeaderData.compressedSize = 0;
244 |
245 | // remove the existing central directory from the data
246 | unsigned long long lfHeaderDataOffset = self.cdTrailer.offsetOfStartOfCentralDirectory;
247 | [self.data setLength:lfHeaderDataOffset];
248 |
249 | if (isSymlink) {
250 | NSString *symlinkPath = [self.fileManager destinationOfSymbolicLinkAtPath:path error:nil];
251 | NSData *symlinkData = [symlinkPath dataUsingEncoding:NSUTF8StringEncoding];
252 | lfHeaderData.crc = [symlinkData zk_crc32];
253 | lfHeaderData.compressedSize = [symlinkData length];
254 | lfHeaderData.uncompressedSize = [symlinkData length];
255 | lfHeaderData.compressionMethod = Z_NO_COMPRESSION;
256 | lfHeaderData.versionNeededToExtract = 10;
257 | [self.data appendData:[lfHeaderData data]];
258 | [self.data appendData:symlinkData];
259 | } else if (isDir) {
260 | lfHeaderData.crc = 0;
261 | lfHeaderData.compressedSize = 0;
262 | lfHeaderData.uncompressedSize = 0;
263 | lfHeaderData.compressionMethod = Z_NO_COMPRESSION;
264 | lfHeaderData.versionNeededToExtract = 10;
265 | [self.data appendData:[lfHeaderData data]];
266 | }
267 |
268 | // create the central directory header and add it to central directory
269 | ZKCDHeader *cdHeaderData = [[ZKCDHeader new] autorelease];
270 | cdHeaderData.uncompressedSize = lfHeaderData.uncompressedSize;
271 | cdHeaderData.lastModDate = lfHeaderData.lastModDate;
272 | cdHeaderData.crc = lfHeaderData.crc;
273 | cdHeaderData.compressedSize = lfHeaderData.compressedSize;
274 | cdHeaderData.filename = lfHeaderData.filename;
275 | cdHeaderData.filenameLength = lfHeaderData.filenameLength;
276 | cdHeaderData.localHeaderOffset = lfHeaderDataOffset;
277 | cdHeaderData.compressionMethod = lfHeaderData.compressionMethod;
278 | cdHeaderData.generalPurposeBitFlag = lfHeaderData.generalPurposeBitFlag;
279 | cdHeaderData.versionNeededToExtract = lfHeaderData.versionNeededToExtract;
280 | cdHeaderData.externalFileAttributes = [self.fileManager zk_externalFileAttributesAtPath:path];
281 | [self.centralDirectory addObject:cdHeaderData];
282 |
283 | // update the central directory trailer
284 | self.cdTrailer.numberOfCentralDirectoryEntriesOnThisDisk++;
285 | self.cdTrailer.totalNumberOfCentralDirectoryEntries++;
286 | self.cdTrailer.sizeOfCentralDirectory += [cdHeaderData length];
287 |
288 | self.cdTrailer.offsetOfStartOfCentralDirectory = [self.data length];
289 | for (ZKCDHeader *cdHeader in self.centralDirectory)
290 | [self.data appendData:[cdHeader data]];
291 |
292 | [self.data appendData:[self.cdTrailer data]];
293 |
294 | return zkSucceeded;
295 | }
296 |
297 | - (NSInteger) deflateData:(NSData *)data withFilename:(NSString *) filename andAttributes:(NSDictionary *) fileAttributes {
298 | if (!filename || [filename length] < 1)
299 | return zkFailed;
300 |
301 | NSData *deflatedData = [data zk_deflate];
302 | if (!deflatedData)
303 | return zkFailed;
304 |
305 | unsigned long long lfHeaderDataOffset = self.cdTrailer.offsetOfStartOfCentralDirectory;
306 | [self.data setLength:lfHeaderDataOffset];
307 |
308 | ZKLFHeader *lfHeaderData = [[ZKLFHeader new] autorelease];
309 | lfHeaderData.uncompressedSize = [data length];
310 | lfHeaderData.filename = filename;
311 | lfHeaderData.filenameLength = [lfHeaderData.filename zk_precomposedUTF8Length];
312 | lfHeaderData.crc = [data zk_crc32];
313 | lfHeaderData.compressedSize = [deflatedData length];
314 |
315 | ZKCDHeader *cdHeaderData = [[ZKCDHeader new] autorelease];
316 | cdHeaderData.uncompressedSize = lfHeaderData.uncompressedSize;
317 | cdHeaderData.crc = lfHeaderData.crc;
318 | cdHeaderData.compressedSize = lfHeaderData.compressedSize;
319 | cdHeaderData.filename = lfHeaderData.filename;
320 | cdHeaderData.filenameLength = lfHeaderData.filenameLength;
321 | cdHeaderData.localHeaderOffset = lfHeaderDataOffset;
322 | cdHeaderData.compressionMethod = lfHeaderData.compressionMethod;
323 | cdHeaderData.generalPurposeBitFlag = lfHeaderData.generalPurposeBitFlag;
324 | cdHeaderData.versionNeededToExtract = lfHeaderData.versionNeededToExtract;
325 | [self.centralDirectory addObject:cdHeaderData];
326 |
327 | self.cdTrailer.numberOfCentralDirectoryEntriesOnThisDisk++;
328 | self.cdTrailer.totalNumberOfCentralDirectoryEntries++;
329 | self.cdTrailer.sizeOfCentralDirectory += [cdHeaderData length];
330 |
331 | if (fileAttributes) {
332 | if ([[fileAttributes allKeys] containsObject:NSFileModificationDate]) {
333 | lfHeaderData.lastModDate = [fileAttributes objectForKey:NSFileModificationDate];
334 | cdHeaderData.lastModDate = lfHeaderData.lastModDate;
335 | }
336 | cdHeaderData.externalFileAttributes = [self.fileManager zk_externalFileAttributesFor:fileAttributes];
337 | }
338 |
339 | [self.data appendData:[lfHeaderData data]];
340 | [self.data appendData:deflatedData];
341 |
342 | self.cdTrailer.offsetOfStartOfCentralDirectory = [self.data length];
343 | for (ZKCDHeader *cdHeader in self.centralDirectory)
344 | [self.data appendData:[cdHeader data]];
345 |
346 | [self.data appendData:[self.cdTrailer data]];
347 |
348 | return zkSucceeded;
349 | }
350 |
351 | #pragma mark -
352 | #pragma mark Setup
353 |
354 | - (id) init {
355 | if (self = [super init]) {
356 | self.data = [NSMutableData data];
357 | self.inflatedFiles = [NSMutableArray array];
358 | }
359 | return self;
360 | }
361 |
362 | - (void) dealloc {
363 | self.data = nil;
364 | self.inflatedFiles = nil;
365 | [super dealloc];
366 | }
367 |
368 | - (void) finalize {
369 | self.data = nil;
370 | [self.inflatedFiles removeAllObjects];
371 | self.inflatedFiles = nil;
372 | [super finalize];
373 | }
374 |
375 | @synthesize data = _data, inflatedFiles = _inflatedFiles;
376 |
377 | @end
--------------------------------------------------------------------------------
/External/ZipKit/ZKDefs.h:
--------------------------------------------------------------------------------
1 | //
2 | // ZKDefs.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #define ZK_TARGET_OS_MAC (TARGET_OS_MAC && !(TARGET_OS_EMBEDDED || TARGET_OS_IPHONE))
9 | #define ZK_TARGET_OS_IPHONE (TARGET_OS_EMBEDDED || TARGET_OS_IPHONE || TARGET_OS_IPHONE_SIMULATOR)
10 |
11 | enum ZKReturnCodes {
12 | zkFailed = -1,
13 | zkCancelled = 0,
14 | zkSucceeded = 1,
15 | };
16 |
17 | // File & path naming
18 | extern NSString* const ZKArchiveFileExtension;
19 | extern NSString* const ZKMacOSXDirectory;
20 | extern NSString* const ZKDotUnderscore;
21 | extern NSString* const ZKExpansionDirectoryName;
22 |
23 | // Keys for dictionary passed to size calculation thread
24 | extern NSString* const ZKPathsKey;
25 | extern NSString* const ZKusingResourceForkKey;
26 |
27 | // Keys for dictionary returned from ZKDataArchive inflation
28 | extern NSString* const ZKFileDataKey;
29 | extern NSString* const ZKFileAttributesKey;
30 | extern NSString* const ZKPathKey;
31 |
32 | // Zipping & Unzipping
33 | extern const NSUInteger ZKZipBlockSize;
34 | extern const NSUInteger ZKNotificationIterations;
35 |
36 | // Magic numbers and lengths for zip records
37 | extern const NSUInteger ZKCDHeaderMagicNumber;
38 | extern const NSUInteger ZKCDHeaderFixedDataLength;
39 |
40 | extern const NSUInteger ZKCDTrailerMagicNumber;
41 | extern const NSUInteger ZKCDTrailerFixedDataLength;
42 |
43 | extern const NSUInteger ZKLFHeaderMagicNumber;
44 | extern const NSUInteger ZKLFHeaderFixedDataLength;
45 |
46 | extern const NSUInteger ZKCDTrailer64MagicNumber;
47 | extern const NSUInteger ZKCDTrailer64FixedDataLength;
48 |
49 | extern const NSUInteger ZKCDTrailer64LocatorMagicNumber;
50 | extern const NSUInteger ZKCDTrailer64LocatorFixedDataLength;
51 |
--------------------------------------------------------------------------------
/External/ZipKit/ZKDefs.m:
--------------------------------------------------------------------------------
1 | //
2 | // ZKDefs.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "ZKDefs.h"
9 |
10 | NSString* const ZKArchiveFileExtension = @"zip";
11 | NSString* const ZKMacOSXDirectory = @"__MACOSX";
12 | NSString* const ZKDotUnderscore = @"._";
13 | NSString* const ZKExpansionDirectoryName = @".ZipKit";
14 |
15 | NSString* const ZKPathsKey = @"paths";
16 | NSString* const ZKusingResourceForkKey = @"usingResourceFork";
17 |
18 | NSString* const ZKFileDataKey = @"fileData";
19 | NSString* const ZKFileAttributesKey = @"fileAttributes";
20 | NSString* const ZKPathKey = @"path";
21 |
22 | const NSUInteger ZKZipBlockSize = 262144;
23 | const NSUInteger ZKNotificationIterations = 100;
24 |
25 | const NSUInteger ZKCDHeaderMagicNumber = 0x02014B50;
26 | const NSUInteger ZKCDHeaderFixedDataLength = 46;
27 |
28 | const NSUInteger ZKCDTrailerMagicNumber = 0x06054B50;
29 | const NSUInteger ZKCDTrailerFixedDataLength = 22;
30 |
31 | const NSUInteger ZKLFHeaderMagicNumber = 0x04034B50;
32 | const NSUInteger ZKLFHeaderFixedDataLength = 30;
33 |
34 | const NSUInteger ZKCDTrailer64MagicNumber = 0x06064b50;
35 | const NSUInteger ZKCDTrailer64FixedDataLength = 56;
36 |
37 | const NSUInteger ZKCDTrailer64LocatorMagicNumber = 0x07064b50;
38 | const NSUInteger ZKCDTrailer64LocatorFixedDataLength = 20;
39 |
--------------------------------------------------------------------------------
/External/ZipKit/ZKFileArchive.h:
--------------------------------------------------------------------------------
1 | //
2 | // ZKFileArchive.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 | #import "ZKArchive.h"
10 |
11 | @class ZKCDHeader;
12 |
13 | @interface ZKFileArchive : ZKArchive {
14 | @private
15 | BOOL _useZip64Extensions;
16 | }
17 |
18 | + (ZKFileArchive *) process:(id) item usingResourceFork:(BOOL) flag withInvoker:(id) invoker andDelegate:(id) delegate;
19 | + (ZKFileArchive *) archiveWithArchivePath:(NSString *) archivePath;
20 |
21 | - (NSInteger) inflateToDiskUsingResourceFork:(BOOL) flag;
22 | - (NSInteger) inflateToDirectory:(NSString *)expansionDirectory usingResourceFork:(BOOL)rfFlag;
23 | - (NSInteger) inflateFile:(ZKCDHeader *) cdHeader toDirectory:(NSString *) expansionDirectory;
24 |
25 | - (NSInteger) deflateFiles:(NSArray *) paths relativeToPath:(NSString *) basePath usingResourceFork:(BOOL) flag;
26 | - (NSInteger) deflateDirectory:(NSString *) dirPath relativeToPath:(NSString *) basePath usingResourceFork:(BOOL) flag;
27 | - (NSInteger) deflateFile:(NSString *) path relativeToPath:(NSString *) basePath usingResourceFork:(BOOL) flag;
28 |
29 | @property (assign) BOOL useZip64Extensions;
30 |
31 | @end
--------------------------------------------------------------------------------
/External/ZipKit/ZKLFHeader.h:
--------------------------------------------------------------------------------
1 | //
2 | // ZKLFHeader.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 |
10 | @interface ZKLFHeader : NSObject {
11 | @private
12 | NSUInteger magicNumber;
13 | NSUInteger versionNeededToExtract;
14 | NSUInteger generalPurposeBitFlag;
15 | NSUInteger compressionMethod;
16 | NSDate *lastModDate;
17 | NSUInteger crc;
18 | unsigned long long compressedSize;
19 | unsigned long long uncompressedSize;
20 | NSUInteger filenameLength;
21 | NSUInteger extraFieldLength;
22 | NSString *filename;
23 | NSData *extraField;
24 | }
25 |
26 | + (ZKLFHeader *) recordWithData:(NSData *)data atOffset:(NSUInteger)offset;
27 | + (ZKLFHeader *) recordWithArchivePath:(NSString *)path atOffset:(unsigned long long)offset;
28 | - (void) parseZip64ExtraField;
29 | - (NSData *) zip64ExtraField;
30 | - (NSData *) data;
31 | - (NSUInteger) length;
32 | - (BOOL) useZip64Extensions;
33 | - (BOOL) isResourceFork;
34 |
35 | @property (assign) NSUInteger magicNumber;
36 | @property (assign) NSUInteger versionNeededToExtract;
37 | @property (assign) NSUInteger generalPurposeBitFlag;
38 | @property (assign) NSUInteger compressionMethod;
39 | @property (retain) NSDate *lastModDate;
40 | @property (assign) NSUInteger crc;
41 | @property (assign) unsigned long long compressedSize;
42 | @property (assign) unsigned long long uncompressedSize;
43 | @property (assign) NSUInteger filenameLength;
44 | @property (assign) NSUInteger extraFieldLength;
45 | @property (copy) NSString *filename;
46 | @property (retain) NSData *extraField;
47 |
48 | @end
--------------------------------------------------------------------------------
/External/ZipKit/ZKLFHeader.m:
--------------------------------------------------------------------------------
1 | //
2 | // ZKLFHeader.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "ZKLFHeader.h"
9 | #import "NSDate+ZKAdditions.h"
10 | #import "NSData+ZKAdditions.h"
11 | #import "NSString+ZKAdditions.h"
12 | #import "ZKDefs.h"
13 | #import "zlib.h"
14 |
15 | @implementation ZKLFHeader
16 |
17 | - (id) init {
18 | if (self = [super init]) {
19 | self.magicNumber = ZKLFHeaderMagicNumber;
20 | self.versionNeededToExtract = 20;
21 | self.generalPurposeBitFlag = 0;
22 | self.compressionMethod = Z_DEFLATED;
23 | self.lastModDate = [NSDate date];
24 | self.crc = 0;
25 | self.compressedSize = 0;
26 | self.uncompressedSize = 0;
27 | self.filenameLength = 0;
28 | self.extraFieldLength = 0;
29 | self.filename = nil;
30 | self.extraField = nil;
31 |
32 | [self addObserver:self forKeyPath:@"compressedSize" options:NSKeyValueObservingOptionNew context:nil];
33 | [self addObserver:self forKeyPath:@"uncompressedSize" options:NSKeyValueObservingOptionNew context:nil];
34 | [self addObserver:self forKeyPath:@"extraField" options:NSKeyValueObservingOptionNew context:nil];
35 | [self addObserver:self forKeyPath:@"filename" options:NSKeyValueObservingOptionNew context:nil];
36 | }
37 | return self;
38 | }
39 |
40 | - (void) removeObservers {
41 | [self removeObserver:self forKeyPath:@"compressedSize"];
42 | [self removeObserver:self forKeyPath:@"uncompressedSize"];
43 | [self removeObserver:self forKeyPath:@"extraField"];
44 | [self removeObserver:self forKeyPath:@"filename"];
45 | }
46 |
47 | - (void) finalize {
48 | [self removeObservers];
49 | [super finalize];
50 | }
51 |
52 | - (void) dealloc {
53 | [self removeObservers];
54 | self.lastModDate = nil;
55 | self.filename = nil;
56 | self.extraField = nil;
57 | [super dealloc];
58 | }
59 |
60 | - (void) observeValueForKeyPath:(NSString *) keyPath ofObject:(id) object change:(NSDictionary *) change context:(void *) context {
61 | if ([keyPath isEqualToString:@"compressedSize"] || [keyPath isEqualToString:@"uncompressedSize"]) {
62 | self.versionNeededToExtract = ([self useZip64Extensions] ? 45 : 20);
63 | } else if ([keyPath isEqualToString:@"extraField"] && self.extraFieldLength < 1) {
64 | self.extraFieldLength = [self.extraField length];
65 | } else if ([keyPath isEqualToString:@"filename"] && self.filenameLength < 1) {
66 | self.filenameLength = [self.filename zk_precomposedUTF8Length];
67 | }
68 | }
69 |
70 | + (ZKLFHeader *) recordWithData:(NSData *) data atOffset:(NSUInteger) offset {
71 | if (!data) return nil;
72 | NSUInteger mn = [data zk_hostInt32OffsetBy:&offset];
73 | if (mn != ZKLFHeaderMagicNumber) return nil;
74 | ZKLFHeader *record = [[ZKLFHeader new] autorelease];
75 | record.magicNumber = mn;
76 | record.versionNeededToExtract = [data zk_hostInt16OffsetBy:&offset];
77 | record.generalPurposeBitFlag = [data zk_hostInt16OffsetBy:&offset];
78 | record.compressionMethod = [data zk_hostInt16OffsetBy:&offset];
79 | record.lastModDate = [NSDate zk_dateWithDosDate:[data zk_hostInt32OffsetBy:&offset]];
80 | record.crc = [data zk_hostInt32OffsetBy:&offset];
81 | record.compressedSize = [data zk_hostInt32OffsetBy:&offset];
82 | record.uncompressedSize = [data zk_hostInt32OffsetBy:&offset];
83 | record.filenameLength = [data zk_hostInt16OffsetBy:&offset];
84 | record.extraFieldLength = [data zk_hostInt16OffsetBy:&offset];
85 | if ([data length] > ZKLFHeaderFixedDataLength) {
86 | if (record.filenameLength > 0)
87 | record.filename = [data zk_stringOffsetBy:&offset length:record.filenameLength];
88 | if (record.extraFieldLength > 0) {
89 | record.extraField = [data subdataWithRange:NSMakeRange(offset, record.extraFieldLength)];
90 | [record parseZip64ExtraField];
91 | }
92 | }
93 | return record;
94 | }
95 |
96 | + (ZKLFHeader *) recordWithArchivePath:(NSString *) path atOffset:(unsigned long long) offset {
97 | NSFileHandle *file = [NSFileHandle fileHandleForReadingAtPath:path];
98 | [file seekToFileOffset:offset];
99 | NSData *fixedData = [file readDataOfLength:ZKLFHeaderFixedDataLength];
100 | ZKLFHeader *record = [self recordWithData:fixedData atOffset:0];
101 | if (record.filenameLength > 0) {
102 | NSData *data = [file readDataOfLength:record.filenameLength];
103 | record.filename = [[[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding] autorelease];
104 | }
105 | if (record.extraFieldLength > 0) {
106 | record.extraField = [file readDataOfLength:record.extraFieldLength];
107 | [record parseZip64ExtraField];
108 | }
109 | [file closeFile];
110 | return record;
111 | }
112 |
113 | - (NSData *) data {
114 | self.extraField = [self zip64ExtraField];
115 |
116 | NSMutableData *data = [NSMutableData zk_dataWithLittleInt32:self.magicNumber];
117 | [data zk_appendLittleInt16:self.versionNeededToExtract];
118 | [data zk_appendLittleInt16:self.generalPurposeBitFlag];
119 | [data zk_appendLittleInt16:self.compressionMethod];
120 | [data zk_appendLittleInt32:[self.lastModDate zk_dosDate]];
121 | [data zk_appendLittleInt32:self.crc];
122 | if ([self useZip64Extensions]) {
123 | [data zk_appendLittleInt32:0xFFFFFFFF];
124 | [data zk_appendLittleInt32:0xFFFFFFFF];
125 | } else {
126 | [data zk_appendLittleInt32:self.compressedSize];
127 | [data zk_appendLittleInt32:self.uncompressedSize];
128 | }
129 | [data zk_appendLittleInt16:self.filenameLength];
130 | [data zk_appendLittleInt16:[self.extraField length]];
131 | [data zk_appendPrecomposedUTF8String:self.filename];
132 | [data appendData:self.extraField];
133 | return data;
134 | }
135 |
136 | - (void) parseZip64ExtraField {
137 | NSUInteger offset = 0, tag, length;
138 | while (offset < self.extraFieldLength) {
139 | tag = [self.extraField zk_hostInt16OffsetBy:&offset];
140 | length = [self.extraField zk_hostInt16OffsetBy:&offset];
141 | if (tag == 0x0001) {
142 | if (length >= 8)
143 | self.uncompressedSize = [self.extraField zk_hostInt64OffsetBy:&offset];
144 | if (length >= 16)
145 | self.compressedSize = [self.extraField zk_hostInt64OffsetBy:&offset];
146 | break;
147 | } else {
148 | offset += length;
149 | }
150 | }
151 | }
152 |
153 | - (NSData *) zip64ExtraField {
154 | NSMutableData *zip64ExtraField = nil;
155 | if ([self useZip64Extensions]) {
156 | zip64ExtraField = [NSMutableData zk_dataWithLittleInt16:0x0001];
157 | [zip64ExtraField zk_appendLittleInt16:16];
158 | [zip64ExtraField zk_appendLittleInt64:self.uncompressedSize];
159 | [zip64ExtraField zk_appendLittleInt64:self.compressedSize];
160 | }
161 | return zip64ExtraField;
162 | }
163 |
164 | - (NSUInteger) length {
165 | if (!self.extraField || [self.extraField length] == 0)
166 | self.extraField = [self zip64ExtraField];
167 | return ZKLFHeaderFixedDataLength + self.filenameLength + [self.extraField length];
168 | }
169 |
170 | - (BOOL) useZip64Extensions {
171 | return (self.uncompressedSize >= 0xFFFFFFFF) || (self.compressedSize >= 0xFFFFFFFF);
172 | }
173 |
174 | - (NSString *) description {
175 | return [NSString stringWithFormat:@"%@ modified %@, %qu bytes (%qu compressed)",
176 | self.filename, self.lastModDate, self.uncompressedSize, self.compressedSize];
177 | }
178 |
179 | - (BOOL) isResourceFork {
180 | return [self.filename zk_isResourceForkPath];
181 | }
182 |
183 | @synthesize magicNumber, versionNeededToExtract, generalPurposeBitFlag, compressionMethod, lastModDate, crc, compressedSize, uncompressedSize, filenameLength, extraFieldLength, filename, extraField;
184 |
185 | @end
186 |
--------------------------------------------------------------------------------
/External/ZipKit/ZKLog.h:
--------------------------------------------------------------------------------
1 | //
2 | // ZKLog.h
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import
9 |
10 | enum ZKLogLevel {
11 | ZKLogLevelNotice = 3,
12 | ZKLogLevelError = 2,
13 | ZKLogLevelDebug = 1,
14 | ZKLogLevelAll = 0,
15 | };
16 |
17 | #define ZKLog(s, l, ...) [[ZKLog sharedInstance] logFile:__FILE__ lineNumber:__LINE__ level:l format:(s), ## __VA_ARGS__]
18 |
19 | #define ZKLogError(s, ...) ZKLog((s), ZKLogLevelError, ## __VA_ARGS__)
20 | #define ZKLogNotice(s, ...) ZKLog((s), ZKLogLevelNotice, ## __VA_ARGS__)
21 | #define ZKLogDebug(s, ...) ZKLog((s), ZKLogLevelDebug, ## __VA_ARGS__)
22 |
23 | #define ZKLogWithException(e) ZKLogError(@"Exception in %@: \n\tname: %@\n\treason: %@\n\tuserInfo: %@", NSStringFromSelector(_cmd), [e name], [e reason], [e userInfo]);
24 | #define ZKLogWithError(e) ZKLogError(@"Error in %@: \n\tdomain: %@\n\tcode: %@\n\tdescription: %@", NSStringFromSelector(_cmd), [e domain], [e code], [e localizedDescription]);
25 |
26 | #define ZKStringFromBOOL(b) (b ? @"YES": @"NO")
27 |
28 | extern NSString* const ZKLogLevelKey;
29 | extern NSString* const ZKLogToFileKey;
30 |
31 | @interface ZKLog : NSObject {
32 | @private
33 | NSUInteger minimumLevel;
34 | NSDateFormatter *dateFormatter;
35 | int pid;
36 | NSString *logFilePath;
37 | FILE *logFilePointer;
38 | }
39 |
40 | - (void) logFile:(char*) sourceFile lineNumber:(NSUInteger) lineNumber level:(NSUInteger) level format:(NSString*) format, ...;
41 |
42 | - (NSString *) levelToLabel:(NSUInteger) level;
43 |
44 | + (ZKLog *) sharedInstance;
45 |
46 | @property (assign) NSUInteger minimumLevel;
47 | @property (retain) NSDateFormatter *dateFormatter;
48 | @property (assign) int pid;
49 | @property (copy) NSString *logFilePath;
50 | @property (assign) FILE *logFilePointer;
51 |
52 | @end
--------------------------------------------------------------------------------
/External/ZipKit/ZKLog.m:
--------------------------------------------------------------------------------
1 | //
2 | // ZKLog.m
3 | // ZipKit
4 | //
5 | // Created by Karl Moskowski on 01/04/09.
6 | //
7 |
8 | #import "ZKLog.h"
9 |
10 | NSString* const ZKLogLevelKey = @"ZKLogLevel";
11 | NSString* const ZKLogToFileKey = @"ZKLogToFile";
12 |
13 | @implementation ZKLog
14 |
15 | - (void) logFile:(char*) sourceFile lineNumber:(NSUInteger) lineNumber level:(NSUInteger) level format:(NSString*) format, ... {
16 | if (level >= self.minimumLevel) {
17 | va_list args;
18 | va_start(args, format);
19 | NSString *message = [[[NSString alloc] initWithFormat:format arguments:args] autorelease];
20 | va_end(args);
21 | NSString *label = [self levelToLabel:level];
22 | NSString *now = [self.dateFormatter stringFromDate:[NSDate date]];
23 | if (label) {
24 | NSString *line = [NSString stringWithFormat:@"%@ [%i] %@ %@ (%@:%u)", now, self.pid, label, message, [[NSString stringWithUTF8String:sourceFile] lastPathComponent], lineNumber];
25 | fprintf(stderr, "%s\n", [line UTF8String]);
26 | fflush(stderr);
27 | }
28 | }
29 | return;
30 | }
31 |
32 | - (NSUInteger) minimumLevel {
33 | return minimumLevel;
34 | }
35 | - (void) setMinimumLevel:(NSUInteger) value {
36 | switch (value) {
37 | case ZKLogLevelError:
38 | case ZKLogLevelNotice:
39 | case ZKLogLevelDebug:
40 | case ZKLogLevelAll:
41 | minimumLevel = value;
42 | break;
43 | default:
44 | ZKLogError(@"Invalid logging level: %u. Old value %@ unchanged.", value, [self levelToLabel:self.minimumLevel]);
45 | break;
46 | }
47 | return;
48 | }
49 |
50 | - (NSString *) levelToLabel:(NSUInteger) level {
51 | NSString *label = nil;
52 | switch (level) {
53 | case ZKLogLevelError:
54 | label = @"";
55 | break;
56 | case ZKLogLevelNotice:
57 | label = @"";
58 | break;
59 | case ZKLogLevelDebug:
60 | label = @"";
61 | break;
62 | default:
63 | label = nil;
64 | break;
65 | }
66 | return label;
67 | }
68 |
69 | static ZKLog *sharedInstance = nil;
70 | + (ZKLog *) sharedInstance {
71 | @synchronized(self) {
72 | if (sharedInstance == nil) {
73 | sharedInstance = [self new];
74 | }
75 | }
76 | return sharedInstance;
77 | }
78 |
79 | - (id) init {
80 | @synchronized([self class]) {
81 | if (sharedInstance == nil) {
82 | if (self = [super init]) {
83 | sharedInstance = self;
84 |
85 | self.pid = [[NSProcessInfo processInfo] processIdentifier];
86 | self.minimumLevel = ZKLogLevelError;
87 | self.dateFormatter = [[NSDateFormatter new] autorelease];
88 | [self.dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss.SSS"];
89 |
90 | if ([[NSUserDefaults standardUserDefaults] boolForKey:ZKLogToFileKey]) {
91 | NSArray *searchPaths = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES);
92 | NSString *libraryFolder = [searchPaths objectAtIndex:0];
93 | NSString *logFolder = [libraryFolder stringByAppendingPathComponent:@"Logs"];
94 | [[[NSFileManager new] autorelease] createDirectoryAtPath:logFolder withIntermediateDirectories:YES attributes:nil error:nil];
95 | self.logFilePath = [logFolder stringByAppendingPathComponent:
96 | [[[NSBundle mainBundle] objectForInfoDictionaryKey:@"CFBundleIdentifier"]
97 | stringByAppendingPathExtension:@"log"]];
98 | freopen([self.logFilePath fileSystemRepresentation], "a+", stderr);
99 | }
100 | }
101 | }
102 | }
103 | return sharedInstance;
104 | }
105 |
106 | + (id) allocWithZone:(NSZone *) zone {
107 | @synchronized(self) {
108 | if (sharedInstance == nil) {
109 | return [super allocWithZone:zone];
110 | }
111 | }
112 | return sharedInstance;
113 | }
114 |
115 | + (void) initialize {
116 | [[NSUserDefaults standardUserDefaults] registerDefaults:
117 | [NSDictionary dictionaryWithObject:[NSNumber numberWithBool:NO] forKey:ZKLogToFileKey]];
118 | [super initialize];
119 | }
120 |
121 | - (id) copyWithZone:(NSZone *) zone {
122 | return self;
123 | }
124 |
125 | - (void) finalize {
126 | if (self.logFilePointer)
127 | fclose(self.logFilePointer);
128 | [super finalize];
129 | }
130 |
131 | - (void) dealloc {
132 | if (self.logFilePointer)
133 | fclose(self.logFilePointer);
134 | self.dateFormatter = nil;
135 | self.logFilePath = nil;
136 | [super dealloc];
137 | }
138 |
139 | @synthesize dateFormatter, pid, logFilePath, logFilePointer;
140 | @dynamic minimumLevel;
141 |
142 | @end
--------------------------------------------------------------------------------
/IPAViewController.xib:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | 1280
5 | 10K549
6 | 1938
7 | 1038.36
8 | 461.00
9 |
10 | com.apple.InterfaceBuilder.IBCocoaTouchPlugin
11 | 933
12 |
13 |
14 | IBUISearchDisplayController
15 | IBUITableView
16 | IBUISearchBar
17 | IBProxyObject
18 |
19 |
20 | com.apple.InterfaceBuilder.IBCocoaTouchPlugin
21 |
22 |
23 | PluginDependencyRecalculationVersion
24 |
25 |
26 |
27 |
28 | IBFilesOwner
29 | IBCocoaTouchFramework
30 |
31 |
32 | IBFirstResponder
33 | IBCocoaTouchFramework
34 |
35 |
36 |
37 | 274
38 |
39 |
40 |
41 | 290
42 | {320, 44}
43 |
44 |
45 | 3
46 | IBCocoaTouchFramework
47 |
48 | IBCocoaTouchFramework
49 |
50 |
51 |
52 | {320, 460}
53 |
54 |
55 |
56 |
57 | 3
58 | MC43NQA
59 |
60 | 2
61 |
62 |
63 | YES
64 | IBCocoaTouchFramework
65 | YES
66 | 1
67 | 0
68 | YES
69 | 44
70 | 22
71 | 22
72 |
73 |
74 |
75 | IBCocoaTouchFramework
76 |
77 |
78 |
79 |
80 |
81 |
82 | view
83 |
84 |
85 |
86 | 4
87 |
88 |
89 |
90 | searchDisplayController
91 |
92 |
93 |
94 | 15
95 |
96 |
97 |
98 | delegate
99 |
100 |
101 |
102 | 20
103 |
104 |
105 |
106 | searchContentsController
107 |
108 |
109 |
110 | 16
111 |
112 |
113 |
114 | searchResultsDataSource
115 |
116 |
117 |
118 | 17
119 |
120 |
121 |
122 | searchResultsDelegate
123 |
124 |
125 |
126 | 18
127 |
128 |
129 |
130 | delegate
131 |
132 |
133 |
134 | 19
135 |
136 |
137 |
138 | searchBar
139 |
140 |
141 |
142 | 14
143 |
144 |
145 |
146 |
147 |
148 | 0
149 |
150 |
151 |
152 |
153 |
154 | -1
155 |
156 |
157 | File's Owner
158 |
159 |
160 | -2
161 |
162 |
163 |
164 |
165 | 2
166 |
167 |
168 |
169 |
170 |
171 |
172 |
173 | 13
174 |
175 |
176 |
177 |
178 | 12
179 |
180 |
181 |
182 |
183 |
184 |
185 | IPAViewController
186 | com.apple.InterfaceBuilder.IBCocoaTouchPlugin
187 | UIResponder
188 | com.apple.InterfaceBuilder.IBCocoaTouchPlugin
189 | com.apple.InterfaceBuilder.IBCocoaTouchPlugin
190 | com.apple.InterfaceBuilder.IBCocoaTouchPlugin
191 | com.apple.InterfaceBuilder.IBCocoaTouchPlugin
192 |
193 |
194 |
195 |
196 |
197 | 20
198 |
199 |
200 |
201 |
202 | IPAViewController
203 | UITableViewController
204 |
205 | IBProjectSource
206 | ./Classes/IPAViewController.h
207 |
208 |
209 |
210 |
211 | 0
212 | IBCocoaTouchFramework
213 | YES
214 | 3
215 | 933
216 |
217 |
218 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | ## iOS Artwork
2 |
3 | *iOS Artwork Extractor* extracts all the artwork and emoji symbols contained in iOS into png files.
4 |
5 | In order to extract *Retina Display @2x* high resolution images, choose the **Hardware > Device > iPhone 4** menu in the iPhone Simulator.
6 |
7 | See instructions on the wiki to [extract more artwork](https://github.com/0xced/iOS-Artwork-Extractor/wiki/Extracting-more-artwork).
8 |
9 | * Set the `ARTWORK_DIRECTORY` environment variable to control where the png files are saved. If it is not set, the files will be saved into a folder on your desktop.
10 |
11 | ## Glossy Buttons
12 |
13 | *iOS Artwork Extractor* can also generate glossy buttons png files if you are using a simulator running **iOS 5.0 or older**. Thanks to [@schwa](http://twitter.com/schwa/status/9288691077) for the original code. Three states (normal/highlighted/disabled) glossy buttons png files are saved into the same directory as iOS artwork png files under the *UIGlassButton* subdirectory.
14 |
15 | ## IPAs
16 |
17 | *iOS Artwork Extractor* also knows how to extract artwork from apps you downloaded from the App Store. It goes without saying that this is for educational purpose only and that you should not steal others' artwork.
18 |
19 | * Use the `MOBILE_APPLICATIONS_DIRECTORY` environment variable if your iTunes library is not located in the standard location, i.e. `~/Music/iTunes`.
20 |
21 | ## Screenshots
22 |
23 |
24 |
25 |
26 |
27 |
28 |
--------------------------------------------------------------------------------
/Resources/Artwork.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Artwork.png
--------------------------------------------------------------------------------
/Resources/Artwork@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Artwork@2x.png
--------------------------------------------------------------------------------
/Resources/Checkerboard.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Checkerboard.png
--------------------------------------------------------------------------------
/Resources/Emoji.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Emoji.png
--------------------------------------------------------------------------------
/Resources/Emoji@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Emoji@2x.png
--------------------------------------------------------------------------------
/Resources/GlossyButton.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/GlossyButton.png
--------------------------------------------------------------------------------
/Resources/GlossyButton@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/GlossyButton@2x.png
--------------------------------------------------------------------------------
/Resources/IPA.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/IPA.png
--------------------------------------------------------------------------------
/Resources/IPA@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/IPA@2x.png
--------------------------------------------------------------------------------
/Resources/Icon.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Icon.png
--------------------------------------------------------------------------------
/Resources/Icon@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Icon@2x.png
--------------------------------------------------------------------------------
/Resources/Shared/UITintedGlassButtonHighlight@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Shared/UITintedGlassButtonHighlight@2x.png
--------------------------------------------------------------------------------
/Resources/Shared/UITintedGlassButtonMask@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Shared/UITintedGlassButtonMask@2x.png
--------------------------------------------------------------------------------
/Resources/Shared/UITintedGlassButtonShadow@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Shared/UITintedGlassButtonShadow@2x.png
--------------------------------------------------------------------------------
/Resources/Unknown.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Unknown.png
--------------------------------------------------------------------------------
/Resources/Unknown@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Resources/Unknown@2x.png
--------------------------------------------------------------------------------
/Screenshots/Artwork.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Screenshots/Artwork.png
--------------------------------------------------------------------------------
/Screenshots/Emoji.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Screenshots/Emoji.png
--------------------------------------------------------------------------------
/Screenshots/GlossyButton.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Screenshots/GlossyButton.png
--------------------------------------------------------------------------------
/Screenshots/IPA.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Screenshots/IPA.png
--------------------------------------------------------------------------------
/Screenshots/UISwitch.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/ide/iOS-Artwork-Extractor/17e6f1a62ca846c9c6535a8104a0f7e7a1221a66/Screenshots/UISwitch.png
--------------------------------------------------------------------------------
/iOS Artwork Extractor.xcodeproj/project.xcworkspace/contents.xcworkspacedata:
--------------------------------------------------------------------------------
1 |
2 |
4 |
6 |
7 |
8 |
--------------------------------------------------------------------------------
/iOS_Artwork_Extractor-Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | CFBundleDevelopmentRegion
6 | English
7 | CFBundleDisplayName
8 | Extractor
9 | CFBundleExecutable
10 | ${EXECUTABLE_NAME}
11 | CFBundleIconFiles
12 |
13 | Icon.png
14 | Icon@2x.png
15 |
16 | CFBundleIdentifier
17 | ch.pitaya.${PRODUCT_NAME:rfc1034identifier}
18 | CFBundleInfoDictionaryVersion
19 | 6.0
20 | CFBundleName
21 | ${PRODUCT_NAME}
22 | CFBundlePackageType
23 | APPL
24 | CFBundleVersion
25 | 1.0
26 | LSRequiresIPhoneOS
27 |
28 | NSMainNibFile
29 | MainWindow
30 | UIPrerenderedIcon
31 |
32 | UIFileSharingEnabled
33 |
34 |
35 |
36 |
--------------------------------------------------------------------------------
/iOS_Artwork_Extractor_Prefix.pch:
--------------------------------------------------------------------------------
1 | //
2 | // Prefix header for all source files of the 'iOS Artwork Extractor' target in the 'iOS Artwork Extractor' project
3 | //
4 |
5 | #ifdef __OBJC__
6 | #import
7 | #import
8 | #import
9 |
10 | #if __IPHONE_OS_VERSION_MAX_ALLOWED < 40000
11 | @interface UIScreen (iOS4)
12 | @property(nonatomic,readonly) CGFloat scale;
13 | @end
14 |
15 | @interface UIImage (iOS4)
16 | @property(nonatomic,readonly) CGFloat scale;
17 | @end
18 | #endif
19 |
20 | #endif
21 |
--------------------------------------------------------------------------------
/main.m:
--------------------------------------------------------------------------------
1 | //
2 | // main.m
3 | // iOS Artwork Extractor
4 | //
5 | // Created by Cédric Luthi on 19.02.10.
6 | // Copyright Cédric Luthi 2010. All rights reserved.
7 | //
8 |
9 | #import
10 | #import
11 |
12 | CGFloat iOS3_scale(id self, SEL _cmd)
13 | {
14 | return 1.0;
15 | }
16 |
17 | int main(int argc, char *argv[])
18 | {
19 | NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
20 |
21 | // -[UIView alpha] has the same method signature as -[UIScreen/UIImage scale]
22 | Method alpha = class_getInstanceMethod([UIView class], @selector(alpha));
23 | if (![UIScreen instancesRespondToSelector:@selector(scale)])
24 | class_addMethod([UIScreen class], @selector(scale), (IMP)iOS3_scale, method_getTypeEncoding(alpha));
25 | if (![UIImage instancesRespondToSelector:@selector(scale)])
26 | class_addMethod([UIImage class], @selector(scale), (IMP)iOS3_scale, method_getTypeEncoding(alpha));
27 |
28 | int retVal = UIApplicationMain(argc, argv, nil, nil);
29 | [pool release];
30 | return retVal;
31 | }
32 |
--------------------------------------------------------------------------------