Skip to content

Commit 55ac521

Browse files
authored
Merge pull request uxlfoundation#803 from hvdijk/llvm21-binop-fmaximum-fminimum
[LLVM 21] Add FMaximum, FMinimum.
2 parents ec51261 + cb3a206 commit 55ac521

2 files changed

Lines changed: 131 additions & 52 deletions

File tree

Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
// Copyright (C) Codeplay Software Limited
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License") with LLVM
4+
// Exceptions; you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// https://github.com/codeplaysoftware/oneapi-construction-kit/blob/main/LICENSE.txt
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
11+
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
12+
// License for the specific language governing permissions and limitations
13+
// under the License.
14+
//
15+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
16+
17+
#ifndef MULTI_LLVM_MULTI_INSTRUCTIONS_H_INCLUDED
18+
#define MULTI_LLVM_MULTI_INSTRUCTIONS_H_INCLUDED
19+
20+
#include <llvm/IR/Instructions.h>
21+
#include <multi_llvm/llvm_version.h>
22+
23+
namespace multi_llvm {
24+
25+
namespace detail {
26+
27+
template <typename Base = llvm::AtomicRMWInst, typename = void>
28+
struct AtomicRMWInst : Base {};
29+
30+
#if LLVM_VERSION_LESS(20, 0)
31+
template <typename Base>
32+
struct AtomicRMWInst<
33+
Base, std::enable_if_t<Base::LAST_BINOP - Base::FIRST_BINOP == 16>>
34+
: llvm::AtomicRMWInst {
35+
static constexpr BinOp USubCond = static_cast<BinOp>(BAD_BINOP + 1);
36+
static constexpr BinOp USubSat = static_cast<BinOp>(BAD_BINOP + 2);
37+
static constexpr BinOp FMaximum = static_cast<BinOp>(BAD_BINOP + 3);
38+
static constexpr BinOp FMinimum = static_cast<BinOp>(BAD_BINOP + 4);
39+
};
40+
#endif
41+
42+
// #if LLVM_VERSION_LESS(21, 0)
43+
// This is enabled for now on LLVM 21 as well to allow building against older
44+
// LLVM 21 snapshots.
45+
template <typename Base>
46+
struct AtomicRMWInst<
47+
Base, std::enable_if_t<Base::LAST_BINOP - Base::FIRST_BINOP == 18>>
48+
: llvm::AtomicRMWInst {
49+
static constexpr BinOp FMaximum = static_cast<BinOp>(BAD_BINOP + 1);
50+
static constexpr BinOp FMinimum = static_cast<BinOp>(BAD_BINOP + 2);
51+
};
52+
// #endif
53+
54+
} // namespace detail
55+
56+
struct AtomicRMWInst : detail::AtomicRMWInst<> {};
57+
58+
} // namespace multi_llvm
59+
60+
#endif // MULTI_LLVM_MULTI_INSTRUCTIONS_H_INCLUDED

modules/compiler/vecz/source/vectorization_context.cpp

Lines changed: 71 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828
#include <llvm/IR/Instructions.h>
2929
#include <llvm/Support/AtomicOrdering.h>
3030
#include <llvm/Target/TargetMachine.h>
31+
#include <multi_llvm/instructions.h>
3132
#include <multi_llvm/multi_llvm.h>
3233
#include <multi_llvm/vector_type_helper.h>
3334

@@ -415,53 +416,53 @@ VectorizationContext::isMaskedAtomicFunction(const Function &F) const {
415416
}
416417
AtomicInfo.IsVolatile = FnName.consume_front("volatile_");
417418

