Replicating the effect of Compact.exe?

Comments, questions, bug reports, etc.
Post Reply
Dwedit
Posts: 2
Joined: Mon Jul 25, 2022 3:38 am

Replicating the effect of Compact.exe?

Post by Dwedit »

Is it known how to replicate the effect of Compact.exe, and cause LZX compression to be applied to files?

I was looking at what Compact.exe did, but only really noticed two calls to DeviceIoControl, one with FSCTL_GET_EXTERNAL_BACKING and one with FSCTL_SET_EXTERNAL_BACKING.
synchronicity
Site Admin
Posts: 472
Joined: Sun Aug 02, 2015 10:31 pm

Re: Replicating the effect of Compact.exe?

Post by synchronicity »

You need to use FSCTL_SET_EXTERNAL_BACKING. Take a look at the code here.
Dwedit
Posts: 2
Joined: Mon Jul 25, 2022 3:38 am

Re: Replicating the effect of Compact.exe?

Post by Dwedit »

Thank you very much.
I was able to use that code as reference to write C# code to add or remove compression from files.
I used to call Compact.exe, but now I can skip that part.

My project is a C# program where you give it a directory, and it recursively compresses files, but first checks if the files are compressible (and not already compressed) before it actually tries to compress them. It takes 16 evenly distributed samples of a file, 64K in size, and tries to compress them with Deflate. If Deflate was able to save at least 20%, then it compresses the file. This avoids situations where a giant 16GB package file gets compressed with LZX only to save a mere 1MB.

The thing that really surprised me is that you can freely compress files in "C:\Program Files" without admin privileges.

A quick licensing question, is porting over code from two functions "winnt_fsctl" and "set_system_compression" enough to make the project now LGPL?
synchronicity
Site Admin
Posts: 472
Joined: Sun Aug 02, 2015 10:31 pm

Re: Replicating the effect of Compact.exe?

Post by synchronicity »

I don't mind if you look at this small bit of code as a reference. Note that it would probably be simpler for you to use DeviceIoControl() instead of NtFsControlFile() as wimlib does, though.
Post Reply