Preserve DACL when creating tempfile on Win32.
diff --git a/lib/zip_source_win32file.c b/lib/zip_source_win32file.c
index ee8319e..b392ab8 100644
--- a/lib/zip_source_win32file.c
+++ b/lib/zip_source_win32file.c
@@ -417,20 +417,52 @@
     int i;
     HANDLE th = INVALID_HANDLE_VALUE;
     void *temp = NULL;
+    SECURITY_INFORMATION si;
+    SECURITY_ATTRIBUTES sa;
+    PSECURITY_DESCRIPTOR psd = NULL;
+    PSECURITY_ATTRIBUTES psa = NULL;
+    DWORD len;
+    BOOL success;
+
+    /*
+    Read the DACL from the original file, so we can copy it to the temp file.
+    If there is no original file, or if we can't read the DACL, we'll use the
+    default security descriptor.
+    */
+    if (ctx->h != INVALID_HANDLE_VALUE && GetFileType(ctx->h) == FILE_TYPE_DISK) {
+	si = DACL_SECURITY_INFORMATION | UNPROTECTED_DACL_SECURITY_INFORMATION;
+	len = 0;
+	success = GetUserObjectSecurity(ctx->h, &si, NULL, len, &len);
+	if (!success && GetLastError() == ERROR_INSUFFICIENT_BUFFER) {
+	    if ((psd = (PSECURITY_DESCRIPTOR)malloc(len)) == NULL) {
+		zip_error_set(&ctx->error, ZIP_ER_MEMORY, 0);
+		return -1;
+	    }
+	    success = GetUserObjectSecurity(ctx->h, &si, psd, len, &len);
+	}
+	if (success) {
+	    sa.nLength = sizeof(SECURITY_ATTRIBUTES);
+	    sa.bInheritHandle = FALSE;
+	    sa.lpSecurityDescriptor = psd;
+	    psa = &sa;
+	}
+    }
 
     zip_uint32_t value = GetTickCount();
     for (i = 0; i < 1024 && th == INVALID_HANDLE_VALUE; i++) {
-	th = ctx->ops->op_create_temp(ctx, &temp, value + i);
+	th = ctx->ops->op_create_temp(ctx, &temp, value + i, psa);
 	if (th == INVALID_HANDLE_VALUE && GetLastError() != ERROR_FILE_EXISTS)
 	    break;
     }
 
     if (th == INVALID_HANDLE_VALUE) {
 	free(temp);
+	free(psd);
 	zip_error_set(&ctx->error, ZIP_ER_TMPOPEN, _zip_win32_error_to_errno(GetLastError()));
 	return -1;
     }
 
+    free(psd);
     ctx->hout = th;
     ctx->tmpname = temp;