3

We have a C++ project that uses a custom object-relational-mapping system, in which tables are defined by .tbl files. These are then run through a code-generator that creates, for each, a .h and a .cpp file.

I'm trying to get a custom build rule working for this, in Visual Studio 2008 and 2010.

This is what I have, so far:

<?xml version="1.0" encoding="utf-8"?>
<VisualStudioToolFile
    Name="z_dbbld"
    Version="8.00"
    >
    <Rules>
        <CustomBuildRule
            Name="z_dbbld"
            DisplayName="z_dbbld"
            CommandLine="$(SolutionDir)\tools\z_dbbld $(InputName)"
            Outputs="$(InputName).cpp"
            FileExtensions="*.tbl"
            ExecutionDescription="z_dbbld  $(InputName)"
            >
            <Properties>
            </Properties>
        </CustomBuildRule>
    </Rules>
</VisualStudioToolFile>

The problem is the dependencies. When I run a build on a clean checkout, where none of the files exist, I get "Cannot open include file" errors, for .h files that are generated by this rule.

I've tried changing Outputs to "$(InputName).h", and I still get the errors.

Now the thing is that these files are created, when the code generator runs. If I compile again, I don't have the errors, because all of the files were created in the first pass. But it makes doing a clean, automated, build from fresh checkout not work.

Any ideas?

Jeff Dege
  • 11,190
  • 22
  • 96
  • 165

2 Answers2

0

I think you need to specify the Output files in the main part of the build (looking at the very last sentence of http://msdn.microsoft.com/en-us/library/hefydhhy.aspx). Probably the easiest way to do that is to add a reference to the files when they exist and then delete them and see if the codegen step runs like it should.

sblom
  • 26,911
  • 4
  • 71
  • 95
  • I am adding the output files to the main part of the build. My problem is that if I add .h and .cpp to the build, and have a rule that says it can generate a .h from a .tbl, it complains that it can't find the .cpp, and if I have a rule that says it can generate a .cpp from a .tbl, it says it can't find the .h. The tool that is wrapped by the rule generates both, but I can't seem to figure out how to configure a rule that will tell it that. – Jeff Dege Oct 21 '11 at 14:29
  • From the documentation for ``, it sounds like you can list multiple files separated by semicolons. – sblom Oct 21 '11 at 16:52
0

The answer given by sblom is correct, but it does not explain the reason.

For each build rule (custom or native) the VS build system needs to know the complete list of inputs and outputs so that it can decide what part of the project needs to be built.

Your build rule declares the generated .cpp file as an output, so VS knows about it and will automatically build this file for you. Since you omitted the header file, VS does not know about it, so any source files that include this header will not know where to get it from and fail to build. A work around to get the build to work in this situation is to add the directory where this .h file is located to your include path, and then #includes of this file will work. You are basically enabling VS to know about this file in a different way.

Conversely, if you change your build rule to declare the header file as output, then source files that include it will know where to get this file from, but now VS does not know about your .cpp file so it won't build it. A work around for this case is to explicitly add the generated .cpp file to your project as a source file. Like in the above case, you are using a trick to get the build system to recognize the generated file.

But while the workarounds above will get you going they are not the best solution, since they just compensate for VS not knowing about a file. The best way to address this problem is to declare both the .cpp and the .h files as outputs in your rule, separating them with a semi-colon. This will enable VS to apply the correct behavior to both files.

Miguel Grinberg
  • 65,299
  • 14
  • 133
  • 152
  • Sorry for taking so long to get back to this. I'd been pulled to another project. When I specify both .h and .cpp as output files, VS doesn't complain, but it doesn't seem to connect the dependencies correctly. That is, it still attempts to compile .cpp files that #include generated .h files that haven't been built, yet. – Jeff Dege Nov 18 '11 at 17:17