Skip to content

Commit

Permalink
Builtin abs() (#458)
Browse files Browse the repository at this point in the history
  • Loading branch information
vtereshkov committed Dec 7, 2024
1 parent c16dc53 commit 938eea7
Show file tree
Hide file tree
Showing 9 changed files with 36 additions and 7 deletions.
2 changes: 1 addition & 1 deletion Umka.sublime-syntax
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ file_extensions:
- um
scope: source.umka
variables:
builtin: (append|atan|atan2|cap|ceil|copy|cos|delete|exit|exp|fabs|floor|fprintf|fscanf|insert|keys|len|log|make|memusage|new|printf|resume|round|scanf|selfhasptr|selftypeeq|sin|sizeof|sizeofself|slice|sort|sprintf|sqrt|sscanf|trunc|typeptr|valid|validkey)
builtin: (abs|append|atan|atan2|cap|ceil|copy|cos|delete|exit|exp|fabs|floor|fprintf|fscanf|insert|keys|len|log|make|memusage|new|printf|resume|round|scanf|selfhasptr|selftypeeq|sin|sizeof|sizeofself|slice|sort|sprintf|sqrt|sscanf|trunc|typeptr|valid|validkey)
ident: '[A-Za-z_][A-Za-z_0-9]*'
typeident: '_*[A-Z][A-Za-z_0-9]*'
space: '\s*'
Expand Down
1 change: 1 addition & 0 deletions doc/lang.md
Original file line number Diff line number Diff line change
Expand Up @@ -683,6 +683,7 @@ fn round(x: real): int // Rounding to the nearest integer
fn trunc(x: real): int // Rounding towards zero
fn ceil (x: real): int // Rounding upwards
fn floor(x: real): int // Rounding downwards
fn abs (x: int): int // Absolute value
fn fabs (x: real): real // Absolute value
fn sqrt (x: real): real // Square root
fn sin (x: real): real // Sine
Expand Down
2 changes: 1 addition & 1 deletion playground/umka.js

Large diffs are not rendered by default.

1 change: 1 addition & 0 deletions src/umka_compiler.c
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,7 @@ static void compilerDeclareBuiltinIdents(Compiler *comp)
identAddBuiltinFunc(&comp->idents, &comp->modules, &comp->blocks, "trunc", comp->intType, BUILTIN_TRUNC);
identAddBuiltinFunc(&comp->idents, &comp->modules, &comp->blocks, "ceil", comp->intType, BUILTIN_CEIL);
identAddBuiltinFunc(&comp->idents, &comp->modules, &comp->blocks, "floor", comp->intType, BUILTIN_FLOOR);
identAddBuiltinFunc(&comp->idents, &comp->modules, &comp->blocks, "abs", comp->intType, BUILTIN_ABS);
identAddBuiltinFunc(&comp->idents, &comp->modules, &comp->blocks, "fabs", comp->realType, BUILTIN_FABS);
identAddBuiltinFunc(&comp->idents, &comp->modules, &comp->blocks, "sqrt", comp->realType, BUILTIN_SQRT);
identAddBuiltinFunc(&comp->idents, &comp->modules, &comp->blocks, "sin", comp->realType, BUILTIN_SIN);
Expand Down
8 changes: 8 additions & 0 deletions src/umka_const.c
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
#include <string.h>
#include <limits.h>
#include <math.h>
#include <inttypes.h>

#include "umka_const.h"

Expand Down Expand Up @@ -230,6 +231,13 @@ void constCallBuiltin(Consts *consts, Const *arg, const Const *arg2, TypeKind ar
case BUILTIN_TRUNC: arg->intVal = (int64_t)trunc(arg->realVal); break;
case BUILTIN_CEIL: arg->intVal = (int64_t)ceil (arg->realVal); break;
case BUILTIN_FLOOR: arg->intVal = (int64_t)floor(arg->realVal); break;
case BUILTIN_ABS:
{
if (arg->intVal == LLONG_MIN)
consts->error->handler(consts->error->context, "abs() domain error");
arg->intVal = llabs(arg->intVal);
break;
}
case BUILTIN_FABS: arg->realVal = fabs(arg->realVal); break;
case BUILTIN_SQRT:
{
Expand Down
13 changes: 8 additions & 5 deletions src/umka_expr.c
Original file line number Diff line number Diff line change
Expand Up @@ -833,9 +833,11 @@ static void parseBuiltinIOCall(Compiler *comp, Type **type, Const *constant, Bui

static void parseBuiltinMathCall(Compiler *comp, Type **type, Const *constant, BuiltinFunc builtin)
{
*type = comp->realType;
Type *argType = (builtin == BUILTIN_ABS) ? comp->intType : comp->realType;

*type = argType;
parseExpr(comp, type, constant);
doAssertImplicitTypeConv(comp, comp->realType, type, constant);
doAssertImplicitTypeConv(comp, argType, type, constant);

Const constant2Val = {.realVal = 0};
Const *constant2 = NULL;
Expand All @@ -854,11 +856,11 @@ static void parseBuiltinMathCall(Compiler *comp, Type **type, Const *constant, B
}

if (constant)
constCallBuiltin(&comp->consts, constant, constant2, TYPE_REAL, builtin);
constCallBuiltin(&comp->consts, constant, constant2, argType->kind, builtin);
else
genCallBuiltin(&comp->gen, TYPE_REAL, builtin);
genCallBuiltin(&comp->gen, argType->kind, builtin);

if (builtin == BUILTIN_ROUND || builtin == BUILTIN_TRUNC || builtin == BUILTIN_CEIL || builtin == BUILTIN_FLOOR)
if (builtin == BUILTIN_ROUND || builtin == BUILTIN_TRUNC || builtin == BUILTIN_CEIL || builtin == BUILTIN_FLOOR || builtin == BUILTIN_ABS)
*type = comp->intType;
else
*type = comp->realType;
Expand Down Expand Up @@ -1515,6 +1517,7 @@ static void parseBuiltinCall(Compiler *comp, Type **type, Const *constant, Built
case BUILTIN_TRUNC:
case BUILTIN_CEIL:
case BUILTIN_FLOOR:
case BUILTIN_ABS:
case BUILTIN_FABS:
case BUILTIN_SQRT:
case BUILTIN_SIN:
Expand Down
6 changes: 6 additions & 0 deletions src/umka_gen.c
Original file line number Diff line number Diff line change
Expand Up @@ -388,6 +388,12 @@ static bool optimizeCallBuiltin(CodeGen *gen, TypeKind typeKind, BuiltinFunc bui
}
break;
}
case BUILTIN_ABS:
{
arg.intVal = prev->operand.intVal;
resultTypeKind = TYPE_INT;
break;
}
case BUILTIN_ROUND:
case BUILTIN_TRUNC:
case BUILTIN_CEIL:
Expand Down
9 changes: 9 additions & 0 deletions src/umka_vm.c
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
#include <math.h>
#include <limits.h>
#include <ctype.h>
#include <inttypes.h>

#include "umka_vm.h"

Expand Down Expand Up @@ -112,6 +113,7 @@ static const char *builtinSpelling [] =
"trunc",
"ceil",
"floor",
"abs",
"fabs",
"sqrt",
"sin",
Expand Down Expand Up @@ -3550,6 +3552,13 @@ static FORCE_INLINE void doCallBuiltin(Fiber *fiber, Fiber **newFiber, HeapPages
case BUILTIN_TRUNC: fiber->top->intVal = (int64_t)trunc(fiber->top->realVal); break;
case BUILTIN_CEIL: fiber->top->intVal = (int64_t)ceil (fiber->top->realVal); break;
case BUILTIN_FLOOR: fiber->top->intVal = (int64_t)floor(fiber->top->realVal); break;
case BUILTIN_ABS:
{
if (fiber->top->intVal == LLONG_MIN)
error->runtimeHandler(error->context, ERR_RUNTIME, "abs() domain error");
fiber->top->intVal = llabs(fiber->top->intVal);
break;
}
case BUILTIN_FABS: fiber->top->realVal = fabs(fiber->top->realVal); break;
case BUILTIN_SQRT:
{
Expand Down
1 change: 1 addition & 0 deletions src/umka_vm.h
Original file line number Diff line number Diff line change
Expand Up @@ -102,6 +102,7 @@ typedef enum
BUILTIN_TRUNC,
BUILTIN_CEIL,
BUILTIN_FLOOR,
BUILTIN_ABS,
BUILTIN_FABS,
BUILTIN_SQRT,
BUILTIN_SIN,
Expand Down

0 comments on commit 938eea7

Please sign in to comment.