diff options
-rw-r--r-- | include/clang/Parse/Action.h | 6 | ||||
-rw-r--r-- | lib/Parse/ParseDecl.cpp | 8 | ||||
-rw-r--r-- | lib/Sema/Sema.h | 3 | ||||
-rw-r--r-- | lib/Sema/SemaTemplateInstantiateDecl.cpp | 3 | ||||
-rw-r--r-- | test/SemaTemplate/instantiate-invalid.cpp | 52 |
5 files changed, 66 insertions, 6 deletions
diff --git a/include/clang/Parse/Action.h b/include/clang/Parse/Action.h index 469816caa5..f211b5ca3a 100644 --- a/include/clang/Parse/Action.h +++ b/include/clang/Parse/Action.h @@ -503,6 +503,12 @@ public: return; } + /// \brief Note that the given declaration had an initializer that could not + /// be parsed. + virtual void ActOnInitializerError(DeclPtrTy Dcl) { + return; + } + /// FinalizeDeclaratorGroup - After a sequence of declarators are parsed, this /// gives the actions implementation a chance to process the group as a whole. virtual DeclGroupPtrTy FinalizeDeclaratorGroup(Scope *S, const DeclSpec& DS, diff --git a/lib/Parse/ParseDecl.cpp b/lib/Parse/ParseDecl.cpp index 4405dcb974..8a32f35b64 100644 --- a/lib/Parse/ParseDecl.cpp +++ b/lib/Parse/ParseDecl.cpp @@ -564,10 +564,10 @@ Parser::DeclPtrTy Parser::ParseDeclarationAfterDeclarator(Declarator &D, } if (Init.isInvalid()) { - SkipUntil(tok::semi, true, true); - return DeclPtrTy(); - } - Actions.AddInitializerToDecl(ThisDecl, move(Init)); + SkipUntil(tok::comma, true, true); + Actions.ActOnInitializerError(ThisDecl); + } else + Actions.AddInitializerToDecl(ThisDecl, move(Init)); } } else if (Tok.is(tok::l_paren)) { // Parse C++ direct initializer: '(' expression-list ')' diff --git a/lib/Sema/Sema.h b/lib/Sema/Sema.h index 0fe9b7fa21..da192dd887 100644 --- a/lib/Sema/Sema.h +++ b/lib/Sema/Sema.h @@ -3413,7 +3413,8 @@ public: Decl *getInstantiationOf(const Decl *D) { Decl *Result = LocalDecls[D]; - assert(Result && "declaration was not instantiated in this scope!"); + assert((Result || D->isInvalidDecl()) && + "declaration was not instantiated in this scope!"); return Result; } diff --git a/lib/Sema/SemaTemplateInstantiateDecl.cpp b/lib/Sema/SemaTemplateInstantiateDecl.cpp index 3d9899e112..0f7bae835f 100644 --- a/lib/Sema/SemaTemplateInstantiateDecl.cpp +++ b/lib/Sema/SemaTemplateInstantiateDecl.cpp @@ -2323,7 +2323,8 @@ NamedDecl *Sema::FindInstantiatedDecl(SourceLocation Loc, NamedDecl *D, } // UsingShadowDecls can instantiate to nothing because of using hiding. - assert((Result || isa<UsingShadowDecl>(D)) + assert((Result || isa<UsingShadowDecl>(D) || D->isInvalidDecl() || + cast<Decl>(ParentDC)->isInvalidDecl()) && "Unable to find instantiation of declaration!"); D = Result; diff --git a/test/SemaTemplate/instantiate-invalid.cpp b/test/SemaTemplate/instantiate-invalid.cpp new file mode 100644 index 0000000000..b8a59015c0 --- /dev/null +++ b/test/SemaTemplate/instantiate-invalid.cpp @@ -0,0 +1,52 @@ +// RUN: not %clang_cc1 -fsyntax-only %s +namespace PR6375 { + template<class Conv> class rasterizer_sl_clip Conv::xi(x2), Conv::yi(y2)); +namespace agg +{ + template<class Clip=rasterizer_sl_clip_int> class rasterizer_scanline_aa + { + template<class Scanline> bool sweep_scanline(Scanline& sl) + { + unsigned num_cells = m_outline.scanline_num_cells(m_scan_y); + while(num_cells) { } + } + } + class scanline_u8 {} + template<class PixelFormat> class renderer_base { } +} + template<class Rasterizer, class Scanline, class BaseRenderer, class ColorT> + void render_scanlines_aa_solid(Rasterizer& ras, Scanline& sl, BaseRenderer& ren, const ColorT& color) + { + while(ras.sweep_scanline(sl)) + { + } + }; +namespace agg +{ + struct rgba8 + { + }; + template<class Rasterizer, class Scanline, class Renderer, class Ctrl> + void render_ctrl(Rasterizer& ras, Scanline& sl, Renderer& r, Ctrl& c) + { + unsigned i; + render_scanlines_aa_solid(ras, sl, r, c.color(i)); + } + template<class ColorT> class rbox_ctrl : public rbox_ctrl_impl + { + const ColorT& color(unsigned i) const { return *m_colors[i]; } + } +class the_application : public agg::platform_support +{ + agg::rbox_ctrl<agg::rgba8> m_polygons; + virtual void on_init() + { + typedef agg::renderer_base<pixfmt_type> base_ren_type; + base_ren_type ren_base(pf); + agg::scanline_u8 sl; + agg::rasterizer_scanline_aa<> ras; + agg::render_ctrl(ras, sl, ren_base, m_polygons); + } +}; +} +} |