brintos

brintos / llvm-project-archived public Read only

0
0
Text · 3.1 KiB · 43fb2e7 Raw
95 lines · cpp
1//===- llvm/Support/KnownFPClass.h - Stores known fplcass -------*- C++ -*-===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8//9// This file contains a class for representing known fpclasses used by10// computeKnownFPClass.11//12//===----------------------------------------------------------------------===//13 14#include "llvm/Support/KnownFPClass.h"15#include "llvm/Support/ErrorHandling.h"16 17using namespace llvm;18 19/// Return true if it's possible to assume IEEE treatment of input denormals in20/// \p F for \p Val.21static bool inputDenormalIsIEEE(DenormalMode Mode) {22  return Mode.Input == DenormalMode::IEEE;23}24 25static bool inputDenormalIsIEEEOrPosZero(DenormalMode Mode) {26  return Mode.Input == DenormalMode::IEEE ||27         Mode.Input == DenormalMode::PositiveZero;28}29 30bool KnownFPClass::isKnownNeverLogicalZero(DenormalMode Mode) const {31  return isKnownNeverZero() &&32         (isKnownNeverSubnormal() || inputDenormalIsIEEE(Mode));33}34 35bool KnownFPClass::isKnownNeverLogicalNegZero(DenormalMode Mode) const {36  return isKnownNeverNegZero() &&37         (isKnownNeverNegSubnormal() || inputDenormalIsIEEEOrPosZero(Mode));38}39 40bool KnownFPClass::isKnownNeverLogicalPosZero(DenormalMode Mode) const {41  if (!isKnownNeverPosZero())42    return false;43 44  // If we know there are no denormals, nothing can be flushed to zero.45  if (isKnownNeverSubnormal())46    return true;47 48  switch (Mode.Input) {49  case DenormalMode::IEEE:50    return true;51  case DenormalMode::PreserveSign:52    // Negative subnormal won't flush to +053    return isKnownNeverPosSubnormal();54  case DenormalMode::PositiveZero:55  default:56    // Both positive and negative subnormal could flush to +057    return false;58  }59 60  llvm_unreachable("covered switch over denormal mode");61}62 63void KnownFPClass::propagateDenormal(const KnownFPClass &Src,64                                     DenormalMode Mode) {65  KnownFPClasses = Src.KnownFPClasses;66  // If we aren't assuming the source can't be a zero, we don't have to check if67  // a denormal input could be flushed.68  if (!Src.isKnownNeverPosZero() && !Src.isKnownNeverNegZero())69    return;70 71  // If we know the input can't be a denormal, it can't be flushed to 0.72  if (Src.isKnownNeverSubnormal())73    return;74 75  if (!Src.isKnownNeverPosSubnormal() && Mode != DenormalMode::getIEEE())76    KnownFPClasses |= fcPosZero;77 78  if (!Src.isKnownNeverNegSubnormal() && Mode != DenormalMode::getIEEE()) {79    if (Mode != DenormalMode::getPositiveZero())80      KnownFPClasses |= fcNegZero;81 82    if (Mode.Input == DenormalMode::PositiveZero ||83        Mode.Output == DenormalMode::PositiveZero ||84        Mode.Input == DenormalMode::Dynamic ||85        Mode.Output == DenormalMode::Dynamic)86      KnownFPClasses |= fcPosZero;87  }88}89 90void KnownFPClass::propagateCanonicalizingSrc(const KnownFPClass &Src,91                                              DenormalMode Mode) {92  propagateDenormal(Src, Mode);93  propagateNaN(Src, /*PreserveSign=*/true);94}95