mirror of
https://github.com/QuasarApp/zip.git
synced 2025-04-27 12:54:32 +00:00
permissions xattr. logic from zip info (#227)
This commit is contained in:
parent
9a52cfc458
commit
11cc5c6d30
39
src/miniz.h
39
src/miniz.h
@ -1357,11 +1357,10 @@ MINIZ_EXPORT mz_bool mz_zip_reader_init_file_v2(mz_zip_archive *pZip,
|
||||
mz_uint64 file_start_ofs,
|
||||
mz_uint64 archive_size);
|
||||
MINIZ_EXPORT mz_bool mz_zip_reader_init_file_v2_rpb(mz_zip_archive *pZip,
|
||||
const char *pFilename,
|
||||
mz_uint flags,
|
||||
mz_uint64 file_start_ofs,
|
||||
mz_uint64 archive_size);
|
||||
|
||||
const char *pFilename,
|
||||
mz_uint flags,
|
||||
mz_uint64 file_start_ofs,
|
||||
mz_uint64 archive_size);
|
||||
|
||||
/* Read an archive from an already opened FILE, beginning at the current file
|
||||
* position. */
|
||||
@ -1625,9 +1624,8 @@ MINIZ_EXPORT mz_bool mz_zip_writer_init_from_reader(mz_zip_archive *pZip,
|
||||
MINIZ_EXPORT mz_bool mz_zip_writer_init_from_reader_v2(mz_zip_archive *pZip,
|
||||
const char *pFilename,
|
||||
mz_uint flags);
|
||||
MINIZ_EXPORT mz_bool mz_zip_writer_init_from_reader_v2_noreopen(mz_zip_archive *pZip,
|
||||
const char *pFilename,
|
||||
mz_uint flags);
|
||||
MINIZ_EXPORT mz_bool mz_zip_writer_init_from_reader_v2_noreopen(
|
||||
mz_zip_archive *pZip, const char *pFilename, mz_uint flags);
|
||||
|
||||
/* Adds the contents of a memory buffer to an archive. These functions record
|
||||
* the current local time into the archive. */
|
||||
@ -5010,6 +5008,13 @@ static int mz_mkdir(const char *pDirname) {
|
||||
#endif /* #ifdef _MSC_VER */
|
||||
#endif /* #ifdef MINIZ_NO_STDIO */
|
||||
|
||||
#ifndef CHMOD
|
||||
// Upon successful completion, a value of 0 is returned.
|
||||
// Otherwise, a value of -1 is returned and errno is set to indicate the error.
|
||||
// int chmod(const char *path, mode_t mode);
|
||||
#define CHMOD(f, m) chmod(f, m)
|
||||
#endif
|
||||
|
||||
#define MZ_TOLOWER(c) ((((c) >= 'A') && ((c) <= 'Z')) ? ((c) - 'A' + 'a') : (c))
|
||||
|
||||
/* Various ZIP archive enums. To completely avoid cross platform compiler
|
||||
@ -5975,9 +5980,10 @@ mz_bool mz_zip_reader_init_file_v2(mz_zip_archive *pZip, const char *pFilename,
|
||||
return MZ_TRUE;
|
||||
}
|
||||
|
||||
mz_bool mz_zip_reader_init_file_v2_rpb(mz_zip_archive *pZip, const char *pFilename,
|
||||
mz_uint flags, mz_uint64 file_start_ofs,
|
||||
mz_uint64 archive_size) {
|
||||
mz_bool mz_zip_reader_init_file_v2_rpb(mz_zip_archive *pZip,
|
||||
const char *pFilename, mz_uint flags,
|
||||
mz_uint64 file_start_ofs,
|
||||
mz_uint64 archive_size) {
|
||||
mz_uint64 file_size;
|
||||
MZ_FILE *pFile;
|
||||
|
||||
@ -8055,8 +8061,8 @@ mz_bool mz_zip_writer_init_from_reader_v2(mz_zip_archive *pZip,
|
||||
}
|
||||
|
||||
mz_bool mz_zip_writer_init_from_reader_v2_noreopen(mz_zip_archive *pZip,
|
||||
const char *pFilename,
|
||||
mz_uint flags) {
|
||||
const char *pFilename,
|
||||
mz_uint flags) {
|
||||
mz_zip_internal_state *pState;
|
||||
|
||||
if ((!pZip) || (!pZip->m_pState) || (pZip->m_zip_mode != MZ_ZIP_MODE_READING))
|
||||
@ -8368,8 +8374,7 @@ mz_bool mz_zip_writer_add_mem_ex_v2(
|
||||
mz_uint user_extra_data_central_len) {
|
||||
mz_uint16 method = 0, dos_time = 0, dos_date = 0;
|
||||
mz_uint level, ext_attributes = 0, num_alignment_padding_bytes;
|
||||
mz_uint64 local_dir_header_ofs = 0,
|
||||
cur_archive_file_ofs = 0, comp_size = 0;
|
||||
mz_uint64 local_dir_header_ofs = 0, cur_archive_file_ofs = 0, comp_size = 0;
|
||||
size_t archive_name_size;
|
||||
mz_uint8 local_dir_header[MZ_ZIP_LOCAL_DIR_HEADER_SIZE];
|
||||
tdefl_compressor *pComp = NULL;
|
||||
@ -8679,8 +8684,8 @@ mz_bool mz_zip_writer_add_read_buf_callback(
|
||||
: MZ_ZIP_LDH_BIT_FLAG_HAS_LOCATOR;
|
||||
mz_uint uncomp_crc32 = MZ_CRC32_INIT, level, num_alignment_padding_bytes;
|
||||
mz_uint16 method = 0, dos_time = 0, dos_date = 0;
|
||||
mz_uint64 local_dir_header_ofs, cur_archive_file_ofs = 0,
|
||||
uncomp_size = 0, comp_size = 0;
|
||||
mz_uint64 local_dir_header_ofs, cur_archive_file_ofs = 0, uncomp_size = 0,
|
||||
comp_size = 0;
|
||||
size_t archive_name_size;
|
||||
mz_uint8 local_dir_header[MZ_ZIP_LOCAL_DIR_HEADER_SIZE];
|
||||
mz_uint8 *pExtra_data = NULL;
|
||||
|
81
src/zip.c
81
src/zip.c
@ -66,6 +66,14 @@
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define UNX_IFDIR 0040000 /* Unix directory */
|
||||
#define UNX_IFREG 0100000 /* Unix regular file */
|
||||
#define UNX_IFSOCK 0140000 /* Unix socket (BSD, not SysV or Amiga) */
|
||||
#define UNX_IFLNK 0120000 /* Unix symbolic link (not SysV, Amiga) */
|
||||
#define UNX_IFBLK 0060000 /* Unix block special (not Amiga) */
|
||||
#define UNX_IFCHR 0020000 /* Unix character special (not Amiga) */
|
||||
#define UNX_IFIFO 0010000 /* Unix fifo (BCC, not MSC or Amiga) */
|
||||
|
||||
struct zip_entry_t {
|
||||
int index;
|
||||
char *name;
|
||||
@ -375,8 +383,8 @@ static int zip_archive_extract(mz_zip_archive *zip_archive, const char *dir,
|
||||
(void)xattr; // unused
|
||||
#else
|
||||
xattr = (info.m_external_attr >> 16) & 0xFFFF;
|
||||
if (xattr > 0) {
|
||||
if (chmod(path, (mode_t)xattr) < 0) {
|
||||
if (xattr > 0 && xattr <= MZ_UINT16_MAX) {
|
||||
if (CHMOD(path, (mode_t)xattr) < 0) {
|
||||
err = ZIP_ENOPERM;
|
||||
goto out;
|
||||
}
|
||||
@ -830,7 +838,8 @@ struct zip_t *zip_open(const char *zipname, int level, char mode) {
|
||||
goto cleanup;
|
||||
}
|
||||
if ((mode == 'a' || mode == 'd')) {
|
||||
if (!mz_zip_writer_init_from_reader_v2_noreopen(&(zip->archive), zipname, 0)) {
|
||||
if (!mz_zip_writer_init_from_reader_v2_noreopen(&(zip->archive), zipname,
|
||||
0)) {
|
||||
mz_zip_reader_end(&(zip->archive));
|
||||
goto cleanup;
|
||||
}
|
||||
@ -957,7 +966,7 @@ int zip_entry_open(struct zip_t *zip, const char *entryname) {
|
||||
|
||||
// UNIX or APPLE
|
||||
#if MZ_PLATFORM == 3 || MZ_PLATFORM == 19
|
||||
// regular file with rw-r--r-- persmissions
|
||||
// regular file with rw-r--r-- permissions
|
||||
zip->entry.external_attr = (mz_uint32)(0100644) << 16;
|
||||
#else
|
||||
zip->entry.external_attr = 0;
|
||||
@ -1315,6 +1324,7 @@ int zip_entry_fwrite(struct zip_t *zip, const char *filename) {
|
||||
MZ_FILE *stream = NULL;
|
||||
mz_uint8 buf[MZ_ZIP_MAX_IO_BUF_SIZE];
|
||||
struct MZ_FILE_STAT_STRUCT file_stat;
|
||||
mz_uint16 modes;
|
||||
|
||||
if (!zip) {
|
||||
// zip_t handler is not initialized
|
||||
@ -1328,11 +1338,32 @@ int zip_entry_fwrite(struct zip_t *zip, const char *filename) {
|
||||
return ZIP_ENOENT;
|
||||
}
|
||||
|
||||
if ((file_stat.st_mode & 0200) == 0) {
|
||||
// MS-DOS read-only attribute
|
||||
zip->entry.external_attr |= 0x01;
|
||||
#if defined(_WIN32) || defined(__WIN32__)
|
||||
(void)modes; // unused
|
||||
#else
|
||||
/* Initialize with permission bits--which are not implementation-optional */
|
||||
modes = file_stat.st_mode &
|
||||
(S_IRWXU | S_IRWXG | S_IRWXO | S_ISUID | S_ISGID | S_ISVTX);
|
||||
if (S_ISDIR(file_stat.st_mode))
|
||||
modes |= UNX_IFDIR;
|
||||
if (S_ISREG(file_stat.st_mode))
|
||||
modes |= UNX_IFREG;
|
||||
if (S_ISLNK(file_stat.st_mode))
|
||||
modes |= UNX_IFLNK;
|
||||
if (S_ISBLK(file_stat.st_mode))
|
||||
modes |= UNX_IFBLK;
|
||||
if (S_ISCHR(file_stat.st_mode))
|
||||
modes |= UNX_IFCHR;
|
||||
if (S_ISFIFO(file_stat.st_mode))
|
||||
modes |= UNX_IFIFO;
|
||||
if (S_ISSOCK(file_stat.st_mode))
|
||||
modes |= UNX_IFSOCK;
|
||||
zip->entry.external_attr = (modes << 16) | !(file_stat.st_mode & S_IWRITE);
|
||||
if ((file_stat.st_mode & S_IFMT) == S_IFDIR) {
|
||||
zip->entry.external_attr |= MZ_ZIP_DOS_DIR_ATTRIBUTE_BITFLAG;
|
||||
}
|
||||
zip->entry.external_attr |= (mz_uint32)((file_stat.st_mode & 0xFFFF) << 16);
|
||||
#endif
|
||||
|
||||
zip->entry.m_time = file_stat.st_mtime;
|
||||
|
||||
if (!(stream = MZ_FOPEN(filename, "rb"))) {
|
||||
@ -1440,8 +1471,8 @@ int zip_entry_fread(struct zip_t *zip, const char *filename) {
|
||||
}
|
||||
|
||||
xattr = (info.m_external_attr >> 16) & 0xFFFF;
|
||||
if (xattr > 0) {
|
||||
if (chmod(filename, (mode_t)xattr) < 0) {
|
||||
if (xattr > 0 && xattr <= MZ_UINT16_MAX) {
|
||||
if (CHMOD(filename, (mode_t)xattr) < 0) {
|
||||
return ZIP_ENOPERM;
|
||||
}
|
||||
}
|
||||
@ -1607,6 +1638,7 @@ int zip_create(const char *zipname, const char *filenames[], size_t len) {
|
||||
mz_zip_archive zip_archive;
|
||||
struct MZ_FILE_STAT_STRUCT file_stat;
|
||||
mz_uint32 ext_attributes = 0;
|
||||
mz_uint16 modes;
|
||||
|
||||
if (!zipname || strlen(zipname) < 1) {
|
||||
// zip_t archive name is empty or NULL
|
||||
@ -1641,11 +1673,32 @@ int zip_create(const char *zipname, const char *filenames[], size_t len) {
|
||||
break;
|
||||
}
|
||||
|
||||
if ((file_stat.st_mode & 0200) == 0) {
|
||||
// MS-DOS read-only attribute
|
||||
ext_attributes |= 0x01;
|
||||
#if defined(_WIN32) || defined(__WIN32__)
|
||||
(void)modes; // unused
|
||||
#else
|
||||
|
||||
/* Initialize with permission bits--which are not implementation-optional */
|
||||
modes = file_stat.st_mode &
|
||||
(S_IRWXU | S_IRWXG | S_IRWXO | S_ISUID | S_ISGID | S_ISVTX);
|
||||
if (S_ISDIR(file_stat.st_mode))
|
||||
modes |= UNX_IFDIR;
|
||||
if (S_ISREG(file_stat.st_mode))
|
||||
modes |= UNX_IFREG;
|
||||
if (S_ISLNK(file_stat.st_mode))
|
||||
modes |= UNX_IFLNK;
|
||||
if (S_ISBLK(file_stat.st_mode))
|
||||
modes |= UNX_IFBLK;
|
||||
if (S_ISCHR(file_stat.st_mode))
|
||||
modes |= UNX_IFCHR;
|
||||
if (S_ISFIFO(file_stat.st_mode))
|
||||
modes |= UNX_IFIFO;
|
||||
if (S_ISSOCK(file_stat.st_mode))
|
||||
modes |= UNX_IFSOCK;
|
||||
ext_attributes = (modes << 16) | !(file_stat.st_mode & S_IWRITE);
|
||||
if ((file_stat.st_mode & S_IFMT) == S_IFDIR) {
|
||||
ext_attributes |= MZ_ZIP_DOS_DIR_ATTRIBUTE_BITFLAG;
|
||||
}
|
||||
ext_attributes |= (mz_uint32)((file_stat.st_mode & 0xFFFF) << 16);
|
||||
#endif
|
||||
|
||||
if (!mz_zip_writer_add_file(&zip_archive, zip_basename(name), name, "", 0,
|
||||
ZIP_DEFAULT_COMPRESSION_LEVEL,
|
||||
|
@ -24,9 +24,7 @@ void test_setup(void) {
|
||||
zip_close(zip);
|
||||
}
|
||||
|
||||
void test_teardown(void) {
|
||||
remove(ZIPNAME);
|
||||
}
|
||||
void test_teardown(void) { remove(ZIPNAME); }
|
||||
|
||||
#define TESTDATA2 "Some test data 2...\0"
|
||||
#define CRC32DATA2 2532008468
|
||||
|
Loading…
x
Reference in New Issue
Block a user