Re: Any tips?
On 3/14/2013 6:34 PM, James Kanze wrote:
I wonder where this comes -- MS switched to MsBuild a few years ago, and
in that you can do about anything you could in a makefile. Yes, those
who mastered makefiles already may be better off with that. Others are
probably not, as for the sensible stuff it's ways simpler, and plays
naturally with the IDE.
That's simply not true.
'True' is never so simple. :) Well, reading my words it is possible to
mean it too literally -- by "anything" I meant a practical approach, we
have many build sytems tuned for different things and ways of work, and
some weaknesses, but *able* to carry out processing any kind of inputs
to any kind of outputs using any kind of translators in between. In
actual work we normally bent to what our tools like rather than waste
much time on fighting a weakness. And IME it's way less terrible than it
looks unless build systems are changed every few months.
Yes, VS has a plenty of problems writing the project files (at least
VS2010 I use), like the property manager is just FUBAR due to bugs, and
the regular editor is obsessed to write the attributes for every config.
But the former is hardly ever needed and the latter is easy to overcome
-- and before checkin you look at diff anyway.
There are so many things that one can
easily do in makefiles, but which are extremely complicated, if
not impossible, with MS's project and solution files (which is
what the IDE uses). Some examples of things you cannot do
in a Microsoft project:
- Build a local .exe to generate the code you need to compile
for the .dll the project is supposed to build. You have to
create a separate project for the .exe (even if it is build from
only a single .cpp). Which, of course, exposes an internal
detail of the project to everyone working on the solution.
You just described how to solve the *build*. So it is not impossible,
right? All tools normally impose some way of organization. So you youse
two projects instead of one. Actually I can think of several ways to
work it around, but all look way too much hassle with an excessive
requirement (and one pretty moot with original comparison).
- Use the same project in different solutions, with the
solution passing down information telling the project how to
configure itself. You can work around this somewhat, by using
conditionals in the project file, but it's awkward, since the
support for conditionals only supports full equality.
Well, it's indeed an overlook that you can't define macros and params
directly in .sln, but you can define them in several ways. And having a
..props file with the condition on solution name and defining them seem
not such a big difference to me.
You
can't make something conditional on a regular expression match
on the solution name, for example.
I'm not so proficient in msbuild to provide actual counterexample code
but am 99% positive that claim is false. You can use a wide range of
string manipulation and other functions -- I do in practice. [it was a
year ago when I had to fix the build of or project]. I recall i could
use anything you can do with a C# String.
And conditions on the
solution name are the only way you can make anything dependent
on the actual solution file.
I bet in practice you use the project in just a handful of solutions and
can figure out groups with just basic string ops if regex is really not
accessible -- what may well be.
Add to this that the VS compiler's error messages can be totally
useless when templates are involved. Not always, not even
usually, but from time to time, you'll get an error message
without the slightest indication of where the error is in *your*
sources.
Yeah, that is plain pure PITA and shame on MS folks. Actually templates
are the better covered part -- but just have an error in a .h file, the
message will not tell how it was included or even which .cpp was being
compiled. (and it's braindead that /showincludes is option that modifies
the project rather than being part of env. Can be worked around somewhat
but still major WTF, especially as would need minimal work on the
implementation.)
I wish msvc had diagnostics on level of gcc. But it's the compiler issue
and has little to do with the IDE or the build.
(for template probblems remember that the 'error list' contains only one
line of info -- if you switch to output you (may) find more diagnostics
explaining the case, with navigation and whatever. )
And the fact that you can't debug into code which was
compiled elsewhere, even if you have the sources.
You what? You can attach to any process, and if one crashes you're
offered attach JIT. You can load symbols anytime and anywhere from
remote servers or collect them in your cache, or just ad hoc -- if you
have them certainly. (did you try right-click on gray lines in stack
trace and use Load symbols'?
Without symbols you're really limited to assy, but it may still be
better than nothing. And IIRC you can force to use source file even if
it is not the same as during compile at your own risk.
(I've
recently worked on a Python interface, and at times, it was
useful to step into the Python code, to see what Python was
expecting of me, and what I was doing wrong. The VS debugger
simply refused to do it; luckily, I had access to Linux box as
well, with gdb.)
Did you install the python extension to VS? I never tried a mix like you
describe but it definitely can walk on python separately.
Certainly you CAN and definitely should share most rules -- that is done
by creating .props and .targets files, and the .vcxproj should have only
the file lists. Certainly any really specific options can be set (either
per project or per file).
Certainly. That's what we do, and I've written Python scripts
to generate new projects, to ensure that every one stays on the
same page. (There are a few things, normally at the top, which
don't seem to work if you put them in at .props: the list of
project configurations, for example.
I didn't have to mess with that part. IMO configuration should work if
you import the props early enough, but the IDE would likely not
recognize them. (It looks for some labels to decypher stuff and if you
stray from what it expects, it misreports some elements -- but they
still fork fine in the build.)
Which was a pain when
I had to add support for 64 bits, but that's not something you
do every day.)
My observation is also that configurations are PITA -- and if you try to
mix C# with C++ in a solution it goes out of hand. Fortunately I could
weed out everything and just have a Debug and Release from the initial
mess. It's especially "nice" how solution creates a full matrix of
config and target.
Do I guess right that you tried to sidestep the mess by creating a copy
of the .sln and one use 32 and the other for 64 bit? I'd probably try
something like that.
But the problem remains: you cannot directly
push down information from the solution file (which in addition
uses GUIDs everywhere, rather than the names of anything, which
makes editing it by hand a real pain). Our .props files are
full of things like:
<attribute_name Condition=" '$(SolutionName)' == 'OneSolution' ">value</attribute_name>
<attribute_name Condition=" '$(SolutionName)' == 'DifferentSolution' ">different_value</attribute_name>
...
Every time we use the project in a new solution, we have to come
back and add it here.
If you use some naming schema that fits with the available string
functions you can make it much simpler. I'd put .EndsWith("64") or
..IndexOf to locate substrings. That IMO could save most of the edits in
a practical system.
But even with the raw form,
compared to all the crap I face everyday I would not consider to mention
that as a minor nuisance. Yes, you have to configure the stuff somewhere
-- so have one file that maps solution names to a set of attribute
values, and the projects work with the latter. And include the mapper up
front.
Sure in my practice there's no proliferation of .sln files, others may
not be so fortunate.
http://msdn.microsoft.com/en-us/library/dd633440.aspx
And from hits like these
http://www.msbuildextensionpack.com/help/4.0.5.0/html/9c5401ed-6f55-089e-3918-2476c186ca66.htm
I'd think you can even extend the msbuild expressions.
So all you write about is possible alright. I don't say it is trivial or
nice but that same applies to make and probably most other build systems
for big real-life projects.
It's true that most build systems are pretty bad: I've been
using GNU make, largely because I know it, but the make syntax
is horrible. Of the other systems I've tried, however, either
they don't have the support for some feature I need, or they're
simply broken.
I worked with several build systems and recall none that could be
figured out without massive reading, or that was simple to find out any
problem if it surfaced. So my general conclusion is that build is a
general life-sucker and I feel lucky if there's a guy around who can
manage it. :) Well, currently I'm out of that luck.
The dependency checking in both Jam and VS is seriously broken:
> VS fails when pre-build steps modify sources or headers (and
Well, that one I would not call 'broken' but the specified way it does
things. IMO it is possible to make build fit that model.
> only allows one pre-build step per project, so you have to write
> scripts to chain several together),
All those steps are defined in some msbuild script file that can be
rewritten to your liking. Yes, I agree that the stock pre and postbuild
steps are extremely limited, and are just dropped in for simple things.
But it is not a msbuild restriction, rather like I claimed make is
broken because I didn't like some of the stock rules.
IIRC the stock steps DO have attribute to describe inputs and outputs
and if you use them correctly, the dependency will be considered. If you
jut modify files without telling the system that will go unnoticed.
However I recall in VS2010 the thing is bugged -- while specification
and even UI allows a list of outputs, only the first one is actually
considered. :-(((
My practical problem is not related to the theory of work at all -- I
keep source generation and other translation as solvable.
But I encounter buggy behavior with dependency output itself. (in the
intermediate folder files are created with inputs, outputs, command
lines, etc) On my machine I see some weird entries listed as
dependency, some nvidia drs.bin file belonging to the video driver.
Other time some .h files are missing from the list. With a small but
noticeable chance. Guess due to some race conditions like those
prevalent in the msdev IDE. Now THAT is something really nasty.
If you called this system not usable for that reason I'd not say a word
of objection.