ObjFW  Check-in [38c16e3793]

Overview
Comment:OFZooArchiveEntry: Support for POSIX permissions
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA3-256: 38c16e3793a2a1751b3a97934a7f6e1f5a9f45bcfc85815ac308fa074d7814af
User & Date: js on 2024-02-28 23:08:48
Other Links: manifest | tags
Context
2024-03-01
18:29
OFZooArchiveEntry: Handle time zone check-in: 6985292473 user: js tags: trunk
2024-02-28
23:08
OFZooArchiveEntry: Support for POSIX permissions check-in: 38c16e3793 user: js tags: trunk
22:34
OFZooArchiveEntry: Support for long file names check-in: 88c236e709 user: js tags: trunk
Changes

Modified src/OFZooArchiveEntry.h from [17bdcfc268] to [15e60ca9a9].

15
16
17
18
19
20
21

22
23
24
25
26
27
28

#import "OFObject.h"
#import "OFArchiveEntry.h"

OF_ASSUME_NONNULL_BEGIN

@class OFDate;

@class OFString;

/**
 * @class OFZooArchiveEntry OFZooArchiveEntry.h ObjFW/OFZooArchiveEntry.h
 *
 * @brief A class which represents an entry in an Zoo archive.
 */







>







15
16
17
18
19
20
21
22
23
24
25
26
27
28
29

#import "OFObject.h"
#import "OFArchiveEntry.h"

OF_ASSUME_NONNULL_BEGIN

@class OFDate;
@class OFNumber;
@class OFString;

/**
 * @class OFZooArchiveEntry OFZooArchiveEntry.h ObjFW/OFZooArchiveEntry.h
 *
 * @brief A class which represents an entry in an Zoo archive.
 */
36
37
38
39
40
41
42

43
44
45
46
47
48
49
@protected
	uint16_t _lastModifiedFileDate, _lastModifiedFileTime;
	uint16_t _CRC16;
	unsigned long long _uncompressedSize, _compressedSize;
	bool _deleted;
	OFString *_Nullable _fileComment;
	OFString *_fileName, *_Nullable _directoryName;

	OF_RESERVE_IVARS(OFZooArchiveEntry, 4)
}

/**
 * @brief The compression method of the entry.
 */
@property (readonly, nonatomic) uint8_t compressionMethod;







>







37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
@protected
	uint16_t _lastModifiedFileDate, _lastModifiedFileTime;
	uint16_t _CRC16;
	unsigned long long _uncompressedSize, _compressedSize;
	bool _deleted;
	OFString *_Nullable _fileComment;
	OFString *_fileName, *_Nullable _directoryName;
	OFNumber *_Nullable _POSIXPermissions;
	OF_RESERVE_IVARS(OFZooArchiveEntry, 4)
}

/**
 * @brief The compression method of the entry.
 */
@property (readonly, nonatomic) uint8_t compressionMethod;

Modified src/OFZooArchiveEntry.m from [66b61bdc12] to [c082c86574].

14
15
16
17
18
19
20

21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
 */

#include "config.h"

#import "OFZooArchiveEntry.h"
#import "OFZooArchiveEntry+Private.h"
#import "OFDate.h"

#import "OFSeekableStream.h"
#import "OFStream.h"
#import "OFString.h"

#import "OFInvalidFormatException.h"

@implementation OFZooArchiveEntry
@synthesize compressionMethod = _compressionMethod, CRC16 = _CRC16;
@synthesize uncompressedSize = _uncompressedSize;
@synthesize compressedSize = _compressedSize, deleted = _deleted;
@synthesize fileComment = _fileComment;

- (instancetype)init
{
	OF_INVALID_INIT_METHOD
}

- (instancetype)of_initWithStream: (OF_KINDOF(OFStream *))stream







>










|







14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
 */

#include "config.h"

#import "OFZooArchiveEntry.h"
#import "OFZooArchiveEntry+Private.h"
#import "OFDate.h"
#import "OFNumber.h"
#import "OFSeekableStream.h"
#import "OFStream.h"
#import "OFString.h"

#import "OFInvalidFormatException.h"

@implementation OFZooArchiveEntry
@synthesize compressionMethod = _compressionMethod, CRC16 = _CRC16;
@synthesize uncompressedSize = _uncompressedSize;
@synthesize compressedSize = _compressedSize, deleted = _deleted;
@synthesize fileComment = _fileComment, POSIXPermissions = _POSIXPermissions;

- (instancetype)init
{
	OF_INVALID_INIT_METHOD
}

- (instancetype)of_initWithStream: (OF_KINDOF(OFStream *))stream
111
112
113
114
115
116
117























118
119
120
121
122
123
124
					    exception];

				_directoryName = [[stream
				    readStringWithLength: directoryNameLength
						encoding: encoding] copy];
				extraLength -= directoryNameLength;
			}























		} else
			_fileName = [[OFString alloc]
			    initWithCString: fileNameBuffer
				   encoding: encoding];

		if (commentOffset != 0) {
			[stream seekToOffset: commentOffset whence: OFSeekSet];







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
					    exception];

				_directoryName = [[stream
				    readStringWithLength: directoryNameLength
						encoding: encoding] copy];
				extraLength -= directoryNameLength;
			}

			if (extraLength >= 2) {
				/* System ID */
				[stream readLittleEndianInt16];
				extraLength -= 2;
			}

			if (extraLength >= 3) {
				uint8_t attributes[3];

				[stream readIntoBuffer: attributes
					   exactLength: 3];

				if (attributes[2] & (1 << 6)) {
					uint16_t mode = (attributes[0] |
					    (attributes[1] << 8)) & 0777;

					_POSIXPermissions = [[OFNumber alloc]
					    initWithUnsignedShort: mode];
				}

				extraLength -= 3;
			}
		} else
			_fileName = [[OFString alloc]
			    initWithCString: fileNameBuffer
				   encoding: encoding];

		if (commentOffset != 0) {
			[stream seekToOffset: commentOffset whence: OFSeekSet];
137
138
139
140
141
142
143

144
145
146
147
148
149
150
}

