Chandler Carruth | 1 Aug 2011 01:13
Picon
Favicon

Re: on libc++ extensions and slist

On Sat, Jul 30, 2011 at 6:31 PM, Howard Hinnant <hhinnant <at> apple.com> wrote:
In existing C++03 standard libraries there are a ton of extensions.  Some good, some not so good.  Some of the better ones have morphed into official  C++11 libraries.  However, I can't think of a single example where an extension has been standardized unchanged from its extension form.  There is good reason for this.

I'm going to pick on slist.  But my argument is meant to be broader than slist.

<snip>

I want to clarify, I don't disagree with *any* of your diagnosis. I agree completely with the flaws and problems present in slist.
 
When our customers are migrating to libc++, it is at a time of their choosing.  They have set aside time to do the migration.  And shown interest in doing so.  A year after they migrate, when subtle problems surface, they are not going to be in the mood to be educated.  They are going to be in the mood to be educated about the right way to do things *when they are migrating*, and not later when run time problems arise.

Keep in mind that some customers at least may not be able to update all of their code in one fell swoop. Forcing changes to the client code in too many places may make it impossible to migrate at all rather than merely adding to the cost of migration.

Also, in some contexts, there is no user education to be done. The code in question is legacy code, old and slated for deletion. No one maintains it, updates it, or cares for it; but it isn't (quite) ready to be removed once and for all. These situations make the arguments about education only apply to a subset of the migration (although there they certainly make sense).
 
1.  We could create an ext::slist that lacks size().  That way the customer would not have to change their code unless they used size().

I agree with your disadvantages here. Reducing (slightly) the magnitude of those changes doesn't seem as attractive. For a significant chunk of the code I've seen in this position, the cost of changing the code is dominated by a very high constant factor, not by the nature of the change itself. (Consider, an open source library that has to have changes pushed back upstream, and written in a particular style and which no one is actively maintaining any longer.)
 
2.  Status quo:  We could do nothing.

Disadvantage:  I'm seeing rising complaints about migration efforts.

There is another disadvantage: it may preclude migration at all. If there exists code that simply can't be updated, you're now stuck.

More realistically, it may drive the cost of migration sufficiently far up that it becomes a difficult or impossible to tackle problem.
 
3.  Educate:  In a private email about a week ago M.E. O'Neill noted that we should provide documentation recommending migration strategies for things like slist -> forward_list.  She suggested actually providing an <slist> header which did nothing but point to the documentation and then error out.  I'm not sure I'd go as far as providing such a header.  But I am really enthusiastic about a "migration document".  Having something to point to which explains why using slist is like playing with a loaded gun.  When people are migrating, they are open to such arguments if those arguments are both convincing and readily available.  And if the migration document provides a way to experiment without committing yourself (i.e. make it easy to backpedal the migration):

Again, see my points above about education. Sometimes there is no one to educate, and no one intending to maintain or improve the code long term. Certainly, documenting the migration hurdles is very helpful to those doing the migration, but it may not be enough for sufficiently popular extensions.
 
Disadvantage:  Doesn't provide seamless migration.  And it is a fair amount of work to document.

Field experience:  I'm responsible for deprecating auto_ptr.  At the same time I introduced unique_ptr.  This involved a lot of documentation.  Not only with committee papers, but in participating in countless newsgroup and mailing posts to the general public, presentations, etc.  And it is paying off.  I now see lots of people I've never heard of telling others that they should replace auto_ptr with unique_ptr, even though it is not a drop-in replacement.  And the listeners are receptive to the message.

I don't really dispute any part of this other than the value of education on old code. For new code and actively maintained code, this is all spot on.

That said, I would like to migrate a very large codebase to a point where it could use libc++. Why? Because I want to migrate the codebase to C++0x, and one aspect of doing that is migrating to a viable standard library for C++0x. I'm very interested in investigating the trade-offs between libstdc++ and libc++ here, but we can't do that if we have to update the entire code base in the process.

