Page 1 of 1

How Do I Use MAKECAB?

Posted: 20 Jun 2011 22:22
by nitt
I usually use IExpress to create CAB files, because it's the only console-based one I know that's built-in to your computer. But recently I discovered MAKECAB.EXE in my system32 folder. I tried it but I can't figure it out. It's confusin'.

Here is what I get for "makecab /?":

Code: Select all

Cabinet Maker - Lossless Data Compression Tool

MAKECAB [/V[n]] [/D var=value ...] [/L dir] source [destination]
MAKECAB [/V[n]] [/D var=value ...] /F directive_file [...]

  source         File to compress.
  destination    File name to give compressed file.  If omitted, the
                 last character of the source file name is replaced
                 with an underscore (_) and used as the destination.
  /F directives  A file with MakeCAB directives (may be repeated). Refer to
                 Microsoft Cabinet SDK for information on directive_file.
  /D var=value   Defines variable with specified value.
  /L dir         Location to place destination (default is current directory).
  /V[n]          Verbosity level (1..3).


I read it but I still just don't get it.

BTW, if you want to see an example of making a CAB file with IExpress in Batch, look here.

Re: How Do I Use MAKECAB?

Posted: 21 Jun 2011 07:48
by Acy Forsythe
The easiest usage is:

MAKECAB sourcefile.ext

That command will create a compressed file named sourcefile.ex_

You can get a lot more use out of it by creating and specifying a directives file. Here is a link to the guide:

http://msdn.microsoft.com/en-us/library ... usersguide

Re: How Do I Use MAKECAB?

Posted: 21 Jun 2011 11:37
by aGerman
In the past I used it in a function.
Example:

Code: Select all

@echo off &setlocal

set "sourceFolder=C:\test"
set "cabFolder=C:\cab"
set "cabName=my.cab"

call :mkCab "%sourceFolder%" "%cabFolder%" "%cabName%"

pause
goto :eof


:mkCab
:: change working directory
pushd "%temp%"
:: define variables in .ddf file
>directives.ddf echo .Option Explicit
>>directives.ddf echo .Set SourceDir="%~1"
>>directives.ddf echo .Set DiskDirectoryTemplate="%~2"
>>directives.ddf echo .Set CabinetNameTemplate="%~3"
>>directives.ddf echo .Set MaxDiskSize=0
>>directives.ddf echo .Set CabinetFileCountThreshold=0
>>directives.ddf echo .Set UniqueFiles=OFF
>>directives.ddf echo .Set Cabinet=ON
>>directives.ddf echo .Set Compress=ON
>>directives.ddf echo .Set CompressionType=MSZIP
:: save current ASCII code page
for /f "tokens=2 delims=:" %%i in ('chcp') do set /a oemcp=%%~ni
:: change code page to ANSI
chcp 1252>nul
:: append all file names of the source folder
for /f "delims=" %%i in ('dir /a-d /b "%~1"') do (
  set "line=%%i"
  setlocal enabledelayedexpansion
  >>directives.ddf echo "!line!"
  endlocal
)
:: change back to ASCII
chcp %oemcp%>nul
:: call makecab
makecab /f directives.ddf
:: clean up
del setup.inf
del setup.rpt
del directives.ddf
:: return to the previous working directory
popd
goto :eof


This code will compress all files in C:\test into C:\cab\my.cab

Regards
aGerman

Re: How Do I Use MAKECAB?

Posted: 21 Jun 2011 12:13
by nitt
Um aGerman can you simplify that a little bit please?

Re: How Do I Use MAKECAB?

Posted: 21 Jun 2011 13:17
by aGerman
Hmm, the best way to use makecab is by creating a directive file which contains the options (variables) and file names. So, how to simplify the code depends on what you would like to do. Maybe you could explain the purpose ...

Regards
aGerman

Re: How Do I Use MAKECAB?

Posted: 21 Jun 2011 13:27
by Acy Forsythe
The only part I don't get is why you're changing to ansi for the file list?

Re: How Do I Use MAKECAB?

Posted: 21 Jun 2011 14:35
by aGerman
Haha, thats typical German. There could be crazy letters in file names like ä ö ü ß :wink: Since file names are ANSI encoded I need to read it in ANSI.

Regards
aGerman

Re: How Do I Use MAKECAB?

Posted: 21 Jun 2011 16:02
by nitt
aGerman wrote:Haha, thats typical German. There could be crazy letters in file names like ä ö ü ß :wink: Since file names are ANSI encoded I need to read it in ANSI.

Regards
aGerman


Like, what is the simplest way to turn a folder into a CAB? I want to be able to turn multiple files into one CAB, not just one.

Re: How Do I Use MAKECAB?

Posted: 21 Jun 2011 16:55
by aGerman
Well, as far as I know makecab is not able to compress a folder. Only the files inside, without subfolders. That means you can't pass the folder name (except where to find files if they are passed without path), but a list of file names. That's the way my code above works. It creates a directive file (directives.ddf) which contains the settings (have a look at Acy Forsythe's link for all valid variables)
.set varName1=value1
.set varName2=value2
...

and a list of file names I created by processing the DIR command
"file1.ext"
"file2.ext"
...


IMO thats really the easiest way to use makecab with multiple files :|

Regards
aGerman

Re: How Do I Use MAKECAB?

Posted: 24 Jun 2011 20:56
by scienceguru1.bat
is there a possible way to change it so it would detect subfolders and do those too (as another cab file) and then compress those cab files into another single cab file?

Re: How Do I Use MAKECAB?

Posted: 25 Jun 2011 16:12
by aGerman
Hmm, I suggest a different way. You could define variable DestinationDir for each file in the .cab file.
MAKECAB corresponds to EXPAND which will use this information to create folders and subfolders while expanding the files.
Changed example that will also process subfolders in the first level:

Code: Select all

@echo off &setlocal

set "sourceFolder=C:\test"
set "cabFolder=C:\cab"
set "cabName=my.cab"

call :mkCab "%sourceFolder%" "%cabFolder%" "%cabName%"

pause
goto :eof


:mkCab
:: change working directory
pushd "%temp%"
:: define variables in .ddf file
>directives.ddf echo .Option Explicit
>>directives.ddf echo .Set SourceDir="%~1"
>>directives.ddf echo .Set DiskDirectoryTemplate="%~2"
>>directives.ddf echo .Set CabinetNameTemplate="%~3"
>>directives.ddf echo .Set MaxDiskSize=0
>>directives.ddf echo .Set CabinetFileCountThreshold=0
>>directives.ddf echo .Set UniqueFiles=OFF
>>directives.ddf echo .Set Cabinet=ON
>>directives.ddf echo .Set Compress=ON
>>directives.ddf echo .Set CompressionType=MSZIP
>>directives.ddf echo .Set DestinationDir="%~n1"
:: save current ASCII code page
for /f "tokens=2 delims=:" %%i in ('chcp') do set /a oemcp=%%~ni
:: change code page to ANSI
chcp 1252>nul
:: append all file names of the source folder
for /f "delims=" %%i in ('dir /a-d /b "%~1"') do (
  >>directives.ddf echo "%%i"
)
:: process sub folders
for /f "delims=" %%i in ('dir /ad /b "%~1"') do (
  >>directives.ddf echo .Set SourceDir="%~1\%%i"
  >>directives.ddf echo .Set DestinationDir="%~n1\%%i"
  for /f "delims=" %%j in ('dir /a-d /b "%~1\%%i"') do (
    >>directives.ddf echo "%%j"
  )
)
:: change back to ASCII
chcp %oemcp%>nul
:: call makecab
makecab /f directives.ddf
:: clean up
del setup.inf
del setup.rpt
del directives.ddf
:: return to the previous working directory
popd
goto :eof


Use ...

Code: Select all

expand C:\cab\my.cab -f:* C:\cab

... to find out how it works.

Regards
aGerman