Changeset 98d1b90 for src/Concurrency


Ignore:
Timestamp:
Mar 21, 2022, 12:17:27 PM (4 years ago)
Author:
Thierry Delisle <tdelisle@…>
Branches:
ADT, ast-experimental, enum, master, pthread-emulation, qualifiedEnum
Children:
4ecc35a
Parents:
adb3ea1 (diff), 41d3c8d (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
Message:

Merge branch 'master' of plg.uwaterloo.ca:software/cfa/cfa-cc

Location:
src/Concurrency
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • src/Concurrency/Keywords.cc

    radb3ea1 r98d1b90  
    12041204                                        //new TypeofType( noQualifiers, args.front()->clone() )
    12051205                                        new TypeofType( noQualifiers, new UntypedExpr(
    1206                                                         new NameExpr( "__get_type" ),
     1206                                                        new NameExpr( "__get_mutexstmt_lock_type" ),
    12071207                                                        { args.front()->clone() }
    12081208                                                )
     
    12161216                                map_range < std::list<Initializer*> > ( args, [](Expression * var ){
    12171217                                        return new SingleInit( new UntypedExpr(
    1218                                                         new NameExpr( "__get_ptr" ),
     1218                                                        new NameExpr( "__get_mutexstmt_lock_ptr" ),
    12191219                                                        { var }
    12201220                                        ) );
     
    12271227                TypeExpr * lock_type_expr = new TypeExpr(
    12281228                        new TypeofType( noQualifiers, new UntypedExpr(
    1229                                 new NameExpr( "__get_type" ),
     1229                                new NameExpr( "__get_mutexstmt_lock_type" ),
    12301230                                { args.front()->clone() }
    12311231                                )
  • src/Concurrency/KeywordsNew.cpp

    radb3ea1 r98d1b90  
    1414//
    1515
     16#include <iostream>
     17
    1618#include "Concurrency/Keywords.h"
    1719
     
    2628#include "Common/Examine.h"
    2729#include "Common/utility.h"
     30#include "Common/UniqueName.h"
    2831#include "ControlStruct/LabelGeneratorNew.hpp"
    2932#include "InitTweak/InitTweak.h"
     
    167170        const ast::StructDecl * typeid_decl = nullptr;
    168171        const ast::StructDecl * vtable_decl = nullptr;
     172
    169173};
    170174
     
    874878
    875879// --------------------------------------------------------------------------
    876 struct MutexKeyword final {
     880struct MutexKeyword final : public ast::WithDeclsToAdd<> {
    877881        const ast::FunctionDecl * postvisit( const ast::FunctionDecl * decl );
    878882        void postvisit( const ast::StructDecl * decl );
     
    887891        ast::CompoundStmt * addStatements( const ast::CompoundStmt * body, const std::vector<ast::ptr<ast::Expr>> & args );
    888892        ast::CompoundStmt * addThreadDtorStatements( const ast::FunctionDecl* func, const ast::CompoundStmt * body, const std::vector<const ast::DeclWithType *> & args );
    889 
     893        ast::ExprStmt * genVirtLockUnlockExpr( const std::string & fnName, ast::ptr<ast::Expr> expr, const CodeLocation & location, ast::Expr * param);
     894        ast::IfStmt * genTypeDiscrimLockUnlock( const std::string & fnName, const std::vector<ast::ptr<ast::Expr>> & args, const CodeLocation & location, ast::UntypedExpr * thisParam );
    890895private:
    891896        const ast::StructDecl * monitor_decl = nullptr;
     
    896901
    897902        static ast::ptr<ast::Type> generic_func;
     903
     904        UniqueName mutex_func_namer = UniqueName("__lock_unlock_curr");
    898905};
    899906
     
    9971004
    9981005const ast::Stmt * MutexKeyword::postvisit( const ast::MutexStmt * stmt ) {
     1006        if ( !lock_guard_decl ) {
     1007                SemanticError( stmt->location, "mutex stmt requires a header, add #include <mutex_stmt.hfa>\n" );
     1008        }
    9991009        ast::CompoundStmt * body =
    10001010                        new ast::CompoundStmt( stmt->location, { stmt->stmt } );
    1001         addStatements( body, stmt->mutexObjs );
    1002         return body;
     1011       
     1012        return addStatements( body, stmt->mutexObjs );;
    10031013}
    10041014
     
    11951205}
    11961206
     1207// generates a cast to the void ptr to the appropriate lock type and dereferences it before calling lock or unlock on it
     1208// used to undo the type erasure done by storing all the lock pointers as void
     1209ast::ExprStmt * MutexKeyword::genVirtLockUnlockExpr( const std::string & fnName, ast::ptr<ast::Expr> expr, const CodeLocation & location, ast::Expr * param ) {
     1210        return new ast::ExprStmt( location,
     1211                new ast::UntypedExpr( location,
     1212                        new ast::NameExpr( location, fnName ), {
     1213                                ast::UntypedExpr::createDeref(
     1214                                        location,
     1215                                        new ast::CastExpr( location,
     1216                                                param,
     1217                                                new ast::PointerType( new ast::TypeofType( new ast::UntypedExpr(
     1218                                                        expr->location,
     1219                                                        new ast::NameExpr( expr->location, "__get_mutexstmt_lock_type" ),
     1220                                                        { expr }
     1221                                                ) ) ),
     1222                                                ast::GeneratedFlag::ExplicitCast
     1223                                        )
     1224                                )
     1225                        }
     1226                )
     1227        );
     1228}
     1229
     1230ast::IfStmt * MutexKeyword::genTypeDiscrimLockUnlock( const std::string & fnName, const std::vector<ast::ptr<ast::Expr>> & args, const CodeLocation & location, ast::UntypedExpr * thisParam ) {
     1231        ast::IfStmt * outerLockIf = nullptr;
     1232        ast::IfStmt * lastLockIf = nullptr;
     1233
     1234        //adds an if/elif clause for each lock to assign type from void ptr based on ptr address
     1235        for ( long unsigned int i = 0; i < args.size(); i++ ) {
     1236               
     1237                ast::UntypedExpr * ifCond = new ast::UntypedExpr( location,
     1238                        new ast::NameExpr( location, "?==?" ), {
     1239                                ast::deepCopy( thisParam ),
     1240                                new ast::CastExpr( location, new ast::AddressExpr( location, args.at(i) ), new ast::PointerType( new ast::VoidType() ))
     1241                        }
     1242                );
     1243
     1244                ast::IfStmt * currLockIf = new ast::IfStmt(
     1245                        location,
     1246                        ifCond,
     1247                        genVirtLockUnlockExpr( fnName, args.at(i), location, ast::deepCopy( thisParam ) )
     1248                );
     1249               
     1250                if ( i == 0 ) {
     1251                        outerLockIf = currLockIf;
     1252                } else {
     1253                        // add ifstmt to else of previous stmt
     1254                        lastLockIf->else_ = currLockIf;
     1255                }
     1256
     1257                lastLockIf = currLockIf;
     1258        }
     1259        return outerLockIf;
     1260}
     1261
    11971262ast::CompoundStmt * MutexKeyword::addStatements(
    11981263                const ast::CompoundStmt * body,
    11991264                const std::vector<ast::ptr<ast::Expr>> & args ) {
    1200         ast::CompoundStmt * mutBody = ast::mutate( body );
    12011265
    12021266        // Code is generated near the beginning of the compound statement.
    1203         const CodeLocation & location = mutBody->location;
     1267        const CodeLocation & location = body->location;
     1268
     1269                // final body to return
     1270        ast::CompoundStmt * newBody = new ast::CompoundStmt( location );
     1271
     1272        // std::string lockFnName = mutex_func_namer.newName();
     1273        // std::string unlockFnName = mutex_func_namer.newName();
    12041274
    12051275        // Make pointer to the monitors.
     
    12091279                new ast::ArrayType(
    12101280                        new ast::PointerType(
    1211                                 new ast::TypeofType(
    1212                                         new ast::UntypedExpr(
    1213                                                 location,
    1214                                                 new ast::NameExpr( location, "__get_type" ),
    1215                                                 { args.front() }
    1216                                         )
    1217                                 )
     1281                                new ast::VoidType()
    12181282                        ),
    12191283                        ast::ConstantExpr::from_ulong( location, args.size() ),
     
    12291293                                                new ast::UntypedExpr(
    12301294                                                        expr->location,
    1231                                                         new ast::NameExpr( expr->location, "__get_ptr" ),
     1295                                                        new ast::NameExpr( expr->location, "__get_mutexstmt_lock_ptr" ),
    12321296                                                        { expr }
    12331297                                                )
     
    12421306        ast::StructInstType * lock_guard_struct =
    12431307                        new ast::StructInstType( lock_guard_decl );
    1244         ast::TypeExpr * lock_type_expr = new ast::TypeExpr(
    1245                 location,
    1246                 new ast::TypeofType(
    1247                         new ast::UntypedExpr(
    1248                                 location,
    1249                                 new ast::NameExpr( location, "__get_type" ),
    1250                                 { args.front() }
    1251                         )
    1252                 )
    1253         );
    1254 
    1255         lock_guard_struct->params.push_back( lock_type_expr );
    1256 
    1257         // In reverse order:
     1308
     1309        // use try stmts to lock and finally to unlock
     1310        ast::TryStmt * outerTry = nullptr;
     1311        ast::TryStmt * currentTry;
     1312        ast::CompoundStmt * lastBody = nullptr;
     1313
     1314        // adds a nested try stmt for each lock we are locking
     1315        for ( long unsigned int i = 0; i < args.size(); i++ ) {
     1316                ast::UntypedExpr * innerAccess = new ast::UntypedExpr(
     1317                        location,
     1318                        new ast::NameExpr( location,"?[?]" ), {
     1319                                new ast::NameExpr( location, "__monitors" ),
     1320                                ast::ConstantExpr::from_int( location, i )
     1321                        }
     1322                );
     1323
     1324                // make the try body
     1325                ast::CompoundStmt * currTryBody = new ast::CompoundStmt( location );
     1326                ast::IfStmt * lockCall = genTypeDiscrimLockUnlock( "lock", args, location, innerAccess );
     1327                currTryBody->push_back( lockCall );
     1328
     1329                // make the finally stmt
     1330                ast::CompoundStmt * currFinallyBody = new ast::CompoundStmt( location );
     1331                ast::IfStmt * unlockCall = genTypeDiscrimLockUnlock( "unlock", args, location, innerAccess );
     1332                currFinallyBody->push_back( unlockCall );
     1333
     1334                // construct the current try
     1335                currentTry = new ast::TryStmt(
     1336                        location,
     1337                        currTryBody,
     1338                        {},
     1339                        new ast::FinallyStmt( location, currFinallyBody )
     1340                );
     1341                if ( i == 0 ) outerTry = currentTry;
     1342                else {
     1343                        // pushback try into the body of the outer try
     1344                        lastBody->push_back( currentTry );
     1345                }
     1346                lastBody = currTryBody;
     1347        }
     1348
     1349        // push body into innermost try body
     1350        if ( lastBody != nullptr ) {
     1351                lastBody->push_back( body );
     1352                newBody->push_front( outerTry );
     1353        }       
     1354
    12581355        // monitor_guard_t __guard = { __monitors, # };
    1259         mutBody->push_front(
     1356        newBody->push_front(
    12601357                new ast::DeclStmt(
    12611358                        location,
     
    12841381
    12851382        // monitor$ * __monitors[] = { get_monitor(a), get_monitor(b) };
    1286         mutBody->push_front( new ast::DeclStmt( location, monitors ) );
    1287 
    1288         return mutBody;
     1383        newBody->push_front( new ast::DeclStmt( location, monitors ) );
     1384
     1385        // // The parameter for both __lock_curr/__unlock_curr routines.
     1386        // ast::ObjectDecl * this_decl = new ast::ObjectDecl(
     1387        //      location,
     1388        //      "this",
     1389        //      new ast::PointerType( new ast::VoidType() ),
     1390        //      nullptr,
     1391        //      {},
     1392        //      ast::Linkage::Cforall
     1393        // );
     1394
     1395        // ast::FunctionDecl * lock_decl = new ast::FunctionDecl(
     1396        //      location,
     1397        //      lockFnName,
     1398        //      { /* forall */ },
     1399        //      {
     1400        //              // Copy the declaration of this.
     1401        //              this_decl,
     1402        //      },
     1403        //      { /* returns */ },
     1404        //      nullptr,
     1405        //      0,
     1406        //      ast::Linkage::Cforall,
     1407        //      { /* attributes */ },
     1408        //      ast::Function::Inline
     1409        // );
     1410
     1411        // ast::FunctionDecl * unlock_decl = new ast::FunctionDecl(
     1412        //      location,
     1413        //      unlockFnName,
     1414        //      { /* forall */ },
     1415        //      {
     1416        //              // Copy the declaration of this.
     1417        //              ast::deepCopy( this_decl ),
     1418        //      },
     1419        //      { /* returns */ },
     1420        //      nullptr,
     1421        //      0,
     1422        //      ast::Linkage::Cforall,
     1423        //      { /* attributes */ },
     1424        //      ast::Function::Inline
     1425        // );
     1426
     1427        // ast::IfStmt * outerLockIf = nullptr;
     1428        // ast::IfStmt * outerUnlockIf = nullptr;
     1429        // ast::IfStmt * lastLockIf = nullptr;
     1430        // ast::IfStmt * lastUnlockIf = nullptr;
     1431
     1432        // //adds an if/elif clause for each lock to assign type from void ptr based on ptr address
     1433        // for ( long unsigned int i = 0; i < args.size(); i++ ) {
     1434        //      ast::VariableExpr * thisParam = new ast::VariableExpr( location, InitTweak::getParamThis( lock_decl ) );
     1435        //      ast::UntypedExpr * ifCond = new ast::UntypedExpr( location,
     1436        //              new ast::NameExpr( location, "?==?" ), {
     1437        //                      thisParam,
     1438        //                      new ast::CastExpr( location, new ast::AddressExpr( location, args.at(i) ), new ast::PointerType( new ast::VoidType() ))
     1439        //              }
     1440        //      );
     1441
     1442        //      ast::IfStmt * currLockIf = new ast::IfStmt(
     1443        //              location,
     1444        //              ast::deepCopy( ifCond ),
     1445        //              genVirtLockUnlockExpr( "lock", args.at(i), location, ast::deepCopy( thisParam ) )
     1446        //      );
     1447
     1448        //      ast::IfStmt * currUnlockIf = new ast::IfStmt(
     1449        //              location,
     1450        //              ifCond,
     1451        //              genVirtLockUnlockExpr( "unlock", args.at(i), location, ast::deepCopy( thisParam ) )
     1452        //      );
     1453               
     1454        //      if ( i == 0 ) {
     1455        //              outerLockIf = currLockIf;
     1456        //              outerUnlockIf = currUnlockIf;
     1457        //      } else {
     1458        //              // add ifstmt to else of previous stmt
     1459        //              lastLockIf->else_ = currLockIf;
     1460        //              lastUnlockIf->else_ = currUnlockIf;
     1461        //      }
     1462
     1463        //      lastLockIf = currLockIf;
     1464        //      lastUnlockIf = currUnlockIf;
     1465        // }
     1466       
     1467        // // add pointer typing if/elifs to body of routines
     1468        // lock_decl->stmts = new ast::CompoundStmt( location, { outerLockIf } );
     1469        // unlock_decl->stmts = new ast::CompoundStmt( location, { outerUnlockIf } );
     1470
     1471        // // add routines to scope
     1472        // declsToAddBefore.push_back( lock_decl );
     1473        // declsToAddBefore.push_back( unlock_decl );
     1474
     1475        // newBody->push_front(new ast::DeclStmt( location, lock_decl ));
     1476        // newBody->push_front(new ast::DeclStmt( location, unlock_decl ));
     1477
     1478        return newBody;
    12891479}
    12901480
Note: See TracChangeset for help on using the changeset viewer.