I actually will pick on hash_{map,set} here because I think they're even better examples. I actually agree that 'slist' is border-line.

There is essentially zero possibility that we will use hash_map forever. We will switch to unordered_map because its better and because its standardized. However, it isn't available (technically[1]) until we switch to C++0x. With a codebase of sufficiently large size, we can't afford to do both transitions simultaneously, we have to first switch to C++0x, and then switch from old extension containers to new standard ones.

[1]: Yes it is available as std::tr1::unordered_map, but now we have to migrate the codebase 3 times, once to the std::tr1 implementation, once to 0x, and then once back to std::. That drives up the cost of migration by another notch.

Now, my goal is to have two different libraries to choose from when migrating to C++0x so that bugs in one don't block progress. But in order to do that we need at least "enough" extension support in both libraries to make it tractable to use either one.


This isn't an argument for "all", merely for "enough". For example libc++ already has hash_map and hash_set, and that is probably the single most important container to support. We've now gotten a trial run conversion of a non-trivial chunk of our codebase to libc++, and the only other container that was missing was 'slist'. The only other missing extensions were a handful of very rarely used algorithms. Algorithms are much easier to work around than types, as two pieces of code can use different but compatible implementations without conflicting. I see no reason for libc++ to bother with these extensions.

The types are trickier. Had there been 10 extension types we needed, making 'slist' a slippery slope of extensions we might never get off of, I would be more sympathetic to drawing the line sooner and more forcefully. I think the best argument for adding a compatible 'slist' implementation is that it seems to be the last we'll need.
_______________________________________________
cfe-dev mailing list
cfe-dev@...
http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev
John McCall | 1 Aug 2011 01:13
Picon
Favicon

Re: Segfault on uncaught exception

On Jul 30, 2011, at 6:10 PM, Thomas Sanchez wrote:
> I was playing with clang++ a little and I had a surprise with the exceptions.

A large number of uncaught-exception bugs have been fixed on ToT;  would you mind verifying that your bug is
one of them?

John.
Sean Hunt | 1 Aug 2011 01:39
Picon
Picon
Favicon

Re: on libc++ extensions and slist

On Sat, Jul 30, 2011 at 18:31, Howard Hinnant <hhinnant-2kanFRK1Nck@public.gmane.orgm> wrote:
<snip>

1.  We could create an ext::slist that lacks size().  That way the customer would not have to change their code unless they used size().

Disadvantage:  We haven't delivered a seamless drop in replacement lib.  They still have to change their code.  Why not also change the name of the container to std::forward_list at the same time?  Otherwise we have to support slist.  And not just to ease migration.  Once we introduce it, we have to support it for forever for backward compatibility with our own lib.

Size is not the only issue with slist. Slist also features container operations without the _after suffix, meaning they operate on the elements pointed to by the iterators. These, also, must have linear complexity, and so don't exist in forward_list. Given this, the migration may be far from trivial - especially given that clients might find that they really ought to be using a doubly-linked list (or some other container) in their situation.

