source: src/Validate/CheckAssertions.cpp@ 464cfc7

Last change on this file since 464cfc7 was 16ba4897, checked in by Andrew Beach <ajbeach@…>, 12 months ago

Replaced SemanticErrorException::isEmpty with ...::throwIfNonEmpty. This is how it was used in every context and it saves a bit of text (if not two lines) at every use. I considered putting this function in the header for better inlining, but this should have at least the same preformance as the last version.

  • Property mode set to 100644
File size: 2.5 KB
Line 
1//
2// Cforall Version 1.0.0 Copyright (C) 2018 University of Waterloo
3//
4// The contents of this file are covered under the licence agreement in the
5// file "LICENCE" distributed with Cforall.
6//
7// CheckAssertions.cpp --
8//
9// Author : Andrew Beach
10// Created On : Thu Sep 5 14:43:00 2024
11// Last Modified By : Andrew Beach
12// Last Modified On : Thu Sep 5 14:43:00 2024
13// Update Count : 0
14//
15
16#include "CheckAssertions.hpp"
17
18#include "AST/Decl.hpp"
19#include "AST/Pass.hpp"
20#include "AST/Type.hpp"
21#include "Common/SemanticError.hpp"
22#include "GenPoly/GenPoly.hpp"
23
24namespace Validate {
25
26namespace {
27
28/// Check for dynamic (sized polymorphic) variadic assertions.
29struct VariadicAssertionCore final {
30 void checkAssertion( GenPoly::TypeVarMap const & typeVars,
31 ast::FunctionDecl const * assert ) {
32 if ( ast::FixedArgs != assert->type->isVarArgs
33 && needsAdapter( assert->type, typeVars ) ) {
34 SemanticError( assert,
35 "Cannot assert a function that both has by-value polymorphic "
36 "parameters or return values, and also takes variadic (...) "
37 "parameters. Consider using a va_list parameter instead.\n" );
38 }
39 }
40
41 template<typename T>
42 void checkList(
43 GenPoly::TypeVarMap const & typeVars,
44 SemanticErrorException & errors,
45 std::vector<ast::ptr<T>> const & members ) {
46 for ( const ast::ptr<T> & member : members ) {
47 try {
48 if ( auto func = member.template as<ast::FunctionDecl>() ) {
49 checkAssertion( typeVars, func );
50 }
51 } catch ( SemanticErrorException & error ) {
52 errors.append( error );
53 }
54 }
55 }
56
57 void postvisit( ast::FunctionDecl const * decl ) {
58 GenPoly::TypeVarMap typeVars;
59 SemanticErrorException errors;
60 makeTypeVarMap( decl, typeVars );
61 checkList( typeVars, errors, decl->assertions );
62 errors.throwIfNonEmpty();
63 }
64
65 void checkAggr( bool checkMembers,
66 ast::AggregateDecl const * decl ) {
67 SemanticErrorException errors;
68 GenPoly::TypeVarMap typeVars;
69 for ( auto & param : decl->params ) {
70 addToTypeVarMap( param, typeVars );
71 checkList( typeVars, errors, param->assertions );
72 }
73 if ( checkMembers ) checkList( typeVars, errors, decl->members );
74 errors.throwIfNonEmpty();
75 }
76
77 void postvisit( ast::StructDecl const * decl ) {
78 checkAggr( false, decl );
79 }
80
81 void postvisit( ast::UnionDecl const * decl ) {
82 checkAggr( false, decl );
83 }
84
85 void postvisit( ast::TraitDecl const * decl ) {
86 checkAggr( true, decl );
87 }
88};
89
90} // namespace
91
92void checkAssertions( ast::TranslationUnit & transUnit ) {
93 ast::Pass<VariadicAssertionCore>::run( transUnit );
94}
95
96} // namespace Validate
Note: See TracBrowser for help on using the repository browser.