Error F2063 Could not compile used unit (of dependent package) - delphi

I have written 2 packages: MEComps_DXE5 and AMLComps_DXE5. The latter depends on the former. Both should be multi-platform: Win32, Win64, and (in the future) OSX.
When I open the first package MEComps_DXE5, I am able to compile it, build it and install it. I get some warnings, as this library contains code that must also compile on old D5, but the build succeeds and creates the dcu and dcp files where expected.
When I open the second package AMLComps_DXE5, I find this situation:
If I do not declare the dependency on MEComps_DXE5, the package will compile and build correctly (no errors, dcu and dcp files are generated), but Delphi will warn me that it has implicitly imported units from MEComps_DXE5, and ask me to add the package to the dependency list (Requires)
If the dependency is declared, then the compilation will fail with "[dcc32 Fatal Error] MEComps_DXE5.dpk(52): F2063 Could not compile used unit 'MEClasses.pas'", where MEClasses is the first unit of the MEComps_DXE5 package.
I've been trying to solve this for a few days now, but to no avail. I'm working on two fronts:
Why is Delphi even trying to compile the other package? I have just built and installed it, and have all dcus and the dcp.
Why is the compilation failing?
As to the first question I have no clue whatsoever.
As to the second question, the documentation is useless in this case. It explains why not being able to compile a used unit is fatal, and states that the cause is determined by looking at the previous errors. But in this case, there are NO previous errors.
As MEComps_DXE5 actually compiles and builds on its own, I doubt this has anything to do with syntax or code. It would seem to be that the compiler is not able to find something it needs to compile those units.
The two packages reside each in their own directory. I put the MEComps\Win32 dcu directory on the library path and on the browsing path. The IDE actually has no problems looking up the used units.
I also checked the dcc32 command line and it seems that all envolved directories are known to the compiler.
Other info I can add:
Both packages have their own include file (in their source directory). I'm not sure if these are to be included in the package contains list or not, but I've tried both ways and nothing seemed to change.
Both packages have a corresponding Delphi 5 package which includes some of the same units and code (different dpk though). These compile and build correctly. Delphi 5 dcu files are generated in the source directory. Can this create problems with the XE5 compiler?
Here is the complete code for the MEComps_DXE5 package. I see a lot of compiler directives that Delphi inserted when it created the empty package. I didn't touch those:
package MEComps_DXE5;
{$R *.res}
{$IFDEF IMPLICITBUILDING This IFDEF should not be used by users}
{$ALIGN 8}
{$ASSERTIONS ON}
{$BOOLEVAL OFF}
{$DEBUGINFO ON}
{$EXTENDEDSYNTAX ON}
{$IMPORTEDDATA ON}
{$IOCHECKS ON}
{$LOCALSYMBOLS ON}
{$LONGSTRINGS ON}
{$OPENSTRINGS ON}
{$OPTIMIZATION OFF}
{$OVERFLOWCHECKS OFF}
{$RANGECHECKS OFF}
{$REFERENCEINFO ON}
{$SAFEDIVIDE OFF}
{$STACKFRAMES ON}
{$TYPEDADDRESS OFF}
{$VARSTRINGCHECKS ON}
{$WRITEABLECONST OFF}
{$MINENUMSIZE 1}
{$IMAGEBASE $400000}
{$DEFINE DEBUG}
{$ENDIF IMPLICITBUILDING}
{$IMPLICITBUILD ON}
requires
rtl,
fmx,
dbrtl,
xmlrtl;
contains
MEClasses in 'MEClasses.pas',
MEConsts in 'MEConsts.pas',
MEDataReader in 'MEDataReader.pas',
MEDateUtils in 'MEDateUtils.pas',
MEEncoding in 'MEEncoding.pas',
MEEncodingISO2022 in 'MEEncodingISO2022.pas',
MEFileUtils in 'MEFileUtils.pas',
MELists in 'MELists.pas',
MEMath in 'MEMath.pas',
MENumUtils in 'MENumUtils.pas',
MESQLUtils in 'MESQLUtils.pas',
MEStrUtils in 'MEStrUtils.pas',
MESysUtils in 'MESysUtils.pas',
METypes in 'METypes.pas',
MEURIUtils in 'MEURIUtils.pas',
MEXMLUtils in 'MEXMLUtils.pas';
end.