One idea that I had for an unrelated problem but might be useful for this one as well would be to have specific deprecated tags like [[deprecated(forward_string)]]. We could put these on the functions that are removed from the standard library, and migration could be done one container at a time by turning on each deprecated tag in order (something akin to -Wdeprecated=forward_string). We could put this on the slist functions that are not present in forward_list, and thus someone can clean up their codebase until it should be a drop-in replacement, and then perform the drop-in replacement. (N.B. to Chandler: I'm aware that this is not applicable in our situation).

Thoughts?

Sean
_______________________________________________
cfe-dev mailing list
cfe-dev@...
http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev
Thomas Sanchez | 1 Aug 2011 01:52
Picon

Re: Segfault on uncaught exception

2011/7/31 John McCall <rjmccall <at> apple.com>:
> A large number of uncaught-exception bugs have been fixed on ToT;  would you mind verifying that your bug
is one of them?

Yes it was, thanks!

--

-- 
Thomas Sanchez

_______________________________________________
cfe-dev mailing list
cfe-dev <at> cs.uiuc.edu
http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev
Howard Hinnant | 1 Aug 2011 03:06
Picon
Favicon

Re: on libc++ extensions and slist

On Jul 31, 2011, at 7:13 PM, Chandler Carruth wrote:

> This isn't an argument for "all", merely for "enough". For example libc++ already has hash_map and
hash_set, and that is probably the single most important container to support. We've now gotten a trial
run conversion of a non-trivial chunk of our codebase to libc++, and the only other container that was
missing was 'slist'. The only other missing extensions were a handful of very rarely used algorithms.
Algorithms are much easier to work around than types, as two pieces of code can use different but
compatible implementations without conflicting. I see no reason for libc++ to bother with these extensions.
> 
> The types are trickier. Had there been 10 extension types we needed, making 'slist' a slippery slope of
extensions we might never get off of, I would be more sympathetic to drawing the line sooner and more
forcefully. I think the best argument for adding a compatible 'slist' implementation is that it seems to
be the last we'll need.

Thanks Chandler.  The migration experience details you have shared with us are very important.

I was wondering if you could expound a little on why the following migration technique isn't viable:

#include <ciso646>  // identify library

#ifdef _LIBCPP_VERSION
#   include <forward_list>
  template <class T> using MyList = std::forward_list<T>;
#else
#   include <ext/slist>
  template <class T> using MyList = __gnu_cxx::slist<T>;
#endif

int main()
{
  MyList<int> c;
  c.push_front(1);
  c.push_front(2);
  c.push_front(3);
}

If you use member functions which aren't in std::foward_list (such as insert), I can see how that would be
problematic.  And in that case I find myself wondering if an adaptor approach around std::forward_list
wouldn't be sufficient.  Something like:

template <class T, class A>
class slist
{
   std::foward_list<T, A> data_;

public:
   // forward everything to data_...

   // except size
   size_type size() const {return std::distance(data_.begin(), data_.end());}

   // and previous
   iterator previous(iterator i)
   {
       iterator r = data_.before_begin();
       for (const_iterator j = data_.begin(); j != i; ++i)
           ++r;
       return r;
   }

   const_iterator previous(const_iterator i) const
   {
       const_iterator r = data_.before_begin();
       for (const_iterator j = data_.begin(); j != i; ++i)
           ++r;
       return r;
   }

    iterator insert(iterator pos, const T& x)
        {return data_.insert_after(previous(pos), x);}

   // etc...
};

Howard
François-Xavier Bourlet | 1 Aug 2011 08:30
Picon
Gravatar

Re: Adding C++ code with a plugin

Hi,

I am trying to do the same kind of things! And I ended up at the same
point as you. Glad that I am not alone trying to rewrite the AST
trough a plugin ;)

In my case what I want to do is add new custom attribute and modify
the AST in consequence.

C++0x propose a standard way to define compiler specific attribute using [[ ]]:

[[some_attr_namespace::attr]]
void myfunc(){};

etc.

I want to change the AST nodes decorated with some custom attribute.
As example, I would like to be able to transform something like that:

[[coroutine::generator]]
int range(int min, int max) {
  while (min != max) {
    yield(min++);
  }
}

to something like:

void range_(coroutine::Yielder<int> yield, int min, int max) {
  while (min != max) {
    yield(min++);
  }
}
coroutine::generator_builder<int (coroutine::Yielder<int> yield, int,
int)> range(&range_);

If it's necessary to patch clang to add a new kind of plugin/new
plugin feature to allow AST modification in the middle of the
compilation process, I am willing to try doing it!

Thanks a lots for any answers.

Thanks also for this wonderful C++ compiler guys. Really.

