Env: Allow load order control for native functions
This commit is contained in:
Vendored
+16
@@ -72,6 +72,22 @@ EnvironmentPtr Environment::create(const ValuePtr lambda, ValueVector&& argument
|
||||
|
||||
// -----------------------------------------
|
||||
|
||||
void Environment::loadFunctions()
|
||||
{
|
||||
loadCollectionAccess();
|
||||
loadCollectionConstructor();
|
||||
loadCollectionModify();
|
||||
loadCompare();
|
||||
loadConvert();
|
||||
loadFormat();
|
||||
loadMeta();
|
||||
loadMutable();
|
||||
loadOperators();
|
||||
loadOther();
|
||||
loadPredicate();
|
||||
loadRepl();
|
||||
}
|
||||
|
||||
void Environment::registerFunction(const std::string& name, FunctionType function)
|
||||
{
|
||||
s_functions.insert_or_assign(name, function);
|
||||
|
||||
Vendored
+15
@@ -24,6 +24,7 @@ public:
|
||||
static EnvironmentPtr create(EnvironmentPtr outer);
|
||||
static EnvironmentPtr create(const ValuePtr lambda, ValueVector&& arguments);
|
||||
|
||||
static void loadFunctions();
|
||||
static void registerFunction(const std::string& name, FunctionType function);
|
||||
static void installFunctions(EnvironmentPtr env);
|
||||
|
||||
@@ -34,6 +35,20 @@ public:
|
||||
private:
|
||||
Environment() {}
|
||||
|
||||
// Outer environment native functions, "Core"
|
||||
static void loadCollectionAccess();
|
||||
static void loadCollectionConstructor();
|
||||
static void loadCollectionModify();
|
||||
static void loadCompare();
|
||||
static void loadConvert();
|
||||
static void loadFormat();
|
||||
static void loadMeta();
|
||||
static void loadMutable();
|
||||
static void loadOperators();
|
||||
static void loadOther();
|
||||
static void loadPredicate();
|
||||
static void loadRepl();
|
||||
|
||||
EnvironmentPtr m_outer { nullptr };
|
||||
std::unordered_map<std::string, ValuePtr> m_values;
|
||||
|
||||
|
||||
+3
@@ -14,6 +14,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadCollectionAccess()
|
||||
{
|
||||
// (first (list 1 2 3)) -> 1
|
||||
ADD_FUNCTION(
|
||||
"first",
|
||||
@@ -135,5 +137,6 @@ ADD_FUNCTION(
|
||||
|
||||
return makePtr<List>(nodes);
|
||||
});
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
@@ -14,6 +14,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadCollectionConstructor()
|
||||
{
|
||||
// (list 1 2) -> (1 2)
|
||||
ADD_FUNCTION(
|
||||
"list",
|
||||
@@ -115,5 +117,6 @@ ADD_FUNCTION(
|
||||
|
||||
return makePtr<HashMap>(elements);
|
||||
});
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
+3
@@ -16,6 +16,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadCollectionModify()
|
||||
{
|
||||
// (apply + 1 2 (list 3 4)) -> (+ 1 2 3 4) -> 10
|
||||
ADD_FUNCTION(
|
||||
"apply",
|
||||
@@ -261,5 +263,6 @@ ADD_FUNCTION(
|
||||
|
||||
return makePtr<HashMap>(elements);
|
||||
});
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
Vendored
+3
@@ -14,6 +14,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadCompare()
|
||||
{
|
||||
#define NUMBER_COMPARE(operator) \
|
||||
{ \
|
||||
bool result = true; \
|
||||
@@ -128,5 +130,6 @@ ADD_FUNCTION(
|
||||
|
||||
return makePtr<Constant>((result) ? Constant::True : Constant::False);
|
||||
});
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
Vendored
+3
@@ -10,6 +10,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadConvert()
|
||||
{
|
||||
// (symbol "foo") -> foo
|
||||
ADD_FUNCTION(
|
||||
"symbol",
|
||||
@@ -45,5 +47,6 @@ ADD_FUNCTION(
|
||||
|
||||
return makePtr<Keyword>(stringValue->data());
|
||||
});
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
Vendored
+3
@@ -16,6 +16,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadFormat()
|
||||
{
|
||||
#define PRINTER_STRING(print_readably, concatenation) \
|
||||
{ \
|
||||
std::string result; \
|
||||
@@ -52,5 +54,6 @@ ADD_FUNCTION("pr-str", PRINTER_STRING(true, " "));
|
||||
|
||||
ADD_FUNCTION("prn", PRINTER_PRINT(true));
|
||||
ADD_FUNCTION("println", PRINTER_PRINT(false));
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
Vendored
+3
@@ -12,6 +12,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadMeta()
|
||||
{
|
||||
// (meta [1 2 3])
|
||||
ADD_FUNCTION(
|
||||
"meta",
|
||||
@@ -49,5 +51,6 @@ ADD_FUNCTION(
|
||||
|
||||
return front->withMeta(*(begin + 1));
|
||||
});
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
Vendored
+3
@@ -15,6 +15,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadMutable()
|
||||
{
|
||||
// (atom 1)
|
||||
ADD_FUNCTION(
|
||||
"atom",
|
||||
@@ -77,5 +79,6 @@ ADD_FUNCTION(
|
||||
|
||||
return atom->reset(value);
|
||||
});
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
Vendored
+3
@@ -12,6 +12,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadOperators()
|
||||
{
|
||||
ADD_FUNCTION(
|
||||
"+",
|
||||
{
|
||||
@@ -87,5 +89,6 @@ ADD_FUNCTION(
|
||||
|
||||
return makePtr<Number>(divide->number() % by->number());
|
||||
});
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
Vendored
+3
@@ -17,6 +17,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadOther()
|
||||
{
|
||||
// (count '(1 2 3)) -> 3
|
||||
// (count [1 2 3]) -> 3
|
||||
ADD_FUNCTION(
|
||||
@@ -67,5 +69,6 @@ ADD_FUNCTION(
|
||||
|
||||
return makePtr<Number>(elapsed);
|
||||
});
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
Vendored
+3
@@ -10,6 +10,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadPredicate()
|
||||
{
|
||||
#define IS_CONSTANT(name, constant) \
|
||||
{ \
|
||||
CHECK_ARG_COUNT_IS(name, SIZE(), 1); \
|
||||
@@ -128,5 +130,6 @@ ADD_FUNCTION(
|
||||
|
||||
return makePtr<Constant>((result) ? Constant::True : Constant::False);
|
||||
});
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
Vendored
+3
@@ -14,6 +14,8 @@
|
||||
|
||||
namespace blaze {
|
||||
|
||||
void Environment::loadRepl()
|
||||
{
|
||||
// REPL reader
|
||||
ADD_FUNCTION(
|
||||
"read-string",
|
||||
@@ -59,5 +61,6 @@ ADD_FUNCTION(
|
||||
|
||||
return eval(*begin, nullptr);
|
||||
});
|
||||
}
|
||||
|
||||
} // namespace blaze
|
||||
|
||||
Vendored
+3
-19
@@ -8,25 +8,9 @@
|
||||
|
||||
#include "env/environment.h"
|
||||
|
||||
// At the top-level you cant invoke any function, but you can create variables.
|
||||
// Using a struct's constructor you can work around this limitation.
|
||||
// Also, the counter macro is used to make the struct names unique.
|
||||
|
||||
#define FUNCTION_STRUCT_NAME(unique) __functionStruct##unique
|
||||
|
||||
#define ADD_FUNCTION_IMPL(unique, symbol, lambda) \
|
||||
struct FUNCTION_STRUCT_NAME(unique) { \
|
||||
FUNCTION_STRUCT_NAME(unique) \
|
||||
(const std::string& __symbol, FunctionType __lambda) \
|
||||
{ \
|
||||
Environment::registerFunction(__symbol, __lambda); \
|
||||
} \
|
||||
}; \
|
||||
static struct FUNCTION_STRUCT_NAME(unique) \
|
||||
FUNCTION_STRUCT_NAME(unique)( \
|
||||
#define ADD_FUNCTION(symbol, lambda) \
|
||||
Environment::registerFunction( \
|
||||
symbol, \
|
||||
[](ValueVectorConstIt begin, ValueVectorConstIt end) -> ValuePtr lambda);
|
||||
|
||||
#define ADD_FUNCTION(symbol, lambda) ADD_FUNCTION_IMPL(__COUNTER__, symbol, lambda);
|
||||
[](ValueVectorConstIt begin, ValueVectorConstIt end) -> blaze::ValuePtr lambda);
|
||||
|
||||
#define SIZE() std::distance(begin, end)
|
||||
|
||||
@@ -149,6 +149,7 @@ auto main(int argc, char* argv[]) -> int
|
||||
std::signal(SIGINT, blaze::cleanup);
|
||||
std::signal(SIGTERM, blaze::cleanup);
|
||||
|
||||
blaze::Environment::loadFunctions();
|
||||
blaze::Environment::installFunctions(blaze::s_outer_env);
|
||||
installLambdas(blaze::s_outer_env);
|
||||
makeArgv(blaze::s_outer_env, arguments);
|
||||
|
||||
Reference in New Issue
Block a user