source: src/ControlStruct/FixLabels.cpp@ cb921d4

ADT ast-experimental enum forall-pointer-decay pthread-emulation qualifiedEnum
Last change on this file since cb921d4 was cb921d4, checked in by Andrew Beach <ajbeach@…>, 4 years ago

Changed some of the new ast code so they no longer pass around the empty LabelGenerator.

  • Property mode set to 100644
File size: 3.2 KB
RevLine 
[b8ab91a]1//
2// Cforall Version 1.0.0 Copyright (C) 2015 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// FixLabels.cpp -- Normalizes labels and handles multi-level exit labels.
8//
9// Author : Andrew Beach
10// Created On : Mon Nov 1 09:39:00 2021
11// Last Modified By : Andrew Beach
[cb921d4]12// Last Modified On : Mon Nov 8 10:53:00 2021
13// Update Count : 3
[b8ab91a]14//
15
16#include "FixLabels.hpp"
17
18#include "AST/Label.hpp"
19#include "AST/Pass.hpp"
20#include "AST/Stmt.hpp"
21#include "ControlStruct/LabelGenerator.h"
22#include "ControlStruct/MultiLevelExit.hpp"
23
24namespace ControlStruct {
25
26namespace {
27
28class FixLabelsCore final : public ast::WithGuards {
[21fe17f]29 LabelToStmt labelTable;
[b8ab91a]30public:
[cb921d4]31 FixLabelsCore( LabelGenerator * gen = nullptr ) : labelTable() {}
[b8ab91a]32
33 void previsit( const ast::FunctionDecl * );
34 const ast::FunctionDecl * postvisit( const ast::FunctionDecl * );
35 void previsit( const ast::Stmt * );
36 void previsit( const ast::BranchStmt * );
37 void previsit( const ast::LabelAddressExpr * );
38
[21fe17f]39 void setLabelsDef( const std::vector<ast::Label> &, const ast::Stmt * );
40 void setLabelsUsage( const ast::Label & );
[b8ab91a]41};
42
43void FixLabelsCore::previsit( const ast::FunctionDecl * ) {
44 GuardValue( labelTable ).clear();
45}
46
47const ast::FunctionDecl * FixLabelsCore::postvisit(
48 const ast::FunctionDecl * decl ) {
49 if ( nullptr == decl->stmts ) return decl;
[21fe17f]50 for ( auto kvp : labelTable ) {
51 if ( nullptr == kvp.second ) {
52 SemanticError( kvp.first.location,
53 "Use of undefined label: " + kvp.first.name );
54 }
55 }
[b8ab91a]56 return ast::mutate_field( decl, &ast::FunctionDecl::stmts,
[cb921d4]57 multiLevelExitUpdate( decl->stmts.get(), labelTable ) );
[b8ab91a]58}
59
60void FixLabelsCore::previsit( const ast::Stmt * stmt ) {
[21fe17f]61 if ( !stmt->labels.empty() ) {
62 setLabelsDef( stmt->labels, stmt );
[b8ab91a]63 }
64}
65
66void FixLabelsCore::previsit( const ast::BranchStmt * stmt ) {
67 if ( !stmt->labels.empty() ) {
[21fe17f]68 setLabelsDef( stmt->labels, stmt );
[b8ab91a]69 }
70 if ( !stmt->target.empty() ) {
[21fe17f]71 setLabelsUsage( stmt->target );
[b8ab91a]72 }
73}
74
75void FixLabelsCore::previsit( const ast::LabelAddressExpr * expr ) {
76 assert( !expr->arg.empty() );
[21fe17f]77 setLabelsUsage( expr->arg );
[b8ab91a]78}
79
[21fe17f]80void FixLabelsCore::setLabelsDef(
[b8ab91a]81 const std::vector<ast::Label> & labels, const ast::Stmt * stmt ) {
82 assert( !labels.empty() );
83 assert( stmt );
84
85 for ( auto label : labels ) {
86 if ( labelTable.find( label ) == labelTable.end() ) {
87 // Make sure to only create the entry once.
[21fe17f]88 labelTable[ label ] = stmt;
89 } else if ( nullptr != labelTable[ label ] ) {
[b8ab91a]90 // Duplicate definition, this is an error.
91 SemanticError( label.location,
92 "Duplicate definition of label: " + label.name );
93 } else {
94 // Perviously used, but not defined until now.
[21fe17f]95 labelTable[ label ] = stmt;
[b8ab91a]96 }
97 }
98}
99
100// Label was used, if it is new add it to the table.
[21fe17f]101void FixLabelsCore::setLabelsUsage( const ast::Label & label ) {
[b8ab91a]102 if ( labelTable.find( label ) == labelTable.end() ) {
[21fe17f]103 labelTable[ label ] = nullptr;
[b8ab91a]104 }
105}
106
107} // namespace
108
109void fixLabels( ast::TranslationUnit & translationUnit ) {
110 ast::Pass<FixLabelsCore>::run( translationUnit );
111}
112
113} // namespace ControlStruct
114
115// Local Variables: //
116// tab-width: 4 //
117// mode: c++ //
118// compile-command: "make install" //
119// End: //
Note: See TracBrowser for help on using the repository browser.