On Thu, Jul 21, 2011 at 8:50 AM, Benjamin Orgogozo
<benjamin.orgogozo@...> wrote:
> Hello,
>
> I'm new to this mailing-list and to CLANG in general so please forgive me if I
> ask a quite stupid question...
>
> I've been reading a few mailing lists and webpages on CLANG now but I can't find
> a clear answer to my question so I hope someone here could at least point me to
> the correct resource.
>
> My goal is simple: I want to compile a C++ code but after automatically adding a
> few lines of code. Here are my question:
>
> - can (or want) I do that with a plugin? At the beginning I wanted to write a
> plugin to the front-end and change the AST but it seems (but I hope I'm wrong)
> that when I use the "load" and "plugin" command line option, I can't generate
> code at the end. Is it true or not?
>
> - How should I do this transformation? The code I want to add is really simple:
> I just want to add function calls in the constructor of classes with specific
> class members as parameters.
> For example, I want to transform:
>
> class A {
>  float f;
> };
> class foo {
>  int bar;
>
>  foo() {}
> };
>
> into
>
> class A {
>  float f;
> };
> class foo {
>  int bar;
>
>  foo() {baz(bar);}
> };
>
> It seems that I have two options:
>  * use a rewriter to add nodes within the AST, but it seems that it's only for
> source to source transformation (and I would like to avoid that if possible).
>  * use a TreeTransform which looks fine but I think I read somewhere that it
> modifiying the AST for compiling it later wasn't always a good idea.
>
>
>
> >From what I understood, it seems that I want to use treetransform, but I wonder
> if I can use it within a plugin *and* generate code with only one call to clang.
>
>
> Any comment and pointer is more than welcome!
>
> Thanks,
>
> --
>  Benjamin Orgogozo
>
> _______________________________________________
> cfe-dev mailing list
> cfe-dev@...
> http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev
>

--

-- 
François-Xavier Bourlet
Ruben Van Boxem | 1 Aug 2011 13:37
Picon
Gravatar

Expanding the Clang Status page to report the status of several OSes and projects

Hi,

I just noticed that the table listing projects and Clang compatibility
was recently removed. This idea still has a lot of merit, and has been
breeding in my mind for several days.

I would like to provide test result data for several popular and high
quality open source libraries that provide an extensive test suite so
the compiled result is strictly analysed. I would do this on Windows
(mingw-w64 CRT+ GCC 4.6 libstdc++ and linker), but I would like this
to be more than a single email to the mailing list.

To this effect, I thought that perhaps expanding the first table that
was on http://clang.llvm.org/cxx_status.html could be expanded
significantly, in vertical (projects) and horizontal
(platforms=OS+arch(+crt in the case of Windows)).

Although I believe that Clang is production ready on Mac OS, it is far
from my elementary trust in the Windows MinGW world. Therefore, I
think it is useful to keep track of wide-scale progress in a
centralized place, because I feel the bugtracker doesn't get enough
attention (at least the problems I am experiencing ;-)).

Concretely, I suggest a larger table with colors like the C++0x table,
with red = doesn't build, orange/yellow: builds, but tests fail due to
a problem in clang (which also means that the tests pass for GCC), and
green is that it builds and all tests pass without a hitch. Links
could be placed to bug reports about the issue, where detailed
information for interested developers could be placed.

The libraries I suggest that should be used as a "quality mark" are
(more are of course welcome!):