- (void)dealloc
{
	[_fileComment release];
	[_fileName release];
	[_directoryName release];


	[super dealloc];
}

- (id)copy
{
	return [self retain];







>







161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
}

- (void)dealloc
{
	[_fileComment release];
	[_fileName release];
	[_directoryName release];
	[_POSIXPermissions release];

	[super dealloc];
}

- (id)copy
{
	return [self retain];

Modified utils/ofarc/ZooArchive.m from [f7ecaea67e] to [84c3532ff9].

28
29
30
31
32
33
34





















35
36
37
38
39
40
41

#import "ZooArchive.h"
#import "OFArc.h"

#import "OFSetItemAttributesFailedException.h"

static OFArc *app;






















static void
setModificationDate(OFString *path, OFZooArchiveEntry *entry)
{
	OFFileAttributes attributes = [OFDictionary
	    dictionaryWithObject: entry.modificationDate
			  forKey: OFFileModificationDate];







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62

#import "ZooArchive.h"
#import "OFArc.h"

#import "OFSetItemAttributesFailedException.h"

static OFArc *app;

static void
setPermissions(OFString *path, OFZooArchiveEntry *entry)
{
#ifdef OF_FILE_MANAGER_SUPPORTS_PERMISSIONS
	OFNumber *POSIXPermissions = entry.POSIXPermissions;

	if (POSIXPermissions == nil)
		return;

	POSIXPermissions = [OFNumber numberWithUnsignedShort:
	    POSIXPermissions.unsignedShortValue & 0777];

	OFFileAttributes attributes = [OFDictionary
	    dictionaryWithObject: POSIXPermissions
			  forKey: OFFilePOSIXPermissions];

	[[OFFileManager defaultManager] setAttributes: attributes
					 ofItemAtPath: path];
#endif
}

static void
setModificationDate(OFString *path, OFZooArchiveEntry *entry)
{
	OFFileAttributes attributes = [OFDictionary
	    dictionaryWithObject: entry.modificationDate
			  forKey: OFFileModificationDate];
149
150
151
152
153
154
155














156
157
158
159
160
161
162
			    @"CRC16: %[crc16]",
			    @"crc16", CRC16)];
			[OFStdOut writeString: @"\t"];
			[OFStdOut writeLine: OF_LOCALIZED(
			    @"list_modification_date",
			    @"Modification date: %[date]",
			    @"date", modificationDate)];














			[OFStdOut writeString: @"\t"];
			[OFStdOut writeLine: OF_LOCALIZED(
			    @"list_deleted",
			    @"["
			    @"    'Deleted: ',"
			    @"    ["
			    @"        {'deleted == 0': 'No'},"







>
>
>
>
>
>
>
>
>
>
>
>
>
>







170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
			    @"CRC16: %[crc16]",
			    @"crc16", CRC16)];
			[OFStdOut writeString: @"\t"];
			[OFStdOut writeLine: OF_LOCALIZED(
			    @"list_modification_date",
			    @"Modification date: %[date]",
			    @"date", modificationDate)];

			if (entry.POSIXPermissions != nil) {
				OFString *permissionsString = [OFString
				    stringWithFormat: @"%llo",
				    entry.POSIXPermissions
				    .unsignedLongLongValue];

				[OFStdOut writeString: @"\t"];
				[OFStdOut writeLine: OF_LOCALIZED(
				    @"list_posix_permissions",
				    @"POSIX permissions: %[perm]",
				    @"perm", permissionsString)];
			}

			[OFStdOut writeString: @"\t"];
			[OFStdOut writeLine: OF_LOCALIZED(
			    @"list_deleted",
			    @"["
			    @"    'Deleted: ',"
			    @"    ["
			    @"        {'deleted == 0': 'No'},"
222
223
224
225
226
227
228

229
230
231
232
233
234
235
					     createParents: true];

		if (![app shouldExtractFile: fileName outFileName: outFileName])
			goto outer_loop_end;

		stream = [_archive streamForReadingCurrentEntry];
		output = [OFFile fileWithPath: outFileName mode: @"w"];


		while (!stream.atEndOfStream) {
			ssize_t length = [app copyBlockFromStream: stream
							 toStream: output
							 fileName: fileName];

			if (length < 0) {







>







257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
					     createParents: true];

		if (![app shouldExtractFile: fileName outFileName: outFileName])
			goto outer_loop_end;

		stream = [_archive streamForReadingCurrentEntry];
		output = [OFFile fileWithPath: outFileName mode: @"w"];
		setPermissions(outFileName, entry);

		while (!stream.atEndOfStream) {
			ssize_t length = [app copyBlockFromStream: stream
							 toStream: output
							 fileName: fileName];

			if (length < 0) {