418-
if (IsCmpXchg) {
419-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::BAD_BINOP;
420-
} else {
421-
if (FnName.consume_front("xchg")) {
422-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::Xchg;
423-
} else if (FnName.consume_front("add")) {
424-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::Add;
425-
} else if (FnName.consume_front("sub")) {
426-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::Sub;
427-
} else if (FnName.consume_front("and")) {
428-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::And;
429-
} else if (FnName.consume_front("nand")) {
430-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::Nand;
431-
} else if (FnName.consume_front("or")) {
432-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::Or;
433-
} else if (FnName.consume_front("xor")) {
434-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::Xor;
435-
} else if (FnName.consume_front("max")) {
436-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::Max;
437-
} else if (FnName.consume_front("min")) {
438-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::Min;
439-
} else if (FnName.consume_front("umax")) {
440-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::UMax;
441-
} else if (FnName.consume_front("umin")) {
442-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::UMin;
443-
} else if (FnName.consume_front("fadd")) {
444-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::FAdd;
445-
} else if (FnName.consume_front("fsub")) {
446-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::FSub;
447-
} else if (FnName.consume_front("fmax")) {
448-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::FMax;
449-
} else if (FnName.consume_front("fmin")) {
450-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::FMin;
451-
} else if (FnName.consume_front("uincwrap")) {
452-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::UIncWrap;
453-
} else if (FnName.consume_front("udecwrap")) {
454-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::UDecWrap;
455-
#if LLVM_VERSION_GREATER_EQUAL(20, 0)
456-
} else if (FnName.consume_front("usubcond")) {
457-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::USubCond;
458-
} else if (FnName.consume_front("usubsat")) {
459-
AtomicInfo.BinOp = AtomicRMWInst::BinOp::USubSat;
460-
#endif
461-
} else {
462-
return std::nullopt;
419+
AtomicInfo.BinOp = AtomicRMWInst::BinOp::BAD_BINOP;
420+
421+
if (!IsCmpXchg) {
422+
if (FnName.consume_front("xchg_")) {
423+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::Xchg;
424+
} else if (FnName.consume_front("add_")) {
425+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::Add;
426+
} else if (FnName.consume_front("sub_")) {
427+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::Sub;
428+
} else if (FnName.consume_front("and_")) {
429+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::And;
430+
} else if (FnName.consume_front("nand_")) {
431+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::Nand;
432+
} else if (FnName.consume_front("or_")) {
433+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::Or;
434+
} else if (FnName.consume_front("xor_")) {
435+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::Xor;
436+
} else if (FnName.consume_front("max_")) {
437+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::Max;
438+
} else if (FnName.consume_front("min_")) {
439+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::Min;
440+
} else if (FnName.consume_front("umax_")) {
441+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::UMax;
442+
} else if (FnName.consume_front("umin_")) {
443+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::UMin;
444+
} else if (FnName.consume_front("fadd_")) {
445+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::FAdd;
446+
} else if (FnName.consume_front("fsub_")) {
447+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::FSub;
448+
} else if (FnName.consume_front("fmax_")) {
449+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::FMax;
450+
} else if (FnName.consume_front("fmin_")) {
451+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::FMin;
452+
} else if (FnName.consume_front("fmaximum_")) {
453+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::FMaximum;
454+
} else if (FnName.consume_front("fminimum_")) {
455+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::FMinimum;
456+
} else if (FnName.consume_front("uincwrap_")) {
457+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::UIncWrap;
458+
} else if (FnName.consume_front("udecwrap_")) {
459+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::UDecWrap;
460+
} else if (FnName.consume_front("usubcond_")) {
461+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::USubCond;
462+
} else if (FnName.consume_front("usubsat_")) {
463+
AtomicInfo.BinOp = multi_llvm::AtomicRMWInst::USubSat;
463464
}
464-
if (!FnName.consume_front("_")) {
465+
if (AtomicInfo.BinOp >= multi_llvm::AtomicRMWInst::BAD_BINOP) {
465466
return std::nullopt;
466467
}
467468
}
@@ -574,11 +575,21 @@ Function *VectorizationContext::getOrCreateMaskedAtomicFunction(
574575
}
575576

576577
if (!isCmpXchg) {
577-
#define BINOP_CASE(BINOP, STR) \
578-
case AtomicRMWInst::BINOP: \
579-
O << (STR); \
578+
#define BINOP_CASE(BINOP, STR) \
579+
case multi_llvm::AtomicRMWInst::BINOP: \
580+
O << (STR); \
580581
break
581582

583+
#ifdef __GNUC__
584+
#pragma GCC diagnostic push
585+
#pragma GCC diagnostic ignored "-Wswitch"
586+
#endif
587+
588+
#ifdef _MSC_VER
589+
#pragma warning(push)
590+
#pragma warning(disable : 4063)
591+
#endif
592+
582593
switch (I.BinOp) {
583594
BINOP_CASE(Xchg, "xchg");
584595
BINOP_CASE(Add, "add");
@@ -595,16 +606,24 @@ Function *VectorizationContext::getOrCreateMaskedAtomicFunction(
595606
BINOP_CASE(FSub, "fsub");
596607
BINOP_CASE(FMax, "fmax");
597608
BINOP_CASE(FMin, "fmin");
609+
BINOP_CASE(FMaximum, "fmaximum");
610+
BINOP_CASE(FMinimum, "fminumum");
598611
BINOP_CASE(UIncWrap, "uincwrap");
599612
BINOP_CASE(UDecWrap, "udecwrap");
600-
#if LLVM_VERSION_GREATER_EQUAL(20, 0)
601613
BINOP_CASE(USubCond, "usubcond");
602614
BINOP_CASE(USubSat, "usubsat");
603-
#endif
604-
case llvm::AtomicRMWInst::BAD_BINOP:
615+
case multi_llvm::AtomicRMWInst::BAD_BINOP:
605616
return nullptr;
606617
}
607618

619+
#ifdef __GNUC__
620+
#pragma GCC diagnostic pop
621+
#endif
622+
623+
#ifdef _MSC_VER
624+
#pragma warning(pop)
625+
#endif
626+
608627
#undef BINOP_CASE
609628
O << "_";
610629
}

0 commit comments

Comments
 (0)