@@ -2341,36 +2341,109 @@ StmtResult Sema::ActOnOmpSsTaskLoopForDirective(
2341
2341
return OSSTaskLoopForDirective::Create (Context, StartLoc, EndLoc, Clauses, AStmt, B);
2342
2342
}
2343
2343
2344
- static void checkOutlineDependency (Sema &S, Expr *RefExpr, bool OSSSyntax= false ) {
2344
+ static bool checkDependency (Sema &S, Expr *RefExpr, bool OSSSyntax, bool Outline ) {
2345
2345
SourceLocation ELoc = RefExpr->getExprLoc ();
2346
2346
Expr *SimpleExpr = RefExpr->IgnoreParenCasts ();
2347
- if (RefExpr->isTypeDependent () || RefExpr->isValueDependent () ||
2348
- RefExpr->containsUnexpandedParameterPack ()) {
2347
+ if (RefExpr->containsUnexpandedParameterPack ()) {
2348
+ S.Diag (RefExpr->getExprLoc (), diag::err_oss_variadic_templates_not_clause_allowed);
2349
+ return false ;
2350
+ } else if (RefExpr->isTypeDependent () || RefExpr->isValueDependent ()) {
2349
2351
// It will be analyzed later.
2350
- return ;
2352
+ return true ;
2351
2353
}
2354
+
2355
+ if (S.RequireCompleteExprType (RefExpr, diag::err_oss_incomplete_type))
2356
+ return false ;
2357
+
2352
2358
auto *ASE = dyn_cast<ArraySubscriptExpr>(SimpleExpr);
2353
- if (!RefExpr->IgnoreParenImpCasts ()->isLValue () ||
2359
+ // Allow only LValues, forbid ArraySubscripts over things
2360
+ // that are not an array like:
2361
+ // typedef float V __attribute__((vector_size(16)));
2362
+ // V a;
2363
+ // #pragma oss task in(a[3])
2364
+ // and functions:
2365
+ // void foo() { #pragma oss task in(foo) {} }
2366
+ if (RefExpr->IgnoreParenImpCasts ()->getType ()->isFunctionType () ||
2367
+ !RefExpr->IgnoreParenImpCasts ()->isLValue () ||
2354
2368
(ASE &&
2355
2369
!ASE->getBase ()->getType ().getNonReferenceType ()->isPointerType () &&
2356
2370
!ASE->getBase ()->getType ().getNonReferenceType ()->isArrayType ())) {
2357
- S.Diag (ELoc, diag::err_oss_expected_dereference_or_array_item)
2358
- << RefExpr->getSourceRange ();
2359
- return ;
2371
+ if (!Outline)
2372
+ S.Diag (ELoc, diag::err_oss_expected_addressable_lvalue_or_array_item)
2373
+ << RefExpr->getSourceRange ();
2374
+ else
2375
+ S.Diag (ELoc, diag::err_oss_expected_lvalue_reference_dereference_or_array_item)
2376
+ << RefExpr->getSourceRange ();
2377
+ return false ;
2360
2378
}
2361
- if (isa<DeclRefExpr>(SimpleExpr) || isa<MemberExpr>(SimpleExpr)) {
2362
- S.Diag (ELoc, diag::err_oss_expected_dereference_or_array_item)
2379
+
2380
+ if (Outline) {
2381
+ if (const DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(RefExpr->IgnoreParenImpCasts ())) {
2382
+ if (const VarDecl *VD = dyn_cast<VarDecl>(DRE->getDecl ())) {
2383
+ if (!VD->getType ()->isReferenceType ())
2384
+ S.Diag (ELoc, diag::err_oss_expected_lvalue_reference_dereference_or_array_item)
2385
+ << RefExpr->getSourceRange ();
2386
+ }
2387
+ }
2388
+ }
2389
+
2390
+ class CheckCallExpr
2391
+ : public ConstStmtVisitor<CheckCallExpr, bool > {
2392
+ // This Visitor checks the base of the
2393
+ // dependency is over a CallExpr, which is error.
2394
+ // int *get();
2395
+ // auto l = []() -> int * {...};
2396
+ // #pragma oss task in(get()[1], l()[3])
2397
+ public:
2398
+ bool VisitOSSMultiDepExpr (const OSSMultiDepExpr *E) {
2399
+ return Visit (E->getDepExpr ());
2400
+ }
2401
+
2402
+ bool VisitOSSArrayShapingExpr (const OSSArrayShapingExpr *E) {
2403
+ return Visit (E->getBase ());
2404
+ }
2405
+
2406
+ bool VisitOSSArraySectionExpr (const OSSArraySectionExpr *E) {
2407
+ return Visit (E->getBase ());
2408
+ }
2409
+
2410
+ bool VisitArraySubscriptExpr (const ArraySubscriptExpr *E) {
2411
+ return Visit (E->getBase ());
2412
+ }
2413
+
2414
+ bool VisitUnaryOperator (const UnaryOperator *E) {
2415
+ return Visit (E->getSubExpr ());
2416
+ }
2417
+
2418
+ bool VisitMemberExpr (const MemberExpr *E) {
2419
+ return Visit (E->getBase ());
2420
+ }
2421
+
2422
+ bool VisitCallExpr (const CallExpr *E) {
2423
+ return true ;
2424
+ }
2425
+ };
2426
+ CheckCallExpr CCE;
2427
+ if (CCE.Visit (RefExpr)) {
2428
+ S.Diag (ELoc, diag::err_oss_call_expr_support)
2363
2429
<< RefExpr->getSourceRange ();
2364
- return ;
2430
+ return false ;
2365
2431
}
2432
+
2433
+ bool InvalidArraySection = false ;
2366
2434
while (auto *OASE = dyn_cast<OSSArraySectionExpr>(SimpleExpr)) {
2367
2435
if (!OASE->isColonForm () && !OSSSyntax) {
2368
2436
S.Diag (OASE->getColonLoc (), diag::err_oss_section_invalid_form)
2369
2437
<< RefExpr->getSourceRange ();
2370
- return ;
2438
+ // Only diagnose the first error
2439
+ InvalidArraySection = true ;
2440
+ break ;
2371
2441
}
2372
- SimpleExpr = OASE->getBase ()->IgnoreParenCasts ();
2442
+ SimpleExpr = OASE->getBase ()->IgnoreParenImpCasts ();
2373
2443
}
2444
+ if (InvalidArraySection)
2445
+ return false ;
2446
+ return true ;
2374
2447
}
2375
2448
2376
2449
Sema::DeclGroupPtrTy Sema::ActOnOmpSsDeclareTaskDirective (
@@ -2460,64 +2533,64 @@ Sema::DeclGroupPtrTy Sema::ActOnOmpSsDeclareTaskDirective(
2460
2533
OnreadyRes = Onready;
2461
2534
}
2462
2535
for (Expr *RefExpr : Ins) {
2463
- checkOutlineDependency (*this , RefExpr, /* OSSSyntax=*/ true );
2536
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ true , /* Outline =*/ true );
2464
2537
}
2465
2538
for (Expr *RefExpr : Outs) {
2466
- checkOutlineDependency (*this , RefExpr, /* OSSSyntax=*/ true );
2539
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ true , /* Outline =*/ true );
2467
2540
}
2468
2541
for (Expr *RefExpr : Inouts) {
2469
- checkOutlineDependency (*this , RefExpr, /* OSSSyntax=*/ true );
2542
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ true , /* Outline =*/ true );
2470
2543
}
2471
2544
for (Expr *RefExpr : Concurrents) {
2472
- checkOutlineDependency (*this , RefExpr, /* OSSSyntax=*/ true );
2545
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ true , /* Outline =*/ true );
2473
2546
}
2474
2547
for (Expr *RefExpr : Commutatives) {
2475
- checkOutlineDependency (*this , RefExpr, /* OSSSyntax=*/ true );
2548
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ true , /* Outline =*/ true );
2476
2549
}
2477
2550
for (Expr *RefExpr : WeakIns) {
2478
- checkOutlineDependency (*this , RefExpr, /* OSSSyntax=*/ true );
2551
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ true , /* Outline =*/ true );
2479
2552
}
2480
2553
for (Expr *RefExpr : WeakOuts) {
2481
- checkOutlineDependency (*this , RefExpr, /* OSSSyntax=*/ true );
2554
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ true , /* Outline =*/ true );
2482
2555
}
2483
2556
for (Expr *RefExpr : WeakInouts) {
2484
- checkOutlineDependency (*this , RefExpr, /* OSSSyntax=*/ true );
2557
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ true , /* Outline =*/ true );
2485
2558
}
2486
2559
for (Expr *RefExpr : WeakConcurrents) {
2487
- checkOutlineDependency (*this , RefExpr, /* OSSSyntax=*/ true );
2560
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ true , /* Outline =*/ true );
2488
2561
}
2489
2562
for (Expr *RefExpr : WeakCommutatives) {
2490
- checkOutlineDependency (*this , RefExpr, /* OSSSyntax=*/ true );
2563
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ true , /* Outline =*/ true );
2491
2564
}
2492
2565
for (Expr *RefExpr : DepIns) {
2493
- checkOutlineDependency (*this , RefExpr);
2566
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ false , /* Outline= */ true );
2494
2567
}
2495
2568
for (Expr *RefExpr : DepOuts) {
2496
- checkOutlineDependency (*this , RefExpr);
2569
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ false , /* Outline= */ true );
2497
2570
}
2498
2571
for (Expr *RefExpr : DepInouts) {
2499
- checkOutlineDependency (*this , RefExpr);
2572
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ false , /* Outline= */ true );
2500
2573
}
2501
2574
for (Expr *RefExpr : DepConcurrents) {
2502
- checkOutlineDependency (*this , RefExpr);
2575
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ false , /* Outline= */ true );
2503
2576
}
2504
2577
for (Expr *RefExpr : DepCommutatives) {
2505
- checkOutlineDependency (*this , RefExpr);
2578
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ false , /* Outline= */ true );
2506
2579
}
2507
2580
for (Expr *RefExpr : DepWeakIns) {
2508
- checkOutlineDependency (*this , RefExpr);
2581
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ false , /* Outline= */ true );
2509
2582
}
2510
2583
for (Expr *RefExpr : DepWeakOuts) {
2511
- checkOutlineDependency (*this , RefExpr);
2584
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ false , /* Outline= */ true );
2512
2585
}
2513
2586
for (Expr *RefExpr : DepWeakInouts) {
2514
- checkOutlineDependency (*this , RefExpr);
2587
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ false , /* Outline= */ true );
2515
2588
}
2516
2589
for (Expr *RefExpr : DepWeakConcurrents) {
2517
- checkOutlineDependency (*this , RefExpr);
2590
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ false , /* Outline= */ true );
2518
2591
}
2519
2592
for (Expr *RefExpr : DepWeakCommutatives) {
2520
- checkOutlineDependency (*this , RefExpr);
2593
+ checkDependency (*this , RefExpr, /* OSSSyntax= */ false , /* Outline= */ true );
2521
2594
}
2522
2595
2523
2596
auto *NewAttr = OSSTaskDeclAttr::CreateImplicit (
@@ -3499,96 +3572,8 @@ Sema::ActOnOmpSsDependClause(ArrayRef<OmpSsDependClauseKind> DepKinds, SourceLoc
3499
3572
return nullptr ;
3500
3573
3501
3574
for (Expr *RefExpr : VarList) {
3502
- SourceLocation ELoc = RefExpr->getExprLoc ();
3503
- Expr *SimpleExpr = RefExpr->IgnoreParenCasts ();
3504
- if (RefExpr->containsUnexpandedParameterPack ()) {
3505
- Diag (RefExpr->getExprLoc (), diag::err_oss_variadic_templates_not_clause_allowed);
3506
- continue ;
3507
- } else if (RefExpr->isTypeDependent () || RefExpr->isValueDependent ()) {
3508
- // It will be analyzed later.
3509
- ClauseVars.push_back (RefExpr);
3510
- continue ;
3511
- }
3512
-
3513
- if (RequireCompleteExprType (RefExpr, diag::err_oss_incomplete_type))
3514
- continue ;
3515
-
3516
- // TODO: check with OSSArraySectionExpr
3517
- auto *ASE = dyn_cast<ArraySubscriptExpr>(SimpleExpr);
3518
- // Allow only LValues, forbid ArraySubscripts over things
3519
- // that are not an array like:
3520
- // typedef float V __attribute__((vector_size(16)));
3521
- // V a;
3522
- // #pragma oss task in(a[3])
3523
- // and functions:
3524
- // void foo() { #pragma oss task in(foo) {} }
3525
- if (RefExpr->IgnoreParenImpCasts ()->getType ()->isFunctionType () ||
3526
- !RefExpr->IgnoreParenImpCasts ()->isLValue () ||
3527
- (ASE &&
3528
- !ASE->getBase ()->getType ().getNonReferenceType ()->isPointerType () &&
3529
- !ASE->getBase ()->getType ().getNonReferenceType ()->isArrayType ())) {
3530
- Diag (ELoc, diag::err_oss_expected_addressable_lvalue_or_array_item)
3531
- << RefExpr->getSourceRange ();
3532
- continue ;
3533
- }
3534
-
3535
- class CheckCallExpr
3536
- : public ConstStmtVisitor<CheckCallExpr, bool > {
3537
- // This Visitor checks the base of the
3538
- // dependency is over a CallExpr, which is error.
3539
- // int *get();
3540
- // auto l = []() -> int * {...};
3541
- // #pragma oss task in(get()[1], l()[3])
3542
- public:
3543
- bool VisitOSSMultiDepExpr (const OSSMultiDepExpr *E) {
3544
- return Visit (E->getDepExpr ());
3545
- }
3546
-
3547
- bool VisitOSSArrayShapingExpr (const OSSArrayShapingExpr *E) {
3548
- return Visit (E->getBase ());
3549
- }
3550
-
3551
- bool VisitOSSArraySectionExpr (const OSSArraySectionExpr *E) {
3552
- return Visit (E->getBase ());
3553
- }
3554
-
3555
- bool VisitArraySubscriptExpr (const ArraySubscriptExpr *E) {
3556
- return Visit (E->getBase ());
3557
- }
3558
-
3559
- bool VisitUnaryOperator (const UnaryOperator *E) {
3560
- return Visit (E->getSubExpr ());
3561
- }
3562
-
3563
- bool VisitMemberExpr (const MemberExpr *E) {
3564
- return Visit (E->getBase ());
3565
- }
3566
-
3567
- bool VisitCallExpr (const CallExpr *E) {
3568
- return true ;
3569
- }
3570
- };
3571
- CheckCallExpr CCE;
3572
- if (CCE.Visit (RefExpr)) {
3573
- Diag (ELoc, diag::err_oss_call_expr_support)
3574
- << RefExpr->getSourceRange ();
3575
- continue ;
3576
- }
3577
-
3578
- bool InvalidArraySection = false ;
3579
- while (auto *OASE = dyn_cast<OSSArraySectionExpr>(SimpleExpr)) {
3580
- if (!OASE->isColonForm () && !OSSSyntax) {
3581
- Diag (OASE->getColonLoc (), diag::err_oss_section_invalid_form)
3582
- << RefExpr->getSourceRange ();
3583
- // Only diagnose the first error
3584
- InvalidArraySection = true ;
3585
- break ;
3586
- }
3587
- SimpleExpr = OASE->getBase ()->IgnoreParenImpCasts ();
3588
- }
3589
- if (InvalidArraySection)
3590
- continue ;
3591
- ClauseVars.push_back (RefExpr->IgnoreParenImpCasts ());
3575
+ if (checkDependency (*this , RefExpr, OSSSyntax, /* Outline=*/ false ))
3576
+ ClauseVars.push_back (RefExpr->IgnoreParenImpCasts ());
3592
3577
}
3593
3578
return OSSDependClause::Create (Context, StartLoc, LParenLoc, EndLoc,
3594
3579
DepKinds, DepKindsOrdered,
0 commit comments