Qt: Huge GUI and core library framework. High quality code that is
extremely cross-platform. Has an internal test suite, but I haven't
yet figured out how to run it (I can't as the build fails on Windows)
wxWidgets: that other tadbit less huge GUI and core framework. Also
high quality code.
GSL: GNU Scientific library: comprehensive test suite.
FFTW: Known around the world, comprehensive test suite
Eigen: idem
Flac: idem
GMP, MPFR, MPC, PPL, CLooG: very fragile and comprehensive libraries.
Also all feature a nice test suite.
Perhaps all the open source graphics libraries (Tiff, png, jpeg, turbojpeg...)

What do you guys think? I do not know HTML, so the table editing would
have to be almost trivial for me to get it done :s. I can test
regularly and see if certain revisions fix the problem (on Windows).

Ruben
Jay Foad | 1 Aug 2011 14:04
Picon

transient link failures when building clang examples

When rebuilding llvm+clang with "make -j2 BUILD_EXAMPLES=1", I
frequently see link failures like this:

llvm[4]: Linking Release+Asserts executable clang-interpreter (without symbols)
/usr/bin/ld: /home/jay/llvm/objdir/Release+Asserts/lib/libclangCodeGen.a(CodeGenModule.o):
in function clang::CodeGen::CodeGenModule::EmitAliasDefinition(clang::GlobalDecl):CodeGenModule.cpp(.text+0x983b):
error: undefined reference to
'llvm::GlobalAlias::GlobalAlias(llvm::Type*,
llvm::GlobalValue::LinkageTypes, llvm::Twine const&, llvm::Constant*,
llvm::Module*)'
/usr/bin/ld: /home/jay/llvm/objdir/Release+Asserts/lib/libclangCodeGen.a(TargetInfo.o):
in function (anonymous
namespace)::MSP430TargetCodeGenInfo::SetTargetAttributes(clang::Decl
const*, llvm::GlobalValue*, clang::CodeGen::CodeGenModule&)
const:TargetInfo.cpp(.text+0x15a0): error: undefined reference to
'llvm::GlobalAlias::GlobalAlias(llvm::Type*,
llvm::GlobalValue::LinkageTypes, llvm::Twine const&, llvm::Constant*,
llvm::Module*)'
/usr/bin/ld: /home/jay/llvm/objdir/Release+Asserts/lib/libclangCodeGen.a(TargetInfo.o):
in function (anonymous
namespace)::MBlazeTargetCodeGenInfo::SetTargetAttributes(clang::Decl
const*, llvm::GlobalValue*, clang::CodeGen::CodeGenModule&)
const:TargetInfo.cpp(.text+0xaf42): error: undefined reference to
'llvm::GlobalAlias::GlobalAlias(llvm::Type*,
llvm::GlobalValue::LinkageTypes, llvm::Twine const&, llvm::Constant*,
llvm::Module*)'
/usr/bin/ld: /home/jay/llvm/objdir/Release+Asserts/lib/libclangCodeGen.a(CGCXX.o):
in function clang::CodeGen::CodeGenModule::TryEmitDefinitionAsAlias(clang::GlobalDecl,
clang::GlobalDecl):CGCXX.cpp(.text+0x9e5): error: undefined reference
to 'llvm::GlobalAlias::GlobalAlias(llvm::Type*,
llvm::GlobalValue::LinkageTypes, llvm::Twine const&, llvm::Constant*,
llvm::Module*)'
collect2: ld returned 1 exit status
make[4]: *** [/home/jay/llvm/objdir/Release+Asserts/bin/clang-interpreter]
Error 1

The failures tend to go away if I rerun the "make", so I've been
ignoring them for a while.

I'm using configure, not cmake.

Thanks,
Jay.
Christopher Jefferson | 1 Aug 2011 14:57

Re: on libc++ extensions and slist


On 31 Jul 2011, at 02:31, Howard Hinnant wrote:

> In existing C++03 standard libraries there are a ton of extensions.  Some good, some not so good.  Some of the
better ones have morphed into official  C++11 libraries.  However, I can't think of a single example where
an extension has been standardized unchanged from its extension form.  There is good reason for this.
> 
> I'm going to pick on slist.  But my argument is meant to be broader than slist.
> …
> 
I have converted some fairly substantial code bases at my work to run on clang, then libc++, then c++0x. I
also did quite a lot of the work involved in getting boost to run on clang/libc++/c++0x.

