I have a problem with SevenZipSharp in x64 platforms. I have used the SevenZipCompressor.CompressFilesEncrypted() to compress a file with EncryptHeaders = true.
I got an argument exception in the following line of the SevenZipCompressor.
setter.SetProperties(namesHandle.AddrOfPinnedObject(), valuesHandle.AddrOfPinnedObject(), names.Count);
I download and compiled the 7z.dll source code for x64 platform. After I debug through the 7z source code. I found that the propvarient size is 24 Bytes.
The ParseProperties.SetBoolProperty failed. "value.vt" have some junk values.
The propvarient structure implementation in SevenZipSharp have a small bug. So that it will not work in some cases in x64 os.
In x64 bit OS the size of the native propvarient strutcure is 24 bytes. But In SevenZipSharp it explicitly defined as 16 bytes in the propvarient definition. So the values in the structure will not correctly marshaled.
The size of the PropVariant in .NET the Marshal.SizeOf(porpv) returns same for both the platforms. (16 for 32 & 64 bit)
PropVarient Native Definition -
typedef struct tagCAC
typedef struct tagCAFILETIME
size of the tagCAC in x86 -> 8
The first member occupies 4 bytes = 4 bytes.
The second member of occupies 4 bytes.[ pointer is 4 byte long in x86] = 4 bytes.
size of the tagCAC in x64 -> 16
The first member occupies 4 bytes + 4 bytes (padding) = 8 bytes. I dont know why the padding bytes or came. May be the default struct alignment in x64 is 8 bytes.
The second member of occupies 8 bytes.[ pointer is 8 byte long in x64] = 8 bytes.
The size of the PROPVARIANT structure in x86 -> 8 bytes + 8 bytes [size of the tagCAC in x86]
The size of the PROPVARIANT structure in x64 -> 8 Bytes + 16 Bytes [size of the tagCAC in x64]
So in .NET We do not specfiy the size of the structure. Also We need to add a new structre inside the PropVarient.
In .net the IntPtr is platform depnedant. Its size differs for 32 bit and 64bit platforms.
So the propvarient C# structure should be defined like this.
internal struct PropVariant
[FieldOffset(0)] private ushort _Vt;
[FieldOffset(8)] private IntPtr _Value;
[FieldOffset(8)] private UInt32 _UInt32Value;
[FieldOffset(8)] private Int64 _Int64Value;
[FieldOffset(8)] private UInt64 _UInt64Value;
[FieldOffset(8)] private FILETIME _FileTime;
[FieldOffset(8)] private PROPARRAY _propArray;
internal struct PROPARRAY
After changing that, the size of the PropVariant in .NET the Marshal.SizeOf(porpv) returns correctly for both platforms. (16 for 32 bit. 24 for 64 bit).
Then the file compresed successfully in 64 bit platforms.
Thanks & Regards