let string_of_error ex =
        match ex with
        | InternalError msg -> "INT-00 internal error, interpreter is in inconsistent state: "^msg
        | LibraryError msg -> "LIB-00 library error: "^msg
        | LexerException (msg, line, col) -> "PRS-00 parsing error: " ^ msg ^ " at line " ^
                        (string_of_int line) ^ " column " ^ (string_of_int col)
        | ParseException msg -> "PRS-01 parsing error: " ^ msg
        | EIncompatibleTypes(type1, type2) -> "EXP-00 incompatible types " ^ type1 ^ " and " ^ type2
        | EInvalidCast(type1, type2) ->"EXP-01 cannot cast a " ^ type1 ^ " to a " ^ type2
        | EInvalidOperation(operator, type1) -> "EXP-02 invalid operation " ^ operator ^ " for " ^ type1 ^ "s"
        | EInvalidComparaison(operator, type1, type2) -> "EXP-03 invalid comparaison " ^ operator ^ " for " ^
                        type1 ^ " and " ^ type2
        | ELeftSideIsNotAMap (typename, value) -> "EXP-04 left side of member expression is not a map or array, but a " ^
                        typename ^ " with value " ^ value
        | ELeftSideCannotBeAssigned -> "EXP-05 left side of assignment expression cannot be assigned"
        | EInvalidMember (typename, value) -> "EXP-06 member expression did not evaluate to a string or integer, but to a " ^
                        typename ^ " with value " ^ value
        | EUndefinedMapMember(name) -> "EXP-07 member expression " ^ name ^ " is undefined"
        | EInvalidArrayIndex(typename, value) -> "EXP-08 invalid array index of type " ^ typename ^ " with value " ^ value
        | EArrayIndexOutOfBounds(value) -> "EXP-09 array index out of bounds: " ^ value
        | ETypeMismatchInAssignment(name, shouldbe, is) -> "EXP-10 type mismatch in assignment of " ^ name ^
                        " declared as " ^ shouldbe ^ ", attempting to assign "^is
        | EMismatchedFunctionArgs(expected, actual) -> "EXP-11 wrong number of arguments in function call, expected " ^
                        (string_of_int expected) ^ ", got " ^ (string_of_int actual)
        | ENotAFunction -> "EXP-12 invalid function call on a non-function variable"
        | ENotACollectionType (msg, typename) -> "EXP-13 expected a collection type for " ^ msg ^ ", but got a " ^
                        typename
        | Division_by_zero -> "EXP-14 Division by zero"
        | EDefaultCaseShouldBeLast -> "STM-00 the default case in a switch statement should be the last case"
        | CFReturn _ -> "STM-01 unexpected return statement outside of a function definition"
        | CFBreak -> "STM-02 unexpected break statement outside of a loop"
        | CFContinue -> "STM-03 unexpected continue statement outside of a loop"
        | CFUserException (_, value) -> "USR-00 unhandled user exception " ^ value
        | Parsing.Parse_error -> ""
        | e -> "uncaught exception "^(Printexc.to_string e)