On any sizeable code base, each of these changes, particularly mapping to clang and then libc++, will take
some work. This work is mostly because other compilers have been far too lax in the past.

I want to see libc++ and clang++ keep their neatness, and not start introducing huge number of patches to get
around old standards-incompatable code.

This certainly seems to be the route that clang++ itself is sticking to, my experience is almost any piece of
sizeable c++ code will fail to compile when first given to clang++ (although the error messages are very
helpful in showing how to fix it).

However, a written migration strategy, covering issues which are likely to come up, would be useful. I'm
not sure what the best way to present such a document would be (in svn, on a wiki for easier editing?)

In short: Tell people how to fix their code, don't help them patch around it silently. They are going to have
pain switching to clang/libc++/0x whatever you do.

Chris
Douglas Gregor | 1 Aug 2011 16:24
Picon
Favicon

Re: Expanding the Clang Status page to report the status of several OSes and projects


On Aug 1, 2011, at 4:37 AM, Ruben Van Boxem wrote:

> Hi,
> 
> I just noticed that the table listing projects and Clang compatibility
> was recently removed. This idea still has a lot of merit, and has been
> breeding in my mind for several days.
> 
> I would like to provide test result data for several popular and high
> quality open source libraries that provide an extensive test suite so
> the compiled result is strictly analysed. I would do this on Windows
> (mingw-w64 CRT+ GCC 4.6 libstdc++ and linker), but I would like this
> to be more than a single email to the mailing list.
> 
> To this effect, I thought that perhaps expanding the first table that
> was on http://clang.llvm.org/cxx_status.html could be expanded
> significantly, in vertical (projects) and horizontal
> (platforms=OS+arch(+crt in the case of Windows)).
> 
> Although I believe that Clang is production ready on Mac OS, it is far
> from my elementary trust in the Windows MinGW world. Therefore, I
> think it is useful to keep track of wide-scale progress in a
> centralized place, because I feel the bugtracker doesn't get enough
> attention (at least the problems I am experiencing ;-)).

The main problem with the Windows MinGW world is that there are far too few LLVM/Clang developers who
actively work on MinGW. Mac OS, Linux, and FreeBSD (to name a few) have a number of LLVM/Clang developers
who made Clang work well on that platform and have kept it that way. We need more interest from the MinGW
world for that to happen there.

> Concretely, I suggest a larger table with colors like the C++0x table,
> with red = doesn't build, orange/yellow: builds, but tests fail due to
> a problem in clang (which also means that the tests pass for GCC), and
> green is that it builds and all tests pass without a hitch. Links
> could be placed to bug reports about the issue, where detailed
> information for interested developers could be placed.
> 
> The libraries I suggest that should be used as a "quality mark" are
> (more are of course welcome!):
> 
> Qt: Huge GUI and core library framework. High quality code that is
> extremely cross-platform. Has an internal test suite, but I haven't
> yet figured out how to run it (I can't as the build fails on Windows)
> wxWidgets: that other tadbit less huge GUI and core framework. Also
> high quality code.
> GSL: GNU Scientific library: comprehensive test suite.
> FFTW: Known around the world, comprehensive test suite
> Eigen: idem
> Flac: idem
> GMP, MPFR, MPC, PPL, CLooG: very fragile and comprehensive libraries.
> Also all feature a nice test suite.
> Perhaps all the open source graphics libraries (Tiff, png, jpeg, turbojpeg...)
> 
> What do you guys think? I do not know HTML, so the table editing would
> have to be almost trivial for me to get it done :s. I can test
> regularly and see if certain revisions fix the problem (on Windows).

The problem with putting these tables up on a web page is that they get out of date very, very quickly. So, for
them to be useful, they really need to be updated automatically. Then best way to do that, in my mind, would
be to set up a buildbot that tests these projects. Bring the buildbot online when one of the projects starts
working on that platform, and keep it running: the buildbot will tell us when things are broken, so we won't regress.

	- Doug

Gmane