Merge branch 'master' of https://scm.cri.ensmp.fr/git/Faustine
[Faustine.git] / interpretor / preprocessor / faust-0.9.47mr3 / compiler / extended / rintprim.cpp
1 #include "xtended.hh"
2 #include "compatibility.hh"
3 #include "Text.hh"
4 #include <math.h>
5
6 #include "floats.hh"
7
8 #if defined(WIN32) && ! defined(__MINGW32__)
9 /* missing on Windows : see http://bugs.mysql.com/bug.php?id=15936 */
10 inline double rint(double nr)
11 {
12 double f = floor(nr);
13 double c = ceil(nr);
14 return (((c -nr) >= (nr - f)) ? f : c);
15 }
16 #endif
17
18 class RintPrim : public xtended
19 {
20
21 public:
22
23 RintPrim() : xtended("rint") {}
24
25 virtual unsigned int arity () { return 1; }
26
27 virtual bool needCache () { return true; }
28
29 virtual Type infereSigType (const vector<Type>& args)
30 {
31 assert (args.size() == arity());
32 interval i = args[0]->getInterval();
33 if (i.valid) {
34 return castInterval(floatCast(args[0]), interval(rint(i.lo), rint(i.hi)));
35 } else {
36 return floatCast(args[0]);
37 }
38 }
39
40 virtual void sigVisit (Tree sig, sigvisitor* visitor) {}
41
42 virtual int infereSigOrder (const vector<int>& args) {
43 assert (args.size() == arity());
44 return args[0];
45 }
46
47
48 virtual Tree computeSigOutput (const vector<Tree>& args) {
49 num n;
50 assert (args.size() == arity());
51 if (isNum(args[0],n)) {
52 return tree(rint(double(n)));
53 } else {
54 return tree(symbol(), args[0]);
55 }
56 }
57
58 virtual string generateCode (Klass* klass, const vector<string>& args, const vector<Type>& types)
59 {
60 assert (args.size() == arity());
61 assert (types.size() == arity());
62
63 return subst("rint$1($0)", args[0], isuffix());
64 }
65
66 virtual string generateLateq (Lateq* lateq, const vector<string>& args, const vector<Type>& types)
67 {
68 assert (args.size() == arity());
69 assert (types.size() == arity());
70
71 return subst("\\left[ {$0} \\right]", args[0]);
72 }
73
74 };
75
76
77 xtended* gRintPrim = new RintPrim();
78
79