This document describes the procedure to produce incremental patch for
the NovellWin32ISO installers. This is somewhat hard to automate. This
document is very much a work in progress, written and updated while
working out how this actually should be done. Read with a large pinch
of salt. This document still mostly talks about the patches between
the 2.0.4 builds, not from the final 2.0.4 build to the first 2.1
build.

The NovellWin32ISO builds are identified by the full three-part
PACKAGEVERSION from openoffice.lst (2.0.4, for instance) suffixed by a
dash and a counter, starting from 1 in the first build. The first
distributed NovellWin32ISO build of 2.0.4 is thus 2.0.4-1.

The "PATCHLEVEL" we talk about below is a NovellWin32ISO concept that
was used in the 2.0.4 build. It is not to be confused with other
things related to "patching" that might have similar names in the
upstream installer-building Perl code (much of which is undocumented,
and even probably unfinished, or remains of procedures never fully
implemented, or whatever). So when you see mentions of patching and
updating in solenv/bin/modules/installer/*.pm etc, note that this has
nothing to do with the Windows Installer patching stuff described
here.

For the first 2.0.4 build, build 1, PATCHLEVEL was 0. For build 2 it
was 1, etc. Yeah, this was illogical, I should have called the first
build 2.0.4-0. 

But anyway, in the 2.1 build I did away with the patchlevel concept
altogether inside the OOo build system. I only use it in the names of
the distributables, i.e. zipfiles or iso files containing installers.
As can be seen below, it was somewhat painful to maintain the correct
patchlevels for each file depending on at which time it had been
rebuilt.

The idea is that the original build directory is kept, and only
incremental changes are done. Only those projects where there has been
code changes (i.e. updated ooo-build patches that affect the project)
since the previous build are rebuilt. Thus the files that are included
in each build's installer are mostly from the original build, only
those that have actual changes are fresher.

The procedure
=============

- Rename build/$tag/instsetoo_native/wntmsci10.pro/OpenOffice to
OpenOffice-$previous (where $previous is the previous build
counter). Ditto for OpenOffice_languagepack, although I don't think
there would be any point in producing Windows Installer patch
installers for language packs.

- Add a new marker to ChangeLog indicating at what point in time this
build was done.

- Run make patch.apply if relevant patches have changed.

- Run sh doc/AUTOGEN.NovellWin32ISO.sh.

- Run a top-level make in ooo-build and interrupt it when it starts
the main build with "Building project solenv", i.e. after having done
the upstream configure script and set_soenv stuff.

- Inspect ChangeLog entries since the last marker. Go to build/$tag,
source winenv.set.sh. In each project directly affected by changes
since the last marker, do a build && deliver. Be careful to do this in
the correct order in case a patch since the last release build has
changed the API of some project, but I sure hope that won't happen.

For 2.0.4-2 vs. 2.0.4-1, the projects affected by patches changed seem
to be, in a hopefully correct order:

officecfg
sfx2
sc
binfilter (but nothing that affected what gets built had changed)
helpcontent2

For 2.0.4-4 vs. 2.0.4-2, they are:

offapi
scp2
scsolver
fpicker
basic
sfx2
filter (because of the added MOOX xcu fragments)
sc
sysui (jimmac's new icons)
desktop (-"-)

Note carefully what changed/new files get delivered, just for
double-checking later.

To find out the correct order to build && deliver, given we know what
projects are affected, go to postprocess and run:

build --all --show | grep 'Building project' |grep -E ' (offapi|sfx2|scsolver|sc|scp2|basic|filter|fpicker)$'

(use the relevant list of projects in the grep, of course.)

- Remove sfx2/wntmsci10.pro/slo/about.obj and do a build && deliver in
sfx2, too, if not already done above. This is to get the new build
date into Help:About.

- Go to postprocess, build & deliver.

- Go to instsetoo_native. Edit util/makefile.mk to avoid building
language packs. Do a build there.

- Do an administrative install of previous build(s), and of what you just
built:

  cd <foo>/build/OOO_2_0_4/instsetoo_native/OpenOffice-2/msi/install/<en-US_ar_cs_blabla>
  msiexec /a openofficeorg20.msi

  cd <foo>/build/OOE680_m6/instsetoo_native/OpenOffice/msi/install/<horrible-hex-string>
  msiexec /a openofficeorg20.msi

for instance, for 2.0.4-8 and 2.2.0-2: install into
c:\tmp\OOo-2.0.4-8-admin and c:\tmp\OOo-2.1.0-2-admin

- Make a new folder for the patch installer, for instance
c:\tmp\OOo-2.1.0-2.patch.

Note that a Windows Installer patch can contain several patch pairs;
for instance, we had a single patch (.msp file) that patched 2.0.4-1,
2.0.4-2, 2.0.4-4, 2.0.4-5, or 2.0.4-6 to 2.0.4-7.

- Create a Patch Creation Properties (.pcp) file, for instance called
Ooo-2.1.0-2.pcp. Copy the Samples/SysMgmt/Msi/Patching/TEMPLATE.PCP
file from the Platform SDK.  A dump of the relevant tables in that
file for the 2.0.4-1 to 2.0.4-2 and 2.0.4-1 and -2 to 2.0.4-4 patches
is included below. Remember to generate a new GUID for each .pcp file
in the PatchGUID property in the Properties table.

- Add PATCHLEVEL to the last part of the ProductVersion in the
Properties table of the .msi file in the "upgraded" administrative
installation.

For instance, for 2.0.4-1, the ProductVersion property is 2.0.9073,
and for 2.0.4-2 this was manually changed to 2.0.9074, and for 2.0.4-4
to 2.0.9076.

Some typical MS braindamage here: The ProductVersion property is
documented to be three digits: uchar.uchar.ushort, i.e. the first two
<= 255, the last <= 65535. So we can't use the same kind of version
number as for the FileVersion column in the File table, which is four
ushorts, and constructed as

 OOO_MAJOR . OOO_MINOR*100+OOO_MICRO . BUILDID . PATCHLEVEL

For files that are changed in 2.0.4-2, that would be 2.4.9073.1. This
sucks, yeah. But just incrementing the last part (buildid) hopefully
won't cause any trouble, even though it is misleading, as the real
buildid of course is the same for all NovellWin32ISO 2.0.4-x
builds. (Recall that "buildid" in OOo means a number corresponding to
the milestone, it has nothing to do with actual "builds" by
distributors of OOo, like NovellWin32ISO builds. For the milestone
OOO_2_0_4 the OOo buildid is 9073.)

Hmm, even though documentation says that the ProductVersion property
should be three parts as above (uchar.uchar.ushort), in reality many
of the .msi files out there, even from Microsoft, have four-part
ProductVersion properties. The Value column in the Property table is a
string, so there is nothing in the MSI format that prevents this,
although it is of course questionable how Windows Installer accepts
other that three-part ProductVersion properties. Oh well...

- Run msimsp to find the differences between the two above
installations, verify that the DLL and EXE files that have changed
indeed have the updated version in their VRBs.

  msimsp -s openofficeorg20.pcp -p openofficeorg20.msp -l logfile.log

Read the logfile looking for which files have changed

- Verify that the changed files are more or less those that you would
have expected.

Note that because of the GNOME CVS -> SVN switch, I had to do a
completely fresh rebuild of 2.0.4 between 2.0.4-5 and 2.0.4-6 (if I
recal correctly), which screwed up all this royally, as all binaries
got new embedded timestamps at the every least, and also all help
indexes etc crap got changed (although really not). So to avoid the
intra-2.0.4 patch growing unnecessarily large, in the later 2.0.4 pcp
files I ignored changes to help index etc files.

================

Exports (.idt files) of the non-empty tables in the Patch Creation
Properties (.pcp) file used when creating the 2.0.4-1 to 2.0.4-2
patch. I have also added some comments.

==> ImageFamilies:

Family	MediaSrcPropName	MediaDiskId	FileSequenceStart	DiskPrompt	VolumeLabel
s8	S72	I2	I2	S128	S32
ImageFamilies	Family
OOo	OOoSrcPropName	100	11000		

The number of files in OOo is under 11000, so we start files
introduced by patches at 11000.

==> PatchMetadata:

Company	Property	Value
S72	s72	l0
PatchMetadata	Company	Property
	AllowRemoval	1
	Classification	update
	CreationTimeUTC	2006-11-21 17:00
	Description	2.0.4-1/2
	DisplayName	2.0.4-1/2
	ManufacturerName	Novell, Inc.
	MoreInfoURL	http://www.novell.com
	TargetProductName	OpenOffice.org 2.0.4

The Description and DisplayName strings don't have any prescribed
format, that "2.0.4-1/2" is just a convention I invented to indicate a
patch from 2.0.4-1 to 2.0.4-2.

==> Properties:

Name	Value
s72	L0
Properties	Name
AllowProductCodeMismatches	1
AllowProductVersionMajorMismatches	1
ApiPatchingSymbolFlags	0x00000000
DontRemoveTempFolderWhenFinished	1
IncludeWholeFilesOnly	0
ListOfPatchGUIDsToReplace	
ListOfTargetProductCodes	*
MinimumRequiredMsiVersion	300
PatchGUID	{489E4A5F-830E-425D-BFA6-6E1C57D35CF6}
PatchOutputPath	openofficeorg20.msp
SEQUENCE_DATA_GENERATION_DISABLED	1

The PatchGUID must be unique for each .msp file.

==> TargetImages:

Target	MsiPath	SymbolPaths	Upgraded	Order	ProductValidateFlags	IgnoreMissingSrcFiles
s13	s255	S255	s13	i2	S16	i2
TargetImages	Target
2p0p4d1	c:\tmp\OOo-2.0.4-1-admin\openofficeorg20.msi		2p0p4d2	1		0

The Target and Upgraded fields must be alphanumeric, thus I
transformed periods to "p" and dashes to "d", i.e. 2.0.4-1 became
2p0p4d1...

==> UpgradedImages:

Upgraded	MsiPath	PatchMsiPath	SymbolPaths	Family
s13	s255	S255	S255	s8
UpgradedImages	Upgraded
2p0p4d2	c:\tmp\OOo-2.0.4-2-admin\openofficeorg20.msi			OOo

================

Corresponding exports of the non-empty tables in the pcp file used
when creating the 2.0.4-1 and 2.0.4-2 to 2.0.4-4 patch.

This patch is capable of upgrading either 2.0.4-1 or 2.0.4-2 to
2.0.4-4. (2.0.4-3 was an intermediate build that I just made the en-US
-only installer for.

Here we had to add rows to the UpgradedFiles_OptionalData table so
that the msvcr71.dll and msvcp71.dll files were included in the patch
as whole files. These files changed when running build in postprocess
as they were rebased to a different address than in the earlier
builds.

Of course, the base addess is just one field in the PE header, so
being able to have a binary patch for them would have been extremely
nice. But unfortunately, as the versions (in the VRB) of these files
didn't change, and we don't generate MsiFileHash entries for dll and
exe files, there is no way Windows Installer can verify that it would
be patching the right file. Thus we have to include the "new" ones
(with just the base address change) in toto.

When starting a new base build plus patch chain (OO.o 2.1?) we should
begin calculating MsiFileHash values also for versioned files, to
avoid this issue.

==> ImageFamilies:

Family	MediaSrcPropName	MediaDiskId	FileSequenceStart	DiskPrompt	VolumeLabel
s8	S72	I2	I2	S128	S32
ImageFamilies	Family
OOo	OOoSrcPropName	100	11000		

==> PatchMetadata:

Company	Property	Value
S72	s72	l0
PatchMetadata	Company	Property
	AllowRemoval	1
	Classification	update
	CreationTimeUTC	2006-12-14 22:00
	Description	2.0.4-1+2/4
	DisplayName	2.0.4-1+2/4
	ManufacturerName	Novell, Inc.
	MoreInfoURL	http://www.novell.com
	TargetProductName	OpenOffice.org 2.0.4

==> Properties:

Name	Value
s72	L0
Properties	Name
AllowProductCodeMismatches	1
AllowProductVersionMajorMismatches	1
ApiPatchingSymbolFlags	0x00000000
DontRemoveTempFolderWhenFinished	1
IncludeWholeFilesOnly	0
ListOfPatchGUIDsToReplace	
ListOfTargetProductCodes	*
MinimumRequiredMsiVersion	300
PatchGUID	{D79AFC12-0A1B-4E9D-9C29-4128BBDE0365}
PatchOutputPath	openofficeorg20.msp

I removed the SEQUENCE_DATA_GENERATION_DISABLED property.

==> TargetImages:

Target	MsiPath	SymbolPaths	Upgraded	Order	ProductValidateFlags	IgnoreMissingSrcFiles
s13	s255	S255	s13	i2	S16	i2
TargetImages	Target
2p0p4d1	c:\tmp\OOo-2.0.4-1-admin\openofficeorg20.msi		2p0p4d4	1		0
2p0p4d2	c:\tmp\OOo-2.0.4-2-admin\openofficeorg20.msi		2p0p4d4	2		0

I don't know whether the values in the Order columns actually are
needed or not.

==> UpgradedFiles_OptionalData

Upgraded	FTK	SymbolPaths	AllowIgnoreOnPatchError	IncludeWholeFile
s13	s255	S255	I2	I2
UpgradedFiles_OptionalData	Upgraded	FTK
2p0p4d4	msvcp71.dll			1
2p0p4d4	msvcr71.dll			1

See above why we need to mention msvcr71.dll and msvcp71.dll here.

==> UpgradedImages:

Upgraded	MsiPath	PatchMsiPath	SymbolPaths	Family
s13	s255	S255	S255	s8
UpgradedImages	Upgraded
2p0p4d4	c:\tmp\OOo-2.0.4-4-admin\openofficeorg20.msi			OOo
