1/* longdouble.h -- Definitions of floating-point access for the frontend.
2   Copyright (C) 2015-2020 Free Software Foundation, Inc.
3
4GCC is free software; you can redistribute it and/or modify
5it under the terms of the GNU General Public License as published by
6the Free Software Foundation; either version 3, or (at your option)
7any later version.
8
9GCC is distributed in the hope that it will be useful,
10but WITHOUT ANY WARRANTY; without even the implied warranty of
11MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12GNU General Public License for more details.
13
14You should have received a copy of the GNU General Public License
15along with GCC; see the file COPYING3.  If not see
16<http://www.gnu.org/licenses/>.  */
17
18#ifndef GCC_D_LONGDOUBLE_H
19#define GCC_D_LONGDOUBLE_H
20
21struct real_value;
22class Type;
23
24struct longdouble
25{
26public:
27  /* Return the hidden real_value from the longdouble type.  */
28  const real_value& rv (void) const
29  { return *(const real_value *) this; }
30
31  real_value& rv (void)
32  { return *(real_value *) this; }
33
34  /* Normalize the value to be the precision supported by target.  */
35  longdouble normalize (void);
36
37  /* No constructor to be able to use this class in a union.  */
38  template<typename T> longdouble& operator = (T x)
39  { set (x); return *this; }
40
41  /* Lvalue operators.  */
42  void set (real_value& d);
43  void set (int32_t d);
44  void set (int64_t d);
45  void set (uint32_t d);
46  void set (uint64_t d);
47  void set (bool d);
48
49  /* Rvalue operators.  */
50  bool to_bool () const;
51  int64_t to_int () const;
52  uint64_t to_uint () const;
53
54  operator int32_t (void)
55  { return (int32_t) this->to_int (); }
56
57  operator int64_t (void)
58  { return this->to_int (); }
59
60  operator uint32_t (void)
61  { return (uint32_t) this->to_uint (); }
62
63  operator uint64_t (void)
64  { return this->to_uint (); }
65
66  operator bool (void)
67  { return this->to_bool (); }
68
69  /* Arithmetic operators.  */
70  longdouble add (const longdouble& r) const;
71  longdouble sub (const longdouble& r) const;
72  longdouble mul (const longdouble& r) const;
73  longdouble div (const longdouble& r) const;
74  longdouble mod (const longdouble& r) const;
75  longdouble neg () const;
76
77  longdouble operator + (const longdouble& r)
78  { return this->add (r); }
79
80  longdouble operator - (const longdouble& r)
81  { return this->sub (r); }
82
83  longdouble operator * (const longdouble& r)
84  { return this->mul (r); }
85
86  longdouble operator / (const longdouble& r)
87  { return this->div (r); }
88
89  longdouble operator % (const longdouble& r)
90  { return this->mod (r); }
91
92  longdouble operator -()
93  { return this->neg (); }
94
95  /* Comparison operators.  */
96  int cmp (const longdouble& t) const;
97  int equals (const longdouble& t) const;
98
99  bool operator < (const longdouble& r)
100  { return this->cmp (r) < 0; }
101
102  bool operator <= (const longdouble& r)
103  { return this->cmp (r) <= 0; }
104
105  bool operator > (const longdouble& r)
106  { return this->cmp (r) > 0; }
107
108  bool operator >= (const longdouble& r)
109  { return this->cmp (r) >= 0; }
110
111  bool operator == (const longdouble& r)
112  { return this->equals (r); }
113
114  bool operator != (const longdouble& r)
115  { return !this->equals (r); }
116
117private:
118  /* Including gcc/real.h presents too many problems, so just
119     statically allocate enough space for REAL_VALUE_TYPE.  */
120  long realvalue[(2 + (16 + sizeof (long)) / sizeof (long))];
121};
122
123/* Declared, but "volatile" is not required.  */
124typedef longdouble volatile_longdouble;
125
126/* Use ldouble() to explicitly create a longdouble value.  */
127template<typename T>
128inline longdouble
129ldouble (T x)
130{
131  longdouble d;
132  d.set (x);
133  return d;
134}
135
136#endif  /* GCC_D_LONGDOUBLE_H  */
137