Delphi IDE is far from perfect when it comes to editing/compiling packages but you should solve the problem on your side - configure your packages better and Delphi will compile them correctly.
I can only give you general advices addressing the info given:
If you need a common include file for 2 packages create a separate directory for the file and add this directory to the search paths of both packages (in Base build configuration).
Never keep .dcu's in the same folders with source files; always set "unit output directory" option for your packages (also in Base build configuration); I recommend $(BDSCOMMONDIR)\MyPacks\$(Config)\$(Platform) as such directory for your packages; if you already have .dcu's in the source (.pas) folders delete them, does not matter which Delphi version created these .dcu's.
Never add paths to dependent package's sources to the search path, only paths to compiled .dcu's (would be $(BDSCOMMONDIR)\MyPacks\$(Config)\$(Platform) if you follow previous advice).

Related

One Delphi package is falsely detected as depending from other package

Recently I developed and installed VlControls Delphi package with own components.
Now when any developer on any machine takes other, one year old, CmGUI package, which existed long before VlControls, and tries to build it, following window pops up:
The following changes are necessary to make this package compatible with other installed packages.
Choose OK to apply these changes and rebuild the package.
Add VlControls.
VlControls contains implicit unit(s) TeeBlockCanvas, TeeMesh, TeeBlockEditor, TeeBlockGallery, TeeBlockClasses, TeeWater, TeeBlocks, TeeMakerConst, TeeLoadError, TeeTarga, TeeGLSLShaders, TeeViewBlock, TeeCamera, TeeMakerControl, TeePlayMP3, TeeTextureSelector, TeeMakerEditor, TeeSelectProperty, TeeClipBlock, TeePointEditor, Tee3DSFormat, TeeFacesBlock, TeeObjFormat, TeeSubdivideMesh, TeePointItemEditor, TeeActionGallery, TeeSoundSelector, TeeMakerLibrary, TeeLoadBlock, TeeExtruded, TeeRoundRect, TeeMoveAnimation, TeeNumberAnimation, TeeExtrudedEditor, TeeActionAnimation, TeeBlockAnimations, TeeBlockReplacer, TeeHelix, TeeRain, TeeBlockFormat, TeePipe, TeeProperties, TeeDraw3DEditor, TeeKinematics, TeeColorPalette, TeeRevolutionEditor, TeeRevolution, TeeAnimationGallery, VCLTee.TeeAnimateEditor, TeeTerrain, TeeEdgeStyle, TeeStairs, TeeChartBlock3DEditor, TeeChartBlock, TeeChart3D.
I do not know why this happens, because both packages are completely independent from each other. There are no files in CmGUI which contain "VlControls" string. What both packages have in common, are Tee chart components.
This happens only to this CmGUI package and other old packages are intact.
What could it be?
I am using Delphi 10.
CmGUI.dpk:
package CmGUI;
{$R *.res}
{$IFDEF IMPLICITBUILDING This IFDEF should not be used by users}
{$ALIGN 8}
{$ASSERTIONS OFF}
{$BOOLEVAL OFF}
{$DEBUGINFO ON}
{$EXTENDEDSYNTAX ON}
{$IMPORTEDDATA ON}
{$IOCHECKS OFF}
{$LOCALSYMBOLS ON}
{$LONGSTRINGS ON}
{$OPENSTRINGS ON}
{$OPTIMIZATION OFF}
{$OVERFLOWCHECKS OFF}
{$RANGECHECKS OFF}
{$REFERENCEINFO OFF}
{$SAFEDIVIDE OFF}
{$STACKFRAMES ON}
{$TYPEDADDRESS OFF}
{$VARSTRINGCHECKS ON}
{$WRITEABLECONST OFF}
{$MINENUMSIZE 1}
{$IMAGEBASE $400000}
{$DEFINE DEBUG}
{$ENDIF IMPLICITBUILDING}
{$IMPLICITBUILD ON}
requires
rtl,
vcl,
vclx,
dbrtl,
adortl,
tee923,
designide,
vclactnband,
dclstd,
OurPackageNumber1,
OurPackageNumber2,
vcltouch,
NxCommonRun_d10,
NxGridRun_d10,
TeePro923,
TeeUI923,
TeeImage923,
TeeGL923,
VclSmp,
vclFireDAC,
FireDACIBDriver,
FireDACPgDriver,
IndyProtocols,
NxCollectionRun_d10;
contains
//Here come units from this package only. No external units are included.
end.
VlControls.dpk:
package VlControls;
{$R *.res}
{$IFDEF IMPLICITBUILDING This IFDEF should not be used by users}
{$ALIGN 8}
{$ASSERTIONS ON}
{$BOOLEVAL OFF}
{$DEBUGINFO OFF}
{$EXTENDEDSYNTAX ON}
{$IMPORTEDDATA ON}
{$IOCHECKS ON}
{$LOCALSYMBOLS OFF}
{$LONGSTRINGS ON}
{$OPENSTRINGS ON}
{$OPTIMIZATION ON}
{$OVERFLOWCHECKS OFF}
{$RANGECHECKS OFF}
{$REFERENCEINFO OFF}
{$SAFEDIVIDE OFF}
{$STACKFRAMES OFF}
{$TYPEDADDRESS OFF}
{$VARSTRINGCHECKS ON}
{$WRITEABLECONST OFF}
{$MINENUMSIZE 1}
{$IMAGEBASE $400000}
{$DEFINE RELEASE}
{$ENDIF IMPLICITBUILDING}
{$IMPLICITBUILD ON}
requires
rtl,
vcl,
vclimg,
vclx,
TeePro923,
TeeUI923,
Tee923,
DesignIDE,
TeeImage923,
TeeGL923,
dbrtl,
FireDAC,
FireDACCommonDriver,
FireDACCommon,
IndySystem,
IndyCore;
contains
//Here come units from this package only. No external units are included.
end.
Update
Ok, I looked closely at my package and handled all warnings it displayed at compile time. Now the contains section has following units:
TeeBlockCanvas,
TeeChart3D,
TeeChartBlock3DEditor,
TeeAnimationGallery,
TeeColorPalette,
TeeDraw3DEditor,
TeeProperties,
TeeBlockReplacer,
TeeEdgeStyle,
TeeLoadBlock,
TeeSoundSelector,
TeeActionGallery,
TeeMakerLibrary,
TeeMakerControl,
TeeCamera,
TeePointItemEditor,
TeeSelectProperty,
TeeTextureSelector,
TeeBlockFormat,
TeeSubdivideMesh,
TeePointEditor,
TeeGLSLShaders,
TeeLoadError,
TeeChartBlock,
TeeMesh,
TeeTerrain,
TeeMakerEditor,
TeeClipBlock,
TeeMoveAnimation,
TeeActionAnimation,
TeeBlockAnimations,
TeeNumberAnimation,
TeeKinematics,
TeeBlockEditor,
TeeBlockGallery,
TeeBlockClasses,
TeeViewBlock,
TeeExtrudedEditor,
TeeHelix,
TeeRevolution,
TeeRevolutionEditor,
TeeStairs,
TeeRain,
TeeWater,
VCLTee.TeeAnimateEditor,
TeePlayMP3,
Tee3DSFormat,
TeeObjFormat,
TeeFacesBlock,
TeePipe,
TeeExtruded,
TeeRoundRect,
TeeBlocks,
TeeMakerConst,
TeeTarga;
As I understand, next step would be to look at each unit and find out which package it belongs to and then add package name to requires section removing unit name from contains section.
How to find out which package the unit belongs to if I have no *.pas files, but only *.bpl and *.dcu?
Obviously your package uses a lot of units from a TeeChart package (or several packages? I don't know TeeChart very well). Do not implicitly import them, just put the packages your explicit units (i.e. the units you explicitly name in the contains section) need in the requires section.
Not only does that make your package a lot slimmer, it also avoids such naming conflicts. Anyone who uses your package will face a naming conflict when using other packages that contain units with the same name. That is why the IDE, recognizing that all or most of the packages the other package uses, are in your package, recommends linking to your package.
If your package did not contain these units, that wouldn't happen. That is why you should always, really always, avoid having implicitly imported units. If that happens, you get a warning (during compilation of the package). Heed it.
Example (package MyControls):
contains
MyUnit;
and in MyUnit:
unit MyUnit;
uses
TeeThis, TeeThat, TeeOther;
Now the TeeThis, TeeThat and TeeOther units are implicitly linked into your package. But if your package references the other package that contains these TeeXXX units (say, TeeChart.bpl), the compiler will not add them to your package, it will use them indirectly (reference them) from the TeeChart package. That makes your package smaller, and allows other packages to use the same TeeXXX units in the same way. There will be no naming conflict between your and other packages regarding the TeeXXX units.
requires
TeeChart,
etcetera;
Of course this puts on you the burden to ensure that everyone who uses your package will have the TeeChart package too, if necessary by distributing that package too (assuming licenses allow that).
UPDATE
Your update shows that you now have the TeeChart packages in your requires. If the message is correct, the compiler also includes the units TeeBlockCanvas, TeeMesh, TeeBlockEditor, TeeBlockGallery, TeeBlockClasses, etc.etc. in your package, so the units you explicitly include (in the containssection) seem to use these units too. Put the packages that contain these units (probably TeePro923, TeeUI923 and Tee923) in the requires section too:
requires
rtl,
vcl,
vclx,
// etc...
TeePro923,
TeeUI923,
Tee923,
TeeImage923,
TeeGL923,
// etc...
Now you should not get the message, that all those units were implicitly included into your package, anymore.

{$WARN SYMBOL_PLATFORM OFF} does not turn off warnings

I have this piece of code:
INTERFACE
{$WARN SYMBOL_PLATFORM OFF}
USES
Winapi.Windows, etc, {$IFDEF MSWINDOWS}Vcl.FileCtrl, {$ENDIF} System.IniFiles;
{$WARN SYMBOL_PLATFORM ON}
The compiler shows:
[dcc32 Warning] W1005 Unit 'Vcl.FileCtrl' is
specific to a platform
even though the {$WARN SYMBOL_PLATFORM OFF} is there.
Why?
You are using the wrong directive. SYMBOL_PLATFORM controls warnings for symbols marked platform specific. Your warning relates to a unit marked platform specific.
Control these warnings with UNIT_PLATFORM.
The whole unit is tagged (using the platform hint directive) as one that contains material that might not be available on all platforms. If you are writing multi-device applications, the unit might cause a problem. For example, a unit that uses objects defined in OleAuto might be tagged using the PLATFORM directive.
The $WARN UNIT_PLATFORM ON/OFF compiler directive turns on or off all warnings about the platform directive in units where the platform directive is specified.
There's a really easy way for you to work this out for yourself. Take a look at the two documentation topics I linked to above. Their titles are:
W1002 Symbol '%s' is specific to a platform (Delphi)
W1005 Unit '%s' is specific to a platform (Delphi)
The compiler warning that you received names the warning as W1005. This is all you need to know to determine which directive to use to control it. If you have any trouble finding them simply search for the warning name, W1005 in this instance. Or refer to the documentation that lists them all.

Can't compile package containing DSUtils in XE2

I am trying to compile a package containing DSUtils.pas (part of DSPack) and it fails because it tries to compile wrong DirectShow9.pas unit - not the one from the DSPack but the one from the Delphi XE2 (Update 3) RTL.
The problem can be repeated with a minimal package:
package Package1;
{$R *.res}
{$IFDEF IMPLICITBUILDING This IFDEF should not be used by users}
{$ALIGN 8}
{$ASSERTIONS ON}
{$BOOLEVAL OFF}
{$DEBUGINFO ON}
{$EXTENDEDSYNTAX ON}
{$IMPORTEDDATA ON}
{$IOCHECKS ON}
{$LOCALSYMBOLS ON}
{$LONGSTRINGS ON}
{$OPENSTRINGS ON}
{$OPTIMIZATION OFF}
{$OVERFLOWCHECKS OFF}
{$RANGECHECKS OFF}
{$REFERENCEINFO ON}
{$SAFEDIVIDE OFF}
{$STACKFRAMES ON}
{$TYPEDADDRESS OFF}
{$VARSTRINGCHECKS ON}
{$WRITEABLECONST OFF}
{$MINENUMSIZE 1}
{$IMAGEBASE $400000}
{$DEFINE DEBUG}
{$ENDIF IMPLICITBUILDING}
{$IMPLICITBUILD ON}
requires
rtl;
contains
DSUtils in 'x:\common\pkg\dspack\src\DSPack\DSUtils.pas';
end.
The error occurs in DSUtils line 1058 and the error is Undeclared identifier: FrameRateCode.
Result.FrameRateCode := (x and $00000003) shr 00;
Undeclared is 'FrameRateCode' - CtrlClick on the Result brings us to Winapi.DirectShow9 (in the RTL folder) which doesn't have this field declared.
Interesting part - if I go to the DSUtils uses list, click on DirectShow9 and press Ctrl+Enter, the DSpack version of the unit will open (and this unit has FrameRateCode field defined). So Delphi knows where the unit is. It just tries to compile the package by using the wrong DirectShow9.
Interesting tidbit: If I'm compiling a normal application (non-package) that uses DSUtils, everything works fine.
What I've tried:
Compiling DirectShow9 from the DSPack into its own package (actually I used DirectX9 package from DSPack which contains all files from the DirectX9 folder) and adding it to the 'requires' list. Doesn't work.
Adding the folder with DirectShow9 file (from DSPack) to the beginning of the system path and rebooting. Doesn't work.
Adding the folder with DirectShow9 file to the beginning of the library path. Doesn't work.
Adding the DirectShow9 unit to the package with the explicit path. Doesn't work.
Copying the DirectX9*.pas into the DSPack folder so that the DirectShow9 unit would be in the same folder as the DSUtils unit. Doesn't work.
I see three possible workarounds, but I'm not happy with any of them.
I can comment out the problematic code. Luckily, it is only this one line, everything else compiles with Delphi's DirectShow9.
I can rename DirectShow9 from DSPack but then I may have to fix the 'uses' part in different application.
I can turn off automatic prefixing with 'Winapi.' but that will cause me lots of additional work editing thousands and thousands files.
What I would really like to see is getting XE2 to use the right source file.
I faced the same problem, and I simply commented out all the problem lines (there was 2 or 3 of them). Everything works perfectly fine.
Another option is to use the latest DSPack (which is compatible with XE2): http://code.google.com/p/dspack/
Or you can rename DSPack's DirectShow9 file, as discussed here: http://www.progdigy.com/forums/viewtopic.php?p=16971

Unit GIFImg was compiled with a different version of CCR.Exif.Consts.SOutOfResources

I was trying to use the EXIF library in one of my packages. It worked before but now I get strange messages:
[DCC Fatal Error] F2051 Unit GIFImg was compiled with a different
version of CCR.Exif.Consts.SOutOfResources
I don't really get it... Why Delphi tries to recompile one of its files? How do I fix this?
GifImg is located here:
c:\Program Files\Embarcadero\RAD Studio\8.0\source\vcl\GIFImg.pas
Update:
I looked at the date of that file (1 PAS and 2 DCUs) and it has the same date as any other file in RAD Studio\8.0\source\vcl folder. So, the file was not accidentally modified.
Update2:
This is my uses clause:
USES Windows, SysUtils, AnsiStrings, Graphics, Dialogs, Classes, jPeg,
pngImage,
janFX, //CCR.Exif,
{$IFDEF VER150}
GIFImageFinn {Delphi 7}
{$ELSE}
GIFImg {Delphi 2010/XE}
{$ENDIF}
;
If I comment the CCR.EXIF unit, it starts to compile my package. So, adding EXIF to my package breaks something.
What you report doesn't quite add up. The GIFImg unit that is part of the Delphi source does not refer to CCR.Exif.Consts.SOutOfResources. And none of the units used by GIFImg refer to it either.
So the explanations that seem plausible to me are:
You are including a unit called GIFImg somewhere in your project.
You've found a compiler bug.
The error message F2051 is emitted typically, in my experience, when you attempt to recompile an RTL/VCL unit but fail to set the project options to match that used by the true RTL/VCL. Alternatively it will be emitted when you recompile an RTL/VCL unit that has modifications in its interface section.
Solved:
I removed the dots in the name of the files.
CCRExif instead of CCR.Exif.
That was a nasty one.

Delphi warning - W1002 Symbol 'FileSetDate' is specific to a platform

When I compile my application under Delphi 2006 I get the following warning
[Pascal Warning]- W1002 Symbol 'FileSetDate' is specific to a platform
What must I do to suppress this warning?
The code
MyLastError:= FileSetDate( Files[ i ].Handle, DateTimeToFileDate( arcDate ) );
1) In the project options you can choose the compiler messages you want to see.
If you don't care about platform independency you can just switch off the platform warning there.
2) Another way is disabling the warning for a certain part of the code:
{$WARN SYMBOL_PLATFORM OFF}
// Your code
{$WARN SYMBOL_PLATFORM ON}
For a complete list of options look at the Delphi help file at the topic '$WARN'
3) A last way would be adding
{$WARNINGS OFF}
// Your code
{$WARNINGS ON}
but that is dangerous, because all warnings will be suppressed.
4) Additionally, as the other answers have already suggested, you could just switch to the platform independant variant of FileSetDate which works on file names (i.e. Strings), but as far as I understand that was not your question.
Although the answer of DR solves the warning, it is not the correct solution.
You should use the platform independent version of FileSetDate:
function FileSetDate(const FileName: string; Age: Integer): Integer; overload;
Also in SysUtils.
You can turn off the platform unit and platform symbol compiler warnings. They are obsolete (and disabled in Delphi 2009 by default). They were introduced when there was a Delphi for Linux (Kylix). They do not have a meaning anymore. Especially with the replacement of Delphi.NET with Delphi Prism.
You can turn them off for the whole project in the Project Options dialog (Compiler Messages).

Resources