1 //
2 // FPEnvironment_DEC.cpp
3 //
4 // Library: Foundation
5 // Package: Core
6 // Module:  FPEnvironment
7 //
8 // Copyright (c) 2004-2006, Applied Informatics Software Engineering GmbH.
9 // and Contributors.
10 //
11 // SPDX-License-Identifier:	BSL-1.0
12 //
13 
14 
15 //
16 // _XOPEN_SOURCE disables the ieee fp functions
17 // in <math.h>, therefore we undefine it for this file.
18 //
19 #undef _XOPEN_SOURCE
20 
21 
22 #include <math.h>
23 #include <fp.h>
24 #include <fp_class.h>
25 #if defined(__VMS)
26 #include <starlet.h>
27 #endif
28 #include "Poco/FPEnvironment_DEC.h"
29 
30 
31 namespace Poco {
32 
33 
FPEnvironmentImpl()34 FPEnvironmentImpl::FPEnvironmentImpl()
35 {
36 #if defined(__VMS)
37 	#pragma pointer_size save
38 	#pragma pointer_size 32
39 	struct _ieee env;
40 	sys$ieee_set_fp_control(0, 0, &env);
41 	#pragma pointer_size restore
42 	_env = env;
43 #else
44 	_env = ieee_get_fp_control();
45 #endif
46 }
47 
48 
FPEnvironmentImpl(const FPEnvironmentImpl & env)49 FPEnvironmentImpl::FPEnvironmentImpl(const FPEnvironmentImpl& env)
50 {
51 	_env = env._env;
52 }
53 
54 
~FPEnvironmentImpl()55 FPEnvironmentImpl::~FPEnvironmentImpl()
56 {
57 #if defined(__VMS)
58 	#pragma pointer_size save
59 	#pragma pointer_size 32
60 	struct _ieee mask;
61 	mask.ieee$q_flags = 0xFFFFFFFFFFFFFFFF;
62 	struct _ieee env = _env;
63 	sys$ieee_set_fp_control(&mask, &env, 0);
64 	#pragma pointer_size restore
65 #else
66 	ieee_set_fp_control(_env);
67 #endif
68 }
69 
70 
operator =(const FPEnvironmentImpl & env)71 FPEnvironmentImpl& FPEnvironmentImpl::operator = (const FPEnvironmentImpl& env)
72 {
73 	_env = env._env;
74 	return *this;
75 }
76 
77 
isInfiniteImpl(float value)78 bool FPEnvironmentImpl::isInfiniteImpl(float value)
79 {
80 	int cls = fp_classf(value);
81 	return cls == FP_POS_INF || cls == FP_NEG_INF;
82 }
83 
84 
isInfiniteImpl(double value)85 bool FPEnvironmentImpl::isInfiniteImpl(double value)
86 {
87 	int cls = fp_class(value);
88 	return cls == FP_POS_INF || cls == FP_NEG_INF;
89 }
90 
91 
isInfiniteImpl(long double value)92 bool FPEnvironmentImpl::isInfiniteImpl(long double value)
93 {
94 	int cls = fp_classl(value);
95 	return cls == FP_POS_INF || cls == FP_NEG_INF;
96 }
97 
98 
isNaNImpl(float value)99 bool FPEnvironmentImpl::isNaNImpl(float value)
100 {
101 	return isnanf(value) != 0;
102 }
103 
104 
isNaNImpl(double value)105 bool FPEnvironmentImpl::isNaNImpl(double value)
106 {
107 	return isnan(value) != 0;
108 }
109 
110 
isNaNImpl(long double value)111 bool FPEnvironmentImpl::isNaNImpl(long double value)
112 {
113 	return isnanl(value) != 0;
114 }
115 
116 
copySignImpl(float target,float source)117 float FPEnvironmentImpl::copySignImpl(float target, float source)
118 {
119 	return copysignf(target, source);
120 }
121 
122 
copySignImpl(double target,double source)123 double FPEnvironmentImpl::copySignImpl(double target, double source)
124 {
125 	return copysign(target, source);
126 }
127 
128 
copySignImpl(long double target,long double source)129 long double FPEnvironmentImpl::copySignImpl(long double target, long double source)
130 {
131 	return copysignl(target, source);
132 }
133 
134 
keepCurrentImpl()135 void FPEnvironmentImpl::keepCurrentImpl()
136 {
137 #if defined(__VMS)
138 	#pragma pointer_size save
139 	#pragma pointer_size 32
140 	struct _ieee env;
141 	sys$ieee_set_fp_control(0, 0, &env);
142 	#pragma pointer_size restore
143 	_env = env;
144 #else
145 	ieee_set_fp_control(_env);
146 #endif
147 }
148 
149 
clearFlagsImpl()150 void FPEnvironmentImpl::clearFlagsImpl()
151 {
152 #if defined(__VMS)
153 	#pragma pointer_size save
154 	#pragma pointer_size 32
155 	struct _ieee mask;
156 	mask.ieee$q_flags = 0xFFFFFFFFFFFFFFFF;
157 	struct _ieee clr;
158 	clr.ieee$q_flags  = 0;
159 	sys$ieee_set_fp_control(&mask, &clr, 0);
160 	#pragma pointer_size restore
161 #else
162 	ieee_set_fp_control(0);
163 #endif
164 }
165 
166 
isFlagImpl(FlagImpl flag)167 bool FPEnvironmentImpl::isFlagImpl(FlagImpl flag)
168 {
169 #if defined(__VMS)
170 	#pragma pointer_size save
171 	#pragma pointer_size 32
172 	struct _ieee flags;
173 	sys$ieee_set_fp_control(0, 0, &flags);
174 	return (flags.ieee$q_flags & flag) != 0;
175 	#pragma pointer_size restore
176 #else
177 	return (ieee_get_fp_control() & flag) != 0;
178 #endif
179 }
180 
181 
setRoundingModeImpl(RoundingModeImpl mode)182 void FPEnvironmentImpl::setRoundingModeImpl(RoundingModeImpl mode)
183 {
184 	// not supported
185 }
186 
187 
getRoundingModeImpl()188 FPEnvironmentImpl::RoundingModeImpl FPEnvironmentImpl::getRoundingModeImpl()
189 {
190 	// not supported
191 	return FPEnvironmentImpl::RoundingModeImpl(0);
192 }
193 
194 
195 } // namespace Poco
196