Commit c31ea295 authored by dbarbera's avatar dbarbera
Browse files

Added sin/cos/sqrt/round operators

parent 5dbb40e0
......@@ -804,6 +804,14 @@ def _prim_call(prim):
raise NotImplementedError
elif ident == 'ceil':
raise NotImplementedError
elif ident == 'cos':
raise NotImplementedError
elif ident == 'round':
raise NotImplementedError
elif ident == 'sin':
raise NotImplementedError
elif ident == 'sqrt':
raise NotImplementedError
elif ident == 'trunc':
raise NotImplementedError
else:
......
......@@ -70,6 +70,9 @@ class Context():
ty = core.Type.function(self.void, [self.i8_ptr], True)
self.funcs['printf'] = self.module.add_function(ty, 'printf')
ty = core.Type.function(self.double, [self.double])
self.funcs['round'] = self.module.add_function(ty, 'round')
self.funcs['memcpy'] = core.Function.intrinsic(
self.module,
core.INTR_MEMCPY,
......@@ -88,21 +91,39 @@ class Context():
[self.double]
)
self.funcs['cos'] = core.Function.intrinsic(
self.module,
core.INTR_COS,
[self.double]
)
self.funcs['fabs'] = core.Function.intrinsic(
self.module,
core.INTR_FABS,
[self.double]
)
self.funcs['floor'] = core.Function.intrinsic(
self.module,
core.INTR_FLOOR,
[self.double]
)
self.funcs['trunc'] = core.Function.intrinsic(
self.funcs['sin'] = core.Function.intrinsic(
self.module,
core.INTR_TRUNC,
core.INTR_SIN,
[self.double]
)
self.funcs['fabs'] = core.Function.intrinsic(
self.funcs['sqrt'] = core.Function.intrinsic(
self.module,
core.INTR_FABS,
core.INTR_SQRT,
[self.double]
)
self.funcs['trunc'] = core.Function.intrinsic(
self.module,
core.INTR_TRUNC,
[self.double]
)
......@@ -1293,6 +1314,8 @@ def _prim_call(prim, ctx):
return sdl_abs(arg_vals[0], ctx)
elif name == 'ceil':
return sdl_ceil(arg_vals[0], ctx)
elif name == 'cos':
return sdl_cos(arg_vals[0], ctx)
elif name == 'fix':
return sdl_fix(arg_vals[0], ctx)
elif name == 'float':
......@@ -1307,6 +1330,12 @@ def _prim_call(prim, ctx):
return sdl_power(arg_vals[0], arg_vals[1], ctx)
elif name == 'present':
return sdl_present(arg_vals[0], ctx)
elif name == 'round':
return sdl_round(arg_vals[0], ctx)
elif name == 'sin':
return sdl_sin(arg_vals[0], ctx)
elif name == 'sqrt':
return sdl_sqrt(arg_vals[0], ctx)
elif name == 'trunc':
return sdl_trunc(arg_vals[0], ctx)
......@@ -1849,6 +1878,21 @@ def sdl_ceil(x_val, ctx):
return sdl_call('ceil', [x_val], ctx)
def sdl_cos(x_val, ctx):
''' Generate the IR for a cos operation '''
return sdl_call('cos', [x_val], ctx)
def sdl_sin(x_val, ctx):
''' Generate the IR for a sin operation '''
return sdl_call('sin', [x_val], ctx)
def sdl_sqrt(x_val, ctx):
''' Generate the IR for a sqrt operation '''
return sdl_call('sqrt', [x_val], ctx)
def sdl_trunc(x_val, ctx):
''' Generate the IR for a cos operation '''
return sdl_call('trunc', [x_val], ctx)
......@@ -1875,6 +1919,11 @@ def sdl_power(x_val, y_val, ctx):
return sdl_call('powi', [x_val, y_val], ctx)
def sdl_round(x_val, ctx):
''' Generate the IR for a float operation '''
return sdl_call('round', [x_val], ctx)
def sdl_num(enum_val, ctx):
''' Generate the IR for a num operation'''
return ctx.builder.sext(enum_val, ctx.i64)
......
......@@ -104,17 +104,25 @@ UNKNOWN_TYPE = type('UnknownType', (object,), {'kind': 'UnknownType'})
SPECIAL_OPERATORS = {
'abs': [{'type': NUMERICAL, 'direction': 'in'}],
'ceil': [{'type': REAL, 'direction': 'in'}],
'cos': [{'type': REAL, 'direction': 'in'}],
'fix': [{'type': NUMERICAL, 'direction': 'in'}],
'float': [{'type': NUMERICAL, 'direction': 'in'}],
'floor': [{'type': REAL, 'direction': 'in'}],
'length': [{'type': LIST, 'direction': 'in'}],
'num': [{'type': ENUMERATED, 'direction': 'in'}],
'power': [{'type': NUMERICAL, 'direction': 'in'},
{'type': INTEGER, 'direction': 'in'}],
'power': [
{'type': NUMERICAL, 'direction': 'in'},
{'type': INTEGER, 'direction': 'in'}
],
'present': [{'type': CHOICE, 'direction': 'in'}],
'reset_timer': [{'type': TIMER, 'direction': 'in'}],
'set_timer': [{'type': INTEGER, 'direction': 'in'},
{'type': TIMER, 'direction': 'in'}],
'round': [{'type': REAL, 'direction': 'in'}],
'set_timer': [
{'type': INTEGER, 'direction': 'in'},
{'type': TIMER, 'direction': 'in'}
],
'sin': [{'type': REAL, 'direction': 'in'}],
'sqrt': [{'type': REAL, 'direction': 'in'}],
'trunc': [{'type': REAL, 'direction': 'in'}],
'write': [{'type': ANY_TYPE, 'direction': 'in'}],
'writeln': [{'type': ANY_TYPE, 'direction': 'in'}],
......@@ -492,6 +500,12 @@ def check_call(name, params, context):
'Max': str(math.ceil(float(param_btys[0].Max)))
})
elif name == 'cos':
return type('Cos', (REAL,), {
'Min': str(-1.0),
'Max': str(1.0)
})
elif name == 'fix':
return type('Fix', (INTEGER,), {
'Min': param_btys[0].Min,
......@@ -539,6 +553,24 @@ def check_call(name, params, context):
'EnumValues': param_btys[0].Children
})
elif name == 'round':
return type('Round', (REAL,), {
'Min': str(round(float(param_btys[0].Min))),
'Max': str(round(float(param_btys[0].Max)))
})
elif name == 'sin':
return type('Sin', (REAL,), {
'Min': str(-1.0),
'Max': str(1.0)
})
elif name == 'sqrt':
return type('Sqrt', (REAL,), {
'Min': str(0.0),
'Max': str(math.sqrt(float(param_btys[0].Max)))
})
elif name == 'trunc':
return type('Trunc', (REAL,), {
'Min': str(math.trunc(float(param_btys[0].Min))),
......@@ -1392,7 +1424,7 @@ def primary_call(root, context):
try:
node.exprType = check_call(name, params, context)
except TypeError as err:
except (TypeError, ValueError) as err:
errors.append(error(root, str(err)))
except OverflowError:
errors.append(error(root, 'Result can exceeds 64-bits'))
......
......@@ -23,7 +23,7 @@ test-llvm:
clang -c operators.s
clang -c dataview-uniq.c
clang -c test_llvm.c
clang operators.o dataview-uniq.o test_llvm.o -o testcase
clang operators.o dataview-uniq.o test_llvm.o -o testcase -lm
./testcase | diff expected -
clean:
......
/* CIF PROCESS (140, 161), (150, 75) */
/* CIF PROCESS (142, 159), (146, 75) */
PROCESS operators;
/* CIF TEXT (286, 21), (303, 152) */
DCL i Integer := 2;
......@@ -24,27 +24,33 @@ DCL c Choice := i:2;
CALL assert(abs(-f) = f, 'abs(-f) = f');
/* CIF PROCEDURECALL (-22, 324), (293, 35) */
CALL assert(ceil(f + 0.5) = 3.0, 'ceil(f + 0.5) = 3.0');
/* CIF PROCEDURECALL (12, 374), (224, 35) */
/* CIF PROCEDURECALL (-90, 374), (429, 35) */
CALL assert(round(cos(3.141632)) = -1.0, 'round(cos(3.141632)) = -1.0');
/* CIF PROCEDURECALL (12, 424), (224, 35) */
CALL assert(fix(f) = i, 'fix(f) = i');
/* CIF PROCEDURECALL (-1, 424), (251, 35) */
/* CIF PROCEDURECALL (-1, 474), (251, 35) */
CALL assert(float(i) = f, 'float(i) = f');
/* CIF PROCEDURECALL (-18, 474), (284, 35) */
/* CIF PROCEDURECALL (-18, 524), (284, 35) */
CALL assert(floor(f + 0.5) = f, 'floor(f + 0.5) = f');
/* CIF PROCEDURECALL (-47, 524), (343, 35) */
/* CIF PROCEDURECALL (-47, 574), (343, 35) */
CALL assert(length(fixSeqOf) = 3, 'length(fixSeqOf) = 3');
/* CIF PROCEDURECALL (-51, 574), (350, 35) */
/* CIF PROCEDURECALL (-51, 624), (350, 35) */
CALL assert(length(varSeqOf) = 3, 'length(varSeqOf) = 3');
/* CIF PROCEDURECALL (3, 624), (240, 35) */
/* CIF PROCEDURECALL (3, 674), (240, 35) */
CALL assert(num(e) = 12, 'num(e) = 12');
/* CIF PROCEDURECALL (-14, 674), (276, 35) */
/* CIF PROCEDURECALL (-14, 724), (276, 35) */
CALL assert(power(i, 3) = 8, 'power(i, 3) = 8');
/* CIF PROCEDURECALL (-26, 724), (301, 35) */
/* CIF PROCEDURECALL (-90, 774), (429, 35) */
CALL assert(round(sin(3.141632)) = 0.0, 'round(sin(3.141632)) = 0.0');
/* CIF PROCEDURECALL (-15, 824), (278, 35) */
CALL assert(sqrt(16.0) = 4.0, 'sqrt(16.0) = 4.0');
/* CIF PROCEDURECALL (-26, 874), (301, 35) */
CALL assert(trunc(f + 0.1) = f, 'trunc(f + 0.1) = f');
/* CIF PROCEDURECALL (24, 774), (200, 35) */
/* CIF PROCEDURECALL (24, 924), (200, 35) */
CALL writeln(i, f, b, s);
/* CIF PROCEDURECALL (24, 824), (200, 35) */
/* CIF PROCEDURECALL (24, 974), (200, 35) */
CALL write(i, f, b, s);
/* CIF NEXTSTATE (74, 874), (100, 50) */
/* CIF NEXTSTATE (74, 1024), (100, 50) */
NEXTSTATE Wait;
ENDSTATE;
ENDPROCESS operators;
\ No newline at end of file
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment