Fixing 4.x grammar to be backward compatible.

Added 3.x unit tests back to show this.
This commit is contained in:
Jonathan Turner 2012-05-17 10:14:50 -07:00
parent 4674594ee7
commit c73f16fdfe
211 changed files with 1769 additions and 86 deletions

View File

@ -123,7 +123,7 @@ if (BUILD_MODULES)
set(MODULES stl_extra reflection)
endif()
file(GLOB UNIT_TESTS RELATIVE ${CMAKE_CURRENT_SOURCE_DIR}/unittests/ ${CMAKE_CURRENT_SOURCE_DIR}/unittests/*.chai)
file(GLOB UNIT_TESTS RELATIVE ${CMAKE_CURRENT_SOURCE_DIR}/unittests/ ${CMAKE_CURRENT_SOURCE_DIR}/unittests/*.chai ${CMAKE_CURRENT_SOURCE_DIR}/unittests/3.x/*.chai)
list(SORT UNIT_TESTS)

View File

@ -402,7 +402,7 @@ namespace chaiscript
m->add(fun(&dispatch::Dynamic_Object::get_attrs), "get_attrs");
m->add(fun(&dispatch::Dynamic_Object::get_attr), "get_attr");
m->eval("def Dynamic_Object::clone() { auto &new_o = Dynamic_Object(this.get_type_name()); for_each(this.get_attrs(), bind([](new_o, x) { new_o.get_attr(x.first) = x.second; }, new_o, _) ); return new_o; }");
m->eval("def Dynamic_Object::clone() { auto &new_o = Dynamic_Object(this.get_type_name()); for_each(this.get_attrs(), bind(fun(new_o, x) { new_o.get_attr(x.first) = x.second; }, new_o, _) ); return new_o; }");
m->add(fun(&has_guard), "has_guard");
m->add(fun(&get_guard), "get_guard");

View File

@ -321,6 +321,13 @@ namespace chaiscript
throw exception::eval_error("Missing clone or copy constructor for right hand side of equation", e.parameters, t_ss);
}
}
else if (this->children[1]->text == ":=") {
if (lhs.is_undef() || Boxed_Value::type_match(lhs, retval)) {
lhs.assign(retval);
} else {
throw exception::eval_error("Mismatched types in equation");
}
}
else {
try {
retval = t_ss.call_function(this->children[1]->text, lhs, retval);

View File

@ -1119,11 +1119,7 @@ namespace chaiscript
size_t prev_stack_top = m_match_stack.size();
//if (Keyword("fun")) {
if (Char('[')) {
if (!Char(']')) {
throw exception::eval_error("Closure list not currently supported", File_Position(m_line, m_col), *m_filename);
}
if (Keyword("fun")) {
retval = true;
if (Char('(')) {
@ -1546,7 +1542,7 @@ namespace chaiscript
size_t prev_stack_top = m_match_stack.size();
if (Keyword("auto")) {
if (Keyword("auto") || Keyword("var")) {
retval = true;
if (!(Reference() || Id(true))) {
@ -1601,10 +1597,10 @@ namespace chaiscript
size_t prev_stack_top = m_match_stack.size();
if (Char('{')) {
if (Char('[')) {
retval = true;
Container_Arg_List();
if (!Char('}')) {
if (!Char(']')) {
throw exception::eval_error("Missing closing brace '}' in container initializer", File_Position(m_line, m_col), *m_filename);
}
if ((prev_stack_top != m_match_stack.size()) && (m_match_stack.back()->children.size() > 0)) {
@ -1893,7 +1889,7 @@ namespace chaiscript
if (Operator()) {
retval = true;
if (Symbol("=", true, true) || Symbol("+=", true, true) ||
if (Symbol("=", true, true) || Symbol(":=", true, true) || Symbol("+=", true, true) ||
Symbol("-=", true, true) || Symbol("*=", true, true) || Symbol("/=", true, true) ||
Symbol("%=", true, true) || Symbol("<<=", true, true) || Symbol(">>=", true, true) ||
Symbol("&=", true, true) || Symbol("^=", true, true) || Symbol("|=", true, true)) {

View File

@ -7,7 +7,7 @@
#ifndef CHAISCRIPT_PRELUDE_HPP_
#define CHAISCRIPT_PRELUDE_HPP_
//Note, the expression "{x,y}" in "collate" is parsed as two separate expressions
//Note, the expression "[x,y]" in "collate" is parsed as two separate expressions
//by C++, so CODE_STRING, takes two expressions and adds in the missing comma
#define CODE_STRING(x, y) #x ", " #y
@ -23,7 +23,7 @@ def to_string(x) : call_exists(first, x) && call_exists(second, x) { \n\
}\n\
# to_string for containers\n\
def to_string(x) : call_exists(range, x) && !x.is_type("string"){ \n\
"{" + x.join(", ") + "}"; \n\
"[" + x.join(", ") + "]"; \n\
}\n\
# Basic to_string function\n\
def to_string(x) { \n\
@ -259,7 +259,7 @@ def generate_range(x, y) { \n\
}\n\
# Returns a new Vector with the first value to the second value as its elements\n\
def collate(x, y) { \n\
return {x, y}; \n\
return [x, y]; \n\
} \n\
def zip_with(f, x, y, inserter) : call_exists(range, x) && call_exists(range, y) { \n\
auto r_x = range(x); \n\
@ -305,10 +305,10 @@ def string::find_last_not_of(list) : is_type(list, "string") { \n\
int(find_last_not_of(this, list, -1)); \n\
} \n\
def string::ltrim() { \n\
drop_while(this, [](x) { x == ' ' || x == '\t' || x == '\r' || x == '\n'}); \n\
drop_while(this, fun(x) { x == ' ' || x == '\t' || x == '\r' || x == '\n'}); \n\
} \n\
def string::rtrim() { \n\
reverse(drop_while(reverse(this), [](x) { x == ' ' || x == '\t' || x == '\r' || x == '\n'})); \n\
reverse(drop_while(reverse(this), fun(x) { x == ' ' || x == '\t' || x == '\r' || x == '\n'})); \n\
} \n\
def string::trim() { \n\
ltrim(rtrim(this)); \n\

View File

@ -0,0 +1,2 @@
assert_throws("Mismatched types in equation, lhs is const.", fun() { 1 = 2 } );
assert_throws("Mismatched types in equation, lhs is const.", fun() { 1 + 2 = 2 } );

2
unittests/3.x/bind.chai Normal file
View File

@ -0,0 +1,2 @@
var prod = bind(foldl, _, `*`, 1.0)
assert_equal(60, prod([3, 4, 5]))

34
unittests/3.x/bind2.chai Normal file
View File

@ -0,0 +1,34 @@
def add(x, y)
{
return x + y;
}
assert_equal(2, add.get_arity());
var b = bind(add, 2, _);
assert_equal(1, b.get_arity());
var c = bind(b, 3);
assert_equal(0, c.get_arity());
assert_equal(6, b(4));
assert_equal(5, c());
def concat2(a,b,c,d)
{
return to_string(a) + to_string(b) + to_string(c) + to_string(d);
}
var d = bind(concat2, _, " Hello ", _, " World");
assert_equal(2, d.get_arity());
assert_equal("1 Hello 3 World", d(1,3));
var e = bind(`<`, _, 5);
var types = e.get_param_types();
assert_equal(2, types.size());
assert_equal(true, types[0].bare_equal(bool_type));

View File

@ -0,0 +1 @@
{print("hello")}

View File

@ -0,0 +1 @@
assert_equal(false, !true)

View File

@ -0,0 +1,319 @@
#include <chaiscript/utility/utility.hpp>
using namespace chaiscript;
template<typename T>
void use(T){}
template<typename To>
bool run_test_type_conversion(const Boxed_Value &bv, bool expectedpass)
{
try {
To ret = chaiscript::boxed_cast<To>(bv);
use(ret);
} catch (const chaiscript::exception::bad_boxed_cast &/*e*/) {
if (expectedpass) {
// std::cerr << "Failure in run_test_type_conversion: " << e.what() << std::endl;
return false;
} else {
return true;
}
} catch (const std::exception &e) {
std::cerr << "Unexpected standard exception when attempting cast_conversion: " << e.what() << std::endl;
return false;
} catch (...) {
std::cerr << "Unexpected unknown exception when attempting cast_conversion." << std::endl;
return false;
}
if (expectedpass)
{
return true;
} else {
return false;
}
}
template<typename To>
bool test_type_conversion(const Boxed_Value &bv, bool expectedpass)
{
bool ret = run_test_type_conversion<To>(bv, expectedpass);
if (!ret)
{
std::cerr << "Error with type conversion test. From: "
<< (bv.is_const()?(std::string("const ")):(std::string())) << bv.get_type_info().name()
<< " To: "
<< (boost::is_const<To>::value?(std::string("const ")):(std::string())) << typeid(To).name()
<< " test was expected to " << ((expectedpass)?(std::string("succeed")):(std::string("fail"))) << " but did not" << std::endl;
}
return ret;
}
template<typename Type>
bool do_test(const Boxed_Value &bv, bool T, bool ConstT, bool TRef, bool ConstTRef, bool TPtr, bool ConstTPtr, bool TPtrConst,
bool ConstTPtrConst, bool SharedPtrT, bool SharedConstPtrT,
bool ConstSharedPtrT, bool ConstSharedConstPtrT, bool ConstSharedPtrTRef, bool ConstSharedPtrTConstRef,
bool BoostRef, bool BoostConstRef, bool ConstBoostRef, bool ConstBoostConstRef,
bool ConstBoostRefRef, bool ConstBoostConstRefRef, bool Number,
bool ConstNumber, bool ConstNumberRef, bool TPtrConstRef, bool ConstTPtrConstRef)
{
bool passed = true;
passed &= test_type_conversion<Type>(bv, T);
passed &= test_type_conversion<const Type>(bv, ConstT);
passed &= test_type_conversion<Type &>(bv, TRef);
passed &= test_type_conversion<const Type &>(bv, ConstTRef);
passed &= test_type_conversion<Type *>(bv, TPtr);
passed &= test_type_conversion<const Type *>(bv, ConstTPtr);
passed &= test_type_conversion<Type * const>(bv, TPtrConst);
passed &= test_type_conversion<const Type * const>(bv, ConstTPtrConst);
passed &= test_type_conversion<boost::shared_ptr<Type> >(bv, SharedPtrT);
passed &= test_type_conversion<boost::shared_ptr<const Type> >(bv, SharedConstPtrT);
passed &= test_type_conversion<boost::shared_ptr<Type> &>(bv, false);
passed &= test_type_conversion<boost::shared_ptr<const Type> &>(bv, false);
passed &= test_type_conversion<const boost::shared_ptr<Type> >(bv, ConstSharedPtrT);
passed &= test_type_conversion<const boost::shared_ptr<const Type> >(bv, ConstSharedConstPtrT);
passed &= test_type_conversion<const boost::shared_ptr<Type> &>(bv, ConstSharedPtrTRef);
passed &= test_type_conversion<const boost::shared_ptr<const Type> &>(bv, ConstSharedPtrTConstRef);
passed &= test_type_conversion<boost::reference_wrapper<Type> >(bv, BoostRef);
passed &= test_type_conversion<boost::reference_wrapper<const Type> >(bv, BoostConstRef);
passed &= test_type_conversion<boost::reference_wrapper<Type> &>(bv, false);
passed &= test_type_conversion<boost::reference_wrapper<const Type> &>(bv, false);
passed &= test_type_conversion<const boost::reference_wrapper<Type> >(bv, ConstBoostRef);
passed &= test_type_conversion<const boost::reference_wrapper<const Type> >(bv, ConstBoostConstRef);
passed &= test_type_conversion<const boost::reference_wrapper<Type> &>(bv, ConstBoostRefRef);
passed &= test_type_conversion<const boost::reference_wrapper<const Type> &>(bv, ConstBoostConstRefRef);
passed &= test_type_conversion<Boxed_Number>(bv, Number);
passed &= test_type_conversion<const Boxed_Number>(bv, ConstNumber);
passed &= test_type_conversion<Boxed_Number &>(bv, false);
passed &= test_type_conversion<const Boxed_Number &>(bv, ConstNumberRef);
passed &= test_type_conversion<Boxed_Number *>(bv, false);
passed &= test_type_conversion<const Boxed_Number *>(bv, false);
passed &= test_type_conversion<Boxed_Number * const>(bv, false);
passed &= test_type_conversion<const Boxed_Number *const>(bv, false);
passed &= test_type_conversion<Type *&>(bv, false);
passed &= test_type_conversion<const Type *&>(bv, false);
passed &= test_type_conversion<Type * const&>(bv, TPtrConstRef);
passed &= test_type_conversion<const Type * const&>(bv, ConstTPtrConstRef);
passed &= test_type_conversion<Boxed_Value>(bv, true);
passed &= test_type_conversion<const Boxed_Value>(bv, true);
passed &= test_type_conversion<const Boxed_Value &>(bv, true);
return passed;
}
/** Tests intended for built int types **/
template<typename T>
bool built_in_type_test(const T &initial, bool ispod)
{
bool passed = true;
/** value tests **/
T i = T(initial);
passed &= do_test<T>(var(i), true, true, true, true, true,
true, true, true, true, true,
true, true, true, true, true,
true, true, true, true, true,
ispod && true, ispod && true, ispod && true, true, true);
passed &= do_test<T>(const_var(i), true, true, false, true, false,
true, false, true, false, true,
false, true, false, true, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
passed &= do_test<T>(var(&i), true, true, true, true, true,
true, true, true, false, false,
false, false, false, false, true,
true, true, true, true, true,
ispod && true, ispod && true, ispod && true, true, true);
passed &= do_test<T>(const_var(&i), true, true, false, true, false,
true, false, true, false, false,
false, false, false, false, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, ispod && false, true);
passed &= do_test<T>(var(boost::ref(i)), true, true, true, true, true,
true, true, true, false, false,
false, false, false, false, true,
true, true, true, true, true,
ispod && true, ispod && true, ispod && true, true, true);
passed &= do_test<T>(var(boost::cref(i)), true, true, false, true, false,
true, false, true, false, false,
false, false, false, false, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
/** Const Reference Variable tests */
// This reference will be copied on input, which is expected
const T &ir = i;
passed &= do_test<T>(var(i), true, true, true, true, true,
true, true, true, true, true,
true, true, true, true, true,
true, true, true, true, true,
ispod && true, ispod && true, ispod && true, true, true);
// But a pointer or reference to it should be necessarily const
passed &= do_test<T>(var(&ir), true, true, false, true, false,
true, false, true, false, false,
false, false, false, false, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
passed &= do_test<T>(var(boost::ref(ir)), true, true, false, true, false,
true, false, true, false, false,
false, false, false, false, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
// Make sure const of const works too
passed &= do_test<T>(const_var(&ir), true, true, false, true, false,
true, false, true, false, false,
false, false, false, false, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
passed &= do_test<T>(const_var(boost::ref(ir)), true, true, false, true, false,
true, false, true, false, false,
false, false, false, false, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
/** Const Reference Variable tests */
// This will always be seen as a const
const T*cip = &i;
passed &= do_test<T>(var(cip), true, true, false, true, false,
true, false, true, false, false,
false, false, false, false, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
// make sure const of const works
passed &= do_test<T>(const_var(cip), true, true, false, true, false,
true, false, true, false, false,
false, false, false, false, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
/** shared_ptr tests **/
boost::shared_ptr<T> ip(new T(initial));
passed &= do_test<T>(var(ip), true, true, true, true, true,
true, true, true, true, true,
true, true, true, true, true,
true, true, true, true, true,
ispod && true, ispod && true, ispod && true, true, true);
passed &= do_test<T>(const_var(ip), true, true, false, true, false,
true, false, true, false, true,
false, true, false, true, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
/** const shared_ptr tests **/
boost::shared_ptr<const T> ipc(new T(initial));
passed &= do_test<T>(var(ipc), true, true, false, true, false,
true, false, true, false, true,
false, true, false, true, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
// const of this should be the same, making sure it compiles
passed &= do_test<T>(const_var(ipc), true, true, false, true, false,
true, false, true, false, true,
false, true, false, true, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
/** Double ptr tests **/
/*
T **doublep;
passed &= do_test<T*>(var(doublep), true, true, false, true, false,
true, false, true, false, true,
false, true, false, true, false,
true, false, true, false, true,
ispod && true, ispod && true, ispod && true, false, true);
*/
return passed;
}
template<typename T>
bool pointer_test(const T& default_value, const T& new_value)
{
T *p = new T(default_value);
// we store a pointer to a pointer, so we can get a pointer to a pointer
try {
T **result = boxed_cast<T **>(var(&p));
*(*result) = new_value;
if (p != (*result) ) {
std::cerr << "Pointer passed in different than one returned" << std::endl;
return false;
}
if (*p != *(*result) ) {
std::cerr << "Somehow dereferenced pointer values are not the same?" << std::endl;
return false;
}
return true;
} catch (const exception::bad_boxed_cast &) {
std::cerr << "Bad boxed cast performing ** to ** test" << std::endl;
return false;
} catch (...) {
std::cerr << "Unknown exception performing ** to ** test" << std::endl;
return false;
}
}
int main()
{
bool passed = true;
/*
bool T, bool ConstT, bool TRef, bool ConstTRef, bool TPtr,
bool ConstTPtr, bool TPtrConst, bool ConstTPtrConst, bool SharedPtrT, bool SharedConstPtrT,
bool ConstSharedPtrT, bool ConstSharedConstPtrT, bool ConstSharedPtrTRef, bool ConstSharedPtrTConstRef, bool BoostRef,
bool BoostConstRef, bool ConstBoostRef, bool ConstBoostConstRef, bool ConstBoostRefRef, bool ConstBoostConstRefRef,
bool Number, bool ConstNumber, bool ConstNumberRef
*/
passed &= built_in_type_test<int>(5, true);
passed &= built_in_type_test<double>(1.1, true);
passed &= built_in_type_test<char>('a', true);
passed &= built_in_type_test<uint8_t>('a', true);
passed &= built_in_type_test<int64_t>('a', true);
passed &= built_in_type_test<bool>(false, false);
passed &= built_in_type_test<std::string>("Hello World", false);
// storing a pointer
passed &= pointer_test<int>(1, 0);
if (passed)
{
return EXIT_SUCCESS;
} else {
return EXIT_FAILURE;
}
}

View File

@ -0,0 +1,7 @@
var i = 0
while (i < 10) {
if (++i == 5) {
break
}
}
assert_equal(5, i);

View File

@ -0,0 +1 @@
assert_equal("b", to_string('b'))

View File

@ -0,0 +1,7 @@
assert_equal(true, 1.is_var_const());
assert_equal(false, 1.is_var_reference());
assert_equal(true, 1.is_var_pointer());
assert_equal(false, 1.is_var_null());
assert_equal(false, 1.is_var_undef());
var i;
assert_equal(true, i.is_var_undef());

View File

@ -0,0 +1,3 @@
var v = collate(1, 2)
assert_equal(1, v[0])
assert_equal(2, v[1])

View File

@ -0,0 +1 @@
assert_equal(false, 1 > 2);

View File

@ -0,0 +1 @@
assert_equal(true, 1 < 2)

View File

@ -0,0 +1,5 @@
var v = concat([1, 2], [3, 4]);
assert_equal(4, v.size());
assert_equal(1, v[0]);
assert_equal(4, v[3]);

View File

@ -0,0 +1,4 @@
//If the following succeeds, the test passes
"Hello World".for_each(fun(x) { print(x) } )

View File

@ -0,0 +1 @@
assert_equal("3.5bob", 3.5.to_string() + "bob");

View File

@ -0,0 +1 @@
assert_equal("3bob", 3.to_string + "bob")

View File

@ -0,0 +1 @@
assert_equal(6.8, "3.5".to_double() + 3.3)

View File

@ -0,0 +1 @@
assert_equal(8, "4".to_int() + 4)

View File

@ -0,0 +1,11 @@
var a = [1,2,3, [4,5,6] ]
assert_equal(a[3][0], 4)
def Test::Test() { this.a = [1,2,3]; }
attr Test::a;
var t = Test();
assert_equal(t.a[0], 1)

View File

@ -0,0 +1,11 @@
assert_equal(`==`, `==`);
assert_not_equal(`==`, `<`);
assert_equal(`<`.get_arity(), 2);
assert_equal(`+`.get_annotation(), "Multiple method dispatch function wrapper.");
assert_equal(get_arity.get_contained_functions().size(), 0);
assert_equal(get_arity.get_arity(), 1);
assert_equal(get_arity.get_param_types().size(), 2);
var paramtypes = get_arity.get_param_types();
assert_equal(true, paramtypes[1].bare_equal(Function_type));

1
unittests/3.x/drop.chai Normal file
View File

@ -0,0 +1 @@
assert_equal([3,4], drop([1, 2, 3, 4], 2))

View File

@ -0,0 +1 @@
assert_equal([2, 3], drop_while([1, 2, 3], odd))

View File

@ -0,0 +1,44 @@
#include <chaiscript/utility/utility.hpp>
template<typename LHS, typename RHS>
void assert_equal(const LHS &lhs, const RHS &rhs)
{
if (lhs==rhs)
{
return;
} else {
std::cout << "Got: " << lhs << " expected " << rhs << std::endl;
exit(EXIT_FAILURE);
}
}
int main()
{
chaiscript::ChaiScript chai;
chai("attr bob::z; def bob::bob() { this.z = 10 }; var x = bob()");
chaiscript::dispatch::Dynamic_Object &mydo = chai.eval<chaiscript::dispatch::Dynamic_Object &>("x");
assert_equal(mydo.get_type_name(), "bob");
assert_equal(chaiscript::boxed_cast<int>(mydo.get_attr("z")), 10);
chai("x.z = 15");
assert_equal(chaiscript::boxed_cast<int>(mydo.get_attr("z")), 15);
int &z = chaiscript::boxed_cast<int&>(mydo.get_attr("z"));
assert_equal(z, 15);
z = 20;
assert_equal(z, 20);
assert_equal(chaiscript::boxed_cast<int>(chai("x.z")), 20);
return EXIT_SUCCESS;
}

0
unittests/3.x/empty.chai Normal file
View File

View File

@ -0,0 +1,4 @@
var x=.5
assert_equal(.5, x)
var y=-.5
assert_equal(-.5, y)

1
unittests/3.x/eval.chai Normal file
View File

@ -0,0 +1 @@
assert_equal(7, eval("3 + 4"))

View File

@ -0,0 +1,122 @@
// Tests to make sure that the order in which function dispatches occur is correct
#include <chaiscript/chaiscript.hpp>
int test_generic()
{
chaiscript::ChaiScript chai;
try {
chai.eval("throw(runtime_error(\"error\"));");
} catch (const chaiscript::Boxed_Value &bv) {
const std::exception &e = chaiscript::boxed_cast<const std::exception &>(bv);
if (e.what() == std::string("error"))
{
return EXIT_SUCCESS;
}
}
std::cout << "test_generic failed" << std::endl;
return EXIT_FAILURE;
}
int test_1()
{
chaiscript::ChaiScript chai;
try {
chai.eval("throw(1)", chaiscript::exception_specification<int>());
} catch (int e) {
if (e == 1)
{
return EXIT_SUCCESS;
}
}
std::cout << "test_1 failed" << std::endl;
return EXIT_FAILURE;
}
int test_2()
{
chaiscript::ChaiScript chai;
try {
chai.eval("throw(1.0)", chaiscript::exception_specification<int, double>());
} catch (const double e) {
if (e == 1.0)
{
return EXIT_SUCCESS;
}
}
std::cout << "test_2 failed" << std::endl;
return EXIT_FAILURE;
}
int test_5()
{
chaiscript::ChaiScript chai;
try {
chai.eval("throw(runtime_error(\"error\"))", chaiscript::exception_specification<int, double, float, const std::string &, const std::exception &>());
} catch (const double e) {
std::cout << "test_5 failed with double" << std::endl;
return EXIT_FAILURE;
} catch (int) {
std::cout << "test_5 failed with int" << std::endl;
return EXIT_FAILURE;
} catch (float) {
std::cout << "test_5 failed with float" << std::endl;
return EXIT_FAILURE;
} catch (const std::string &) {
std::cout << "test_5 failed with string" << std::endl;
return EXIT_FAILURE;
} catch (const std::exception &e) {
return EXIT_SUCCESS;
}
std::cout << "test_5 failed" << std::endl;
return EXIT_FAILURE;
}
int test_unhandled()
{
chaiscript::ChaiScript chai;
try {
chai.eval("throw(\"error\")", chaiscript::exception_specification<int, double, float, const std::exception &>());
} catch (double) {
std::cout << "test_unhandled failed with double" << std::endl;
return EXIT_FAILURE;
} catch (int) {
std::cout << "test_unhandled failed with int" << std::endl;
return EXIT_FAILURE;
} catch (float) {
std::cout << "test_unhandled failed with float" << std::endl;
return EXIT_FAILURE;
} catch (const std::exception &e) {
std::cout << "test_unhandled failed with std::exception" << std::endl;
return EXIT_FAILURE;
} catch (const chaiscript::Boxed_Value &bv) {
return EXIT_SUCCESS;
}
std::cout << "test_unhandled failed" << std::endl;
return EXIT_FAILURE;
}
int main()
{
if (test_generic() == EXIT_SUCCESS
&& test_1() == EXIT_SUCCESS
&& test_2() == EXIT_SUCCESS
&& test_5() == EXIT_SUCCESS
&& test_unhandled() == EXIT_SUCCESS)
{
return EXIT_SUCCESS;
} else {
return EXIT_FAILURE;
}
}

View File

@ -0,0 +1,39 @@
load_module("reflection")
def deep()
{
try {
} catch {
} finally {
if (2)
{
}
}
}
def func()
{
deep();
}
def doing()
{
for (var i = 0; i < 10; ++i)
{
func();
}
}
def while_doing()
{
while (true)
{
doing();
}
}
var f = fun() { while_doing(); }
assert_equal(get_eval_error(f).call_stack.size(), 16)

1
unittests/3.x/even.chai Normal file
View File

@ -0,0 +1 @@
assert_equal(true, even(4))

View File

@ -0,0 +1,9 @@
var x = 1
try {
throw(x)
x = 2
}
catch(e) {
x = e + 3
}
assert_equal(4, x);

View File

@ -0,0 +1,32 @@
var finallyone = false;
try {
throw(3)
}
catch(x) {
assert_equal(3, x)
}
finally {
finallyone = true;
}
assert_equal(true, finallyone);
var try2 = false;
var catch2 = false;
var finally2 = false;
try {
try2 = true;
}
catch {
catch2 = true;
}
finally {
finally2 = true;
}
assert_equal(true, try2);
assert_equal(false, catch2);
assert_equal(true, finally2);

View File

@ -0,0 +1,34 @@
var results = [];
for (var i = 2; i < 6; ++i) {
try {
throw(i)
}
catch(e) : e < 2 {
results.push_back("c1: " + e.to_string());
}
catch(e) : e < 4 {
results.push_back("c2: " + e.to_string());
}
catch(e) {
results.push_back("c3: " + e.to_string());
}
catch {
// Should never get called
assert_equal(false, true)
}
}
try {
throw(3)
}
catch(e) : e < 3
{
// Should never get called
assert_equal(false, true);
}
catch {
results.push_back("defaultcatch");
}
assert_equal(["c2: 2", "c2: 3", "c3: 4", "c3: 5", "defaultcatch"], results);

View File

@ -0,0 +1 @@
assert_equal([1,3], filter([1, 2, 3, 4], odd))

7
unittests/3.x/float.chai Normal file
View File

@ -0,0 +1,7 @@
assert_equal(true, 1.2 < 2)
assert_equal(true, 1.2 > 1)
assert_equal(1.2, 1.2)
assert_equal(true, .5 > 0)
assert_equal(true, .5 < 1)
assert_equal(0.5, .5)

1
unittests/3.x/foldl.chai Normal file
View File

@ -0,0 +1 @@
assert_equal(10, foldl([1, 2, 3, 4], `+`, 0))

7
unittests/3.x/for.chai Normal file
View File

@ -0,0 +1,7 @@
var ret = []
for (var i = 0; i < 5; ++i) {
ret.push_back(i);
}
assert_equal([0,1,2,3,4], ret);

View File

@ -0,0 +1 @@
for_each([1, 2, 3], print)

View File

@ -0,0 +1,3 @@
var v = [1,2,3];
var r = range(v);
for_each(r, fun(x) { assert_equal(true, x>0); } )

View File

@ -0,0 +1,4 @@
// Don't bother checking the output from this one, just makes sure it executes
var v = [1,2,3];
var r = retro(range(v));
for_each(r, print)

View File

@ -0,0 +1 @@
assert_equal(2, `+`.get_contained_functions()[0].get_arity())

View File

@ -0,0 +1,76 @@
#Test Function Description
def test_function(a)
{
return a;
}
// test_function tests
assert_equal(test_function.get_arity(), 1);
assert_equal(trim(test_function.get_annotation()), "#Test Function Description");
assert_equal(test_function.get_contained_functions().size(), 0);
assert_equal(test_function.get_param_types().size(), 2);
assert_equal(test_function, test_function);
assert_not_equal(test_function, `+`);
assert_equal(test_function.call([1]), 1);
// dynamic object function tests
def int::test_fun()
{
return this;
}
assert_equal(test_fun.get_arity(), 1);
assert_equal(test_fun.get_contained_functions.size(), 1);
assert_equal(test_fun.get_param_types().size(), 2);
assert_equal(test_fun, test_fun);
var test_fun_types = test_fun.get_param_types();
assert_equal(true, test_fun_types[0].bare_equal(Object_type));
assert_equal(true, test_fun_types[1].bare_equal(int_type));
// built-ins tests
assert_equal(2, `==`.get_arity());
// < should be the merging of two functions bool <(PODObject, PODObject) and bool <(string, string)
// we want to peel it apart and make sure that's true
var types = `<`.get_param_types();
assert_equal(3, types.size());
assert_equal(true, types[0].bare_equal(bool_type));
assert_equal(true, types[1].bare_equal(Object_type));
assert_equal(true, types[2].bare_equal(Object_type));
assert_equal(2, `<`.get_contained_functions().size());
// guard existence tests
def with_guard(x) : x > 3 {}
def without_guard(x) {}
def group_guard(x) {}
def group_guard(x) : x > 3 {}
assert_equal(true, with_guard.has_guard());
assert_equal(false, without_guard.has_guard());
assert_equal(2, group_guard.get_contained_functions().size());
var group = group_guard.get_contained_functions();
assert_equal(true, group[0].has_guard())
assert_equal(false, group[1].has_guard())
assert_throws("Function does not have a guard", fun() { group[0].get_guard(); } );
assert_throws("Function does not have a guard", fun() { without_guard.get_guard(); } );
var guard = with_guard.get_guard();
assert_equal(false, guard.has_guard());
assert_throws("Function does not have a guard", fun() { guard.get_guard(); } );

View File

@ -0,0 +1,38 @@
// Tests to make sure that the order in which function dispatches occur is correct
#include <chaiscript/utility/utility.hpp>
int test_one(const int &)
{
return 1;
}
int test_two(int &)
{
return 2;
}
int main()
{
chaiscript::ChaiScript chai;
chai.eval("def test_fun(x) { return 3; }");
chai.eval("def test_fun(x) : x == \"hi\" { return 4; }");
chai.eval("def test_fun(x) { return 5; }");
chai.add(chaiscript::fun(&test_one), "test_fun");
chai.add(chaiscript::fun(&test_two), "test_fun");
int res1 = chai.eval<int>("test_fun(1)");
int res2 = chai.eval<int>("var i = 1; test_fun(i)");
int res3 = chai.eval<int>("test_fun(\"bob\")");
int res4 = chai.eval<int>("test_fun(\"hi\")");
if (res1 == 1
&& res2 == 2
&& res3 == 3
&& res4 == 4 )
{
return EXIT_SUCCESS;
} else {
return EXIT_FAILURE;
}
}

View File

@ -0,0 +1,3 @@
var x = `+`
x = `-`
assert_equal(1, x(5,4))

View File

@ -0,0 +1,25 @@
#include <chaiscript/utility/utility.hpp>
double test_call(const boost::function<double (int)> &f, int val)
{
return f(val);
}
int main()
{
chaiscript::ChaiScript chai;
chai.add(chaiscript::fun(&test_call), "test_call");
chai.eval("def func(i) { return i * 3.5; };");
double d = chai.eval<double>("test_call(func, 3)");
if (d == 3 * 3.5)
{
return EXIT_SUCCESS;
} else {
return EXIT_FAILURE;
}
}

View File

@ -0,0 +1,26 @@
#include <chaiscript/utility/utility.hpp>
int main()
{
chaiscript::ChaiScript chai;
chai.eval("def func() { print(\"Hello World\"); } ");
boost::function<void ()> f = chai.eval<boost::function<void ()> >("func");
f();
if (chai.eval<boost::function<std::string (int)> >("to_string")(6) != "6")
{
return EXIT_FAILURE;
}
if (chai.eval<boost::function<std::string (const chaiscript::Boxed_Value &)> >("to_string")(chaiscript::var(6)) == "6")
{
return EXIT_SUCCESS;
} else {
return EXIT_FAILURE;
}
}

View File

@ -0,0 +1 @@
assert_equal([1,2,3,4,5,6,7,8,9,10], generate_range(1, 10))

View File

@ -0,0 +1,7 @@
load_module("test_module")
assert_equal(to_int(TestValue1), 1)
assert_equal(TestValue1.type_name(), "TestEnum")

7
unittests/3.x/if.chai Normal file
View File

@ -0,0 +1,7 @@
var t = false;
if (true) {
t = true;
}
assert_equal(true, t);

View File

@ -0,0 +1,13 @@
var i = 3
var b1 = false;
var b2 = false;
if (i == 2) {
b1 = true;
}
else {
b2 = true;
}
assert_equal(false, b1);
assert_equal(true, b2);

View File

@ -0,0 +1,18 @@
var b1 = false;
var b2 = false;
var b3 = false;
var i = 3
if (i == 2) {
b1 = true;
}
else if (i == 4) {
b2 = true;
}
else if (i == 3) {
b3 = true;
}
assert_equal(false, b1);
assert_equal(false, b2);
assert_equal(true, b3);

View File

@ -0,0 +1,14 @@
var i = 3
var b = false
if (i == 2) {
assert_equal(false, true)
}
else if (i == 4) {
assert_equal(false, true)
}
else {
assert_equal(true, true)
b = true
}
assert_equal(true, b)

View File

@ -0,0 +1,10 @@
// tests more complex parses of the index operator
def Bob::bob3() { return [1,2,3]; }
def Bob::Bob() {}
var b = Bob();
assert_equal(b.bob3()[0], 1);
assert_equal((b.bob3())[1], 2);

View File

@ -0,0 +1,8 @@
load_module("test_module")
var t0 = TestBaseType()
var t = TestDerivedType();
assert_equal(t0.func(), 0);
assert_equal(t.func(), 1);

View File

@ -0,0 +1,3 @@
var bob = 5.5
assert_equal("5.5", "${bob}")
assert_equal("val: 8 and 8", "val: ${5.5 + 2.5} and ${bob + 2.5}")

View File

@ -0,0 +1,4 @@
assert_equal("\$ {4 + 5}", "$ {4 + 5}")
assert_equal("\$9", "$${4+5}")
assert_equal("Value: \${4 + 5}", "Value: \${4 + 5}")
assert_equal("Value: \$9", "Value: \$${4 + 5}")

View File

@ -0,0 +1 @@
assert_throws("Illegal const function assignment", fun() { clone = `-` } );

View File

@ -0,0 +1 @@
assert_throws("Invalid function reassignment", fun() { var x = 5; x = `-`; } );

View File

@ -0,0 +1,4 @@
var i;
assert_equal(true, i.is_var_undef());
i = 5;
assert_equal(false, i.is_var_undef());

1
unittests/3.x/join.chai Normal file
View File

@ -0,0 +1 @@
assert_equal("1*2*3", join([1, 2, 3], "*"))

View File

@ -0,0 +1,2 @@
var bob = fun(x) { x + 1 }
assert_equal(4, bob(3));

View File

@ -0,0 +1,8 @@
load_module("stl_extra")
var x = List()
x.push_back(3)
x.push_back("A")
assert_equal(3, x.front());
assert_equal("A", x.back());

View File

@ -0,0 +1,8 @@
load_module("stl_extra")
var x = List()
x.push_front(3)
x.push_front("A")
assert_equal("A", x.front());
assert_equal(3, x.back());

View File

@ -0,0 +1,2 @@
load_module("test_module")
assert_equal("Hello World", hello_world());

View File

@ -0,0 +1,9 @@
var total = 0
for (var i = 0; i < 10; ++i) {
for (var j = 0; j < 10; ++j) {
total += 1
}
}
assert_equal(100, total);

View File

@ -0,0 +1,2 @@
assert_throws("Parse failure", fun() { eval("[\"hello\":5,\"j\",\"k\"]") } );

1
unittests/3.x/map.chai Normal file
View File

@ -0,0 +1 @@
assert_equal([true, false, true], map([1,2,3], odd))

View File

@ -0,0 +1,2 @@
var x = ["bob":2, "fred":3]
assert_equal(3, x["fred"])

View File

@ -0,0 +1,3 @@
var x = ["bob":1, "fred":2]
assert_equal(2, x.size());

View File

@ -0,0 +1 @@
assert_equal(3, (1 + 2))

View File

@ -0,0 +1 @@
assert_equal(3.5, 1.5 + 2)

View File

@ -0,0 +1,3 @@
var i = 3
assert_equal(2, --i)
assert_equal(2, i)

View File

@ -0,0 +1 @@
assert_equal(2, 10/5)

View File

@ -0,0 +1,3 @@
var i = 3
assert_equal(4, ++i)
assert_equal(4, i)

View File

@ -0,0 +1 @@
assert_equal(2, 11 % 3)

View File

@ -0,0 +1 @@
assert_equal(12, 3 * 4)

View File

@ -0,0 +1 @@
assert_equal(-7, -(3 + 4))

View File

@ -0,0 +1 @@
assert_equal(27, 3*(4+5))

View File

@ -0,0 +1 @@
assert_equal(2, 5 - 3)

1
unittests/3.x/max.chai Normal file
View File

@ -0,0 +1 @@
assert_equal(5, max(3, 5))

View File

@ -0,0 +1,12 @@
attr Vector3::x
attr Vector3::y
attr Vector3::z
def Vector3::Vector3(x, y, z) {
this.x = x
this.y = y
this.z = z
}
var v = Vector3(1,2,3);
assert_equal(1, v.x);

View File

@ -0,0 +1 @@
assert_equal(6, [1, 2, 3].sum())

1
unittests/3.x/min.chai Normal file
View File

@ -0,0 +1 @@
assert_equal(3, min(3, 5))

20
unittests/3.x/mmd1.chai Normal file
View File

@ -0,0 +1,20 @@
def bob(x, y, z) {
x + y + z
}
def bob(x, y) {
x - y
}
def bob(x) {
-x
}
def bob() {
10
}
assert_equal(10, bob())
assert_equal(-5, bob(5))
assert_equal(-1, bob(5,6))
assert_equal(18, bob(5,6,7))

9
unittests/3.x/mmd2.chai Normal file
View File

@ -0,0 +1,9 @@
def bob(x, y) : x > 10 { x - y }
def bob(x, y) : x > 5 { x - y + 10 }
def bob(x, y) { x + y }
assert_equal(7, bob(3,4))
assert_equal(9, bob(6,7))
assert_equal(-1, bob(11,12))

View File

@ -0,0 +1,12 @@
#include "multifile_test_chai.hpp"
Multi_Test_Chai::Multi_Test_Chai()
: m_chai(new chaiscript::ChaiScript())
{
}
boost::shared_ptr<chaiscript::ChaiScript> Multi_Test_Chai::get_chai()
{
return m_chai;
}

View File

@ -0,0 +1,14 @@
#include <chaiscript/chaiscript.hpp>
class Multi_Test_Chai
{
public:
Multi_Test_Chai();
boost::shared_ptr<chaiscript::ChaiScript> get_chai();
private:
boost::shared_ptr<chaiscript::ChaiScript> m_chai;
};

View File

@ -0,0 +1,14 @@
#include "multifile_test_chai.hpp"
#include "multifile_test_module.hpp"
#include <chaiscript/chaiscript.hpp>
int main()
{
Multi_Test_Chai chaitest;
Multi_Test_Module chaimodule;
boost::shared_ptr<chaiscript::ChaiScript> chai = chaitest.get_chai();
chai->add(chaimodule.get_module());
return chai->eval<int>("get_module_value()");
}

View File

@ -0,0 +1,21 @@
#include <chaiscript/chaiscript.hpp>
#include "multifile_test_module.hpp"
Multi_Test_Module::Multi_Test_Module()
{
}
int Multi_Test_Module::get_module_value()
{
return 0;
}
chaiscript::ModulePtr Multi_Test_Module::get_module()
{
chaiscript::ModulePtr module(new chaiscript::Module());
module->add(chaiscript::fun(&Multi_Test_Module::get_module_value), "get_module_value");
return module;
}

View File

@ -0,0 +1,11 @@
#include <chaiscript/chaiscript.hpp>
class Multi_Test_Module
{
public:
static int get_module_value();
Multi_Test_Module();
chaiscript::ModulePtr get_module();
};

View File

@ -0,0 +1,9 @@
var x = [1, 2,
3, 4]
assert_equal(1, x[0])
var y = map(x,
fun(x) { x + 1 })
assert_equal(2, y[0])

View File

@ -0,0 +1,3 @@
assert_equal(10, 012)
assert_equal(31, 0x1f)
assert_equal(3, 0b11)

View File

@ -0,0 +1,6 @@
attr bob::z
def bob::bob() { this.z = 10 }
var x = bob()
def bob::fred(x) { this.z - x }
assert_equal(7, x.fred(3))

View File

@ -0,0 +1,9 @@
attr bob::z
def bob::bob() { this.z = 10 }
attr bob2::z
def bob2::bob2() { this.z = 12 }
var b = bob();
var b2 = bob2();

View File

@ -0,0 +1,11 @@
attr bob::z
def bob::bob() { }
var x = bob();
x.z = 10;
var y = clone(x);
y.z = 20;
assert_equal(10, x.z)
assert_equal(20, y.z)

View File

@ -0,0 +1,10 @@
attr bob::val
def bob::bob(x) : x < 10 { this.val = "Less Than Ten: " + x.to_string(); }
def bob::bob(x) { this.val = "Any Other Value: " + x.to_string(); }
var b = bob(12)
var c = bob(3)
assert_equal("Any Other Value: 12", b.val )
assert_equal("Less Than Ten: 3", c.val )

Some files were not shown because too many files have changed in this diff Show More