2164 lines
		
	
	
		
			59 KiB
		
	
	
	
		
			C++
		
	
	
	
	
	
			
		
		
	
	
			2164 lines
		
	
	
		
			59 KiB
		
	
	
	
		
			C++
		
	
	
	
	
	
/*
 | 
						|
 * $Id$
 | 
						|
 *
 | 
						|
    Copyright (c) 2006-2020 Chung, Hyung-Hwan. All rights reserved.
 | 
						|
 | 
						|
    Redistribution and use in source and binary forms, with or without
 | 
						|
    modification, are permitted provided that the following conditions
 | 
						|
    are met:
 | 
						|
    1. Redistributions of source code must retain the above copyright
 | 
						|
       notice, this list of conditions and the following disclaimer.
 | 
						|
    2. Redistributions in binary form must reproduce the above copyright
 | 
						|
       notice, this list of conditions and the following disclaimer in the
 | 
						|
       documentation and/or other materials provided with the distribution.
 | 
						|
 | 
						|
    THIS SOFTWARE IS PROVIDED BY THE AUTHOR "AS IS" AND ANY EXPRESS OR
 | 
						|
    IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
 | 
						|
    OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
 | 
						|
    IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
 | 
						|
    INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
 | 
						|
    NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
 | 
						|
    DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
 | 
						|
    THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 | 
						|
    (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
 | 
						|
    THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 | 
						|
 */
 | 
						|
 | 
						|
#ifndef _HAWK_HAWK_HPP_
 | 
						|
#define _HAWK_HAWK_HPP_
 | 
						|
 | 
						|
#include <hawk.h>
 | 
						|
 | 
						|
#define HAWK_USE_HTB_FOR_FUNCTION_MAP 1
 | 
						|
//#define HAWK_VALUE_USE_IN_CLASS_PLACEMENT_NEW 1
 | 
						|
//#define HAWK_NO_LOCATION_IN_EXCEPTION 1
 | 
						|
 | 
						|
// TOOD: redefine these NAMESPACE stuffs or move them somewhere else
 | 
						|
#define HAWK_BEGIN_NAMESPACE(x) namespace x {
 | 
						|
#define HAWK_END_NAMESPACE(x) }
 | 
						|
 | 
						|
#if defined(HAWK_USE_HTB_FOR_FUNCTION_MAP)
 | 
						|
#	include <hawk-htb.h>
 | 
						|
#else
 | 
						|
// this part not supported for now
 | 
						|
#	include <hawk/HashTable.hpp>
 | 
						|
#	include <hawk/Cstr.hpp>
 | 
						|
#endif
 | 
						|
 | 
						|
/// \file
 | 
						|
/// Hawk Interpreter
 | 
						|
 | 
						|
/////////////////////////////////
 | 
						|
HAWK_BEGIN_NAMESPACE(HAWK)
 | 
						|
/////////////////////////////////
 | 
						|
 | 
						|
#if (__cplusplus >= 201103L) || (defined(_MSC_VER) && _MSC_VER >= 1900) // C++11 or later
 | 
						|
	#define HAWK_LANG_CXX11 1
 | 
						|
	#define HAWK_CXX_NOEXCEPT noexcept(true)
 | 
						|
 | 
						|
	/// The HAWK_CXX_ENABLE_CXX11_MOVE macro enables C++11 move semantics in various classes.
 | 
						|
	#define HAWK_CXX_ENABLE_CXX11_MOVE 1
 | 
						|
 | 
						|
	// The HAWK_CXX_CALL_DESTRUCTOR() macro calls a destructor explicitly.
 | 
						|
	#define HAWK_CXX_CALL_DESTRUCTOR(ptr, class_name) ((ptr)->~class_name())
 | 
						|
 | 
						|
	// The HAWK_CXX_CALL_PLACEMENT_DELETE1() macro calls the global operator delete
 | 
						|
	// with 1 extra argument given.
 | 
						|
	#define HAWK_CXX_CALL_PLACEMENT_DELETE1(ptr, arg1) (::operator delete((ptr), (arg1)))
 | 
						|
 | 
						|
#elif (__cplusplus >= 199711L) // C++98
 | 
						|
	#undef HAWK_LANG_CXX11
 | 
						|
	#define HAWK_CXX_NOEXCEPT throw()
 | 
						|
 | 
						|
	#define HAWK_CXX_CALL_DESTRUCTOR(ptr, class_name) ((ptr)->~class_name())
 | 
						|
	#define HAWK_CXX_CALL_PLACEMENT_DELETE1(ptr, arg1) (::operator delete((ptr), (arg1)))
 | 
						|
#else
 | 
						|
	#undef HAWK_LANG_CXX11
 | 
						|
	#define HAWK_CXX_NOEXCEPT
 | 
						|
 | 
						|
	#if defined(__BORLANDC__)
 | 
						|
 | 
						|
		// Explicit destructor call requires a class name depending on the
 | 
						|
		// C++ standard/compiler.
 | 
						|
		//
 | 
						|
		//   Node* x;
 | 
						|
		//   x->~Node ();
 | 
						|
		//
 | 
						|
		// While x->~Node() is ok with modern compilers, some old compilers
 | 
						|
		// like BCC55 required the class name in the call as shown below.
 | 
						|
		//
 | 
						|
		//   x->Node::~Node ();
 | 
						|
 | 
						|
		#define HAWK_CXX_CALL_DESTRUCTOR(ptr, class_name) ((ptr)->class_name::~class_name())
 | 
						|
		#define HAWK_CXX_CALL_PLACEMENT_DELETE1(ptr, arg1) (::operator delete((ptr), (arg1)))
 | 
						|
 | 
						|
 | 
						|
	#elif defined(__WATCOMC__)
 | 
						|
		// WATCOM has a problem with this syntax.
 | 
						|
		//    Node* x; x->Node::~Node().
 | 
						|
		// But it doesn't support operator delete overloading.
 | 
						|
 | 
						|
		#define HAWK_CXX_CALL_DESTRUCTOR(ptr, class_name) ((ptr)->~class_name())
 | 
						|
		#define HAWK_CXX_CALL_PLACEMENT_DELETE1(ptr, arg1) (::hawk_operator_delete((ptr), (arg1)))
 | 
						|
 | 
						|
		// When  the name of a member template specialization appears after .  or
 | 
						|
		// -> in a postfix-expression, or after :: in a qualified-id that explic-
 | 
						|
		// itly  depends on a template-argument (_temp.dep_), the member template
 | 
						|
		// name must be prefixed by the keyword template.  Otherwise the name  is
 | 
						|
		// assumed to name a non-template.  [Example:
 | 
						|
		// 		class X {
 | 
						|
		// 		public:
 | 
						|
		// 			   template<size_t> X* alloc();
 | 
						|
		// 		};
 | 
						|
		// 		void f(X* p)
 | 
						|
		// 		{
 | 
						|
		// 			   X* p1 = p->alloc<200>();
 | 
						|
		// 					 // ill-formed: < means less than
 | 
						|
		// 			   X* p2 = p->template alloc<200>();
 | 
						|
		// 					 // fine: < starts explicit qualification
 | 
						|
		// 		}
 | 
						|
		// --end example]
 | 
						|
		//
 | 
						|
		// WATCOM doesn't support this qualifier.
 | 
						|
 | 
						|
		#define HAWK_CXX_NO_OPERATOR_DELETE_OVERLOADING 1
 | 
						|
	#else
 | 
						|
 | 
						|
		#define HAWK_CXX_CALL_DESTRUCTOR(ptr, class_name) ((ptr)->~class_name())
 | 
						|
		#define HAWK_CXX_CALL_PLACEMENT_DELETE1(ptr, arg1) (::operator delete((ptr), (arg1)))
 | 
						|
 | 
						|
	#endif
 | 
						|
 | 
						|
#endif
 | 
						|
 | 
						|
#if defined(HAWK_CXX_ENABLE_CXX11_MOVE)
 | 
						|
 | 
						|
	template<typename T> struct HAWK_CXX_RMREF      { typedef T Type; };
 | 
						|
	template<typename T> struct HAWK_CXX_RMREF<T&>  { typedef T Type; };
 | 
						|
	template<typename T> struct HAWK_CXX_RMREF<T&&> { typedef T Type; };
 | 
						|
 | 
						|
	template<typename T> inline
 | 
						|
	typename HAWK_CXX_RMREF<T>::Type&& HAWK_CXX_RVREF(T&& v)
 | 
						|
	{
 | 
						|
		return (typename HAWK_CXX_RMREF<T>::Type&&)v;
 | 
						|
	}
 | 
						|
#else
 | 
						|
 | 
						|
	/*
 | 
						|
	template<typename T> inline
 | 
						|
	T& HAWK_CXX_RVREF(T& v) { return (T&)v; }
 | 
						|
 | 
						|
	template<typename T> inline
 | 
						|
	const T& HAWK_CXX_RVREF(const T& v) { return (const T&)v; }
 | 
						|
	*/
 | 
						|
	#define HAWK_CXX_RVREF(x) x
 | 
						|
#endif
 | 
						|
 | 
						|
/// The Exception class implements the exception object.
 | 
						|
class HAWK_EXPORT Exception
 | 
						|
{
 | 
						|
public:
 | 
						|
	Exception (
 | 
						|
		const hawk_ooch_t* name, const hawk_ooch_t* msg,
 | 
						|
		const hawk_ooch_t* file, hawk_oow_t line) HAWK_CXX_NOEXCEPT:
 | 
						|
		name(name), msg(msg)
 | 
						|
#if !defined(HAWK_NO_LOCATION_IN_EXCEPTION)
 | 
						|
		, file(file), line(line)
 | 
						|
#endif
 | 
						|
	{
 | 
						|
	}
 | 
						|
 | 
						|
	const hawk_ooch_t* name;
 | 
						|
	const hawk_ooch_t* msg;
 | 
						|
#if !defined(HAWK_NO_LOCATION_IN_EXCEPTION)
 | 
						|
	const hawk_ooch_t* file;
 | 
						|
	hawk_oow_t        line;
 | 
						|
#endif
 | 
						|
};
 | 
						|
 | 
						|
#define HAWK_THROW(ex_name) \
 | 
						|
	throw ex_name(HAWK_Q(ex_name),HAWK_Q(ex_name), HAWK_T(__FILE__), (hawk_oow_t)__LINE__)
 | 
						|
#define HAWK_THROW_WITH_MSG(ex_name,msg) \
 | 
						|
	throw ex_name(HAWK_Q(ex_name),msg, HAWK_T(__FILE__), (hawk_oow_t)__LINE__)
 | 
						|
 | 
						|
#define HAWK_EXCEPTION(ex_name) \
 | 
						|
	class ex_name: public HAWK::Exception \
 | 
						|
	{ \
 | 
						|
	public: \
 | 
						|
		ex_name (const hawk_ooch_t* name, const hawk_ooch_t* msg, \
 | 
						|
		         const hawk_ooch_t* file, hawk_oow_t line) HAWK_CXX_NOEXCEPT: \
 | 
						|
			HAWK::Exception (name, msg, file, line) {} \
 | 
						|
	}
 | 
						|
 | 
						|
#define HAWK_EXCEPTION_NAME(exception_object) ((exception_object).name)
 | 
						|
#define HAWK_EXCEPTION_MSG(exception_object)  ((exception_object).msg)
 | 
						|
 | 
						|
#if !defined(HAWK_NO_LOCATION_IN_EXCEPTION)
 | 
						|
#	define HAWK_EXCEPTION_FILE(exception_object) ((exception_object).file)
 | 
						|
#	define HAWK_EXCEPTION_LINE(exception_object) ((exception_object).line)
 | 
						|
#else
 | 
						|
#	define HAWK_EXCEPTION_FILE(exception_object) (HAWK_T(""))
 | 
						|
#	define HAWK_EXCEPTION_LINE(exception_object) (0)
 | 
						|
#endif
 | 
						|
 | 
						|
class HAWK_EXPORT Uncopyable
 | 
						|
{
 | 
						|
public:
 | 
						|
	Uncopyable () HAWK_CXX_NOEXCEPT {}
 | 
						|
	//virtual ~Uncopyable () {}
 | 
						|
 | 
						|
private:
 | 
						|
	Uncopyable (const Uncopyable&);
 | 
						|
	const Uncopyable& operator= (const Uncopyable&);
 | 
						|
};
 | 
						|
 | 
						|
///
 | 
						|
/// The Mmgr class defines a memory manager interface that can be inherited
 | 
						|
/// by a class in need of a memory manager as defined in the primitive
 | 
						|
/// #hawk_mmgr_t type. Using the class over the primitive type enables you to
 | 
						|
/// write code in more object-oriented fashion. An inheriting class should
 | 
						|
/// implement three pure virtual functions.
 | 
						|
///
 | 
						|
/// You are free to call allocMem(), reallocMem(), and freeMem() in C++ context
 | 
						|
/// where no exception raising is desired. If you want an exception to be
 | 
						|
/// raised upon memory allocation errors, you can call allocate(), reallocate(),
 | 
						|
/// dispose() instead.
 | 
						|
///
 | 
						|
///
 | 
						|
class HAWK_EXPORT Mmgr: public hawk_mmgr_t
 | 
						|
{
 | 
						|
public:
 | 
						|
	/// defines an alias type to #hawk_mmgr_t
 | 
						|
	typedef hawk_mmgr_t mmgr_t;
 | 
						|
 | 
						|
	HAWK_EXCEPTION (MemoryError);
 | 
						|
 | 
						|
public:
 | 
						|
	///
 | 
						|
	/// The Mmgr() function builds a memory manager composed of bridge
 | 
						|
	/// functions connecting itself with it.
 | 
						|
	///
 | 
						|
	Mmgr () HAWK_CXX_NOEXCEPT
 | 
						|
	{
 | 
						|
		// NOTE:
 | 
						|
		//  the #hawk_mmgr_t interface is not affected by raise_exception
 | 
						|
		//  because direct calls to the virtual functions that don't raise
 | 
						|
		//  exceptions are made via bridge functions below.
 | 
						|
		this->alloc = alloc_mem;
 | 
						|
		this->realloc = realloc_mem;
 | 
						|
		this->free = free_mem;
 | 
						|
		this->ctx = this;
 | 
						|
	}
 | 
						|
 | 
						|
	///
 | 
						|
	/// The ~Mmgr() function finalizes a memory manager.
 | 
						|
	///
 | 
						|
	virtual ~Mmgr () HAWK_CXX_NOEXCEPT {}
 | 
						|
 | 
						|
	///
 | 
						|
	/// The allocate() function calls allocMem() for memory
 | 
						|
	/// allocation. if it fails, it raise an exception if it's
 | 
						|
	/// configured to do so.
 | 
						|
	///
 | 
						|
	void* allocate (hawk_oow_t n, bool raise_exception = true)
 | 
						|
	{
 | 
						|
		void* xptr = this->allocMem (n);
 | 
						|
		if (!xptr && raise_exception) HAWK_THROW (MemoryError);
 | 
						|
		return xptr;
 | 
						|
	}
 | 
						|
 | 
						|
	///
 | 
						|
	/// The callocate() function allocates memory like allocate() and
 | 
						|
	/// clears the memory before returning.
 | 
						|
	///
 | 
						|
	void* callocate (hawk_oow_t n, bool raise_exception = true);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The reallocate() function calls reallocMem() for memory
 | 
						|
	/// reallocation. if it fails, it raise an exception if it's
 | 
						|
	/// configured to do so.
 | 
						|
	///
 | 
						|
	void* reallocate (void* ptr, hawk_oow_t n, bool raise_exception = true)
 | 
						|
	{
 | 
						|
		void* xptr = this->reallocMem (ptr, n);
 | 
						|
		if (!xptr && raise_exception) HAWK_THROW (MemoryError);
 | 
						|
		return xptr;
 | 
						|
	}
 | 
						|
 | 
						|
	///
 | 
						|
	/// The dispose() function calls freeMem() for memory disposal.
 | 
						|
	///
 | 
						|
	void dispose (void* ptr) HAWK_CXX_NOEXCEPT
 | 
						|
	{
 | 
						|
		this->freeMem (ptr);
 | 
						|
	}
 | 
						|
 | 
						|
//protected:
 | 
						|
	///
 | 
						|
	/// The allocMem() function allocates a chunk of memory of the
 | 
						|
	/// size \a n and return the pointer to the beginning of the chunk.
 | 
						|
	/// If it fails to allocate memory, it should return #HAWK_NULL.
 | 
						|
	///
 | 
						|
	virtual void* allocMem (
 | 
						|
		hawk_oow_t n ///< size of memory chunk to allocate in bytes
 | 
						|
	) HAWK_CXX_NOEXCEPT = 0;
 | 
						|
 | 
						|
	///
 | 
						|
	/// The reallocMem() function resizes a chunk of memory previously
 | 
						|
	/// allocated with the allocMem() function. When resized, the contents
 | 
						|
	/// of the surviving part of a memory chunk is preserved. If it fails to
 | 
						|
	/// resize memory, it should return HAWK_NULL.
 | 
						|
	///
 | 
						|
	virtual void* reallocMem (
 | 
						|
		void* ptr, ///< pointer to memory chunk to resize
 | 
						|
		hawk_oow_t n   ///< new size in bytes
 | 
						|
	) HAWK_CXX_NOEXCEPT = 0;
 | 
						|
 | 
						|
	///
 | 
						|
	/// The freeMem() function frees a chunk of memory allocated with
 | 
						|
	/// the allocMem() function or resized with the reallocMem() function.
 | 
						|
	///
 | 
						|
	virtual void freeMem (
 | 
						|
		void* ptr ///< pointer to memory chunk to free
 | 
						|
	) HAWK_CXX_NOEXCEPT = 0;
 | 
						|
 | 
						|
protected:
 | 
						|
	///
 | 
						|
	/// bridge function from the #hawk_mmgr_t type the allocMem() function.
 | 
						|
	///
 | 
						|
	static void* alloc_mem (mmgr_t* mmgr, hawk_oow_t n) HAWK_CXX_NOEXCEPT;
 | 
						|
 | 
						|
	///
 | 
						|
	/// bridge function from the #hawk_mmgr_t type the reallocMem() function.
 | 
						|
	///
 | 
						|
	static void* realloc_mem (mmgr_t* mmgr, void* ptr, hawk_oow_t n) HAWK_CXX_NOEXCEPT;
 | 
						|
 | 
						|
	///
 | 
						|
	/// bridge function from the #hawk_mmgr_t type the freeMem() function.
 | 
						|
	///
 | 
						|
	static void  free_mem (mmgr_t* mmgr, void* ptr) HAWK_CXX_NOEXCEPT;
 | 
						|
 | 
						|
public:
 | 
						|
	static Mmgr* getDFL () HAWK_CXX_NOEXCEPT;
 | 
						|
	static void setDFL (Mmgr* mmgr) HAWK_CXX_NOEXCEPT;
 | 
						|
 | 
						|
protected:
 | 
						|
	static Mmgr* dfl_mmgr;
 | 
						|
};
 | 
						|
 | 
						|
 | 
						|
class HAWK_EXPORT Mmged
 | 
						|
{
 | 
						|
public:
 | 
						|
	Mmged (Mmgr* mmgr = HAWK_NULL);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The getMmgr() function returns the memory manager associated.
 | 
						|
	///
 | 
						|
	Mmgr* getMmgr () const { return this->_mmgr; }
 | 
						|
 | 
						|
protected:
 | 
						|
	///
 | 
						|
	/// The setMmgr() function changes the memory manager.
 | 
						|
	/// Changing memory manager requires extra care to be taken
 | 
						|
	/// especially when you have some data allocated with the previous
 | 
						|
	/// manager. for this reason, i put this as a protected function.
 | 
						|
	///
 | 
						|
	void setMmgr(Mmgr* mmgr);
 | 
						|
 | 
						|
private:
 | 
						|
	Mmgr* _mmgr;
 | 
						|
};
 | 
						|
 | 
						|
///
 | 
						|
/// The Hawk class implements an AWK interpreter by wrapping around
 | 
						|
/// #hhawk_t and #hawk_rtx_t.
 | 
						|
///
 | 
						|
class HAWK_EXPORT Hawk: public Uncopyable, public Mmged
 | 
						|
{
 | 
						|
public:
 | 
						|
 | 
						|
	enum depth_t
 | 
						|
	{
 | 
						|
		DEPTH_INCLUDE     = HAWK_OPT_DEPTH_INCLUDE,
 | 
						|
		DEPTH_BLOCK_PARSE = HAWK_OPT_DEPTH_BLOCK_PARSE,
 | 
						|
		DEPTH_BLOCK_RUN   = HAWK_OPT_DEPTH_BLOCK_RUN,
 | 
						|
		DEPTH_EXPR_PARSE  = HAWK_OPT_DEPTH_EXPR_PARSE,
 | 
						|
		DEPTH_EXPR_RUN    = HAWK_OPT_DEPTH_EXPR_RUN,
 | 
						|
		DEPTH_REX_BUILD   = HAWK_OPT_DEPTH_REX_BUILD,
 | 
						|
		DEPTH_REX_MATCH   = HAWK_OPT_DEPTH_REX_MATCH
 | 
						|
	};
 | 
						|
 | 
						|
	class Run;
 | 
						|
	friend class Run;
 | 
						|
 | 
						|
 | 
						|
protected:
 | 
						|
	///
 | 
						|
	/// \name Error Handling
 | 
						|
	///
 | 
						|
	/// \{
 | 
						|
 | 
						|
	///
 | 
						|
	/// The getErrorString() function returns a formatting string
 | 
						|
	/// for an error code \a num. You can override this function
 | 
						|
	/// to customize an error message. You must include the same numbers
 | 
						|
	/// of ${X}'s as the orginal formatting string. Their order may be
 | 
						|
	/// different. The example below changes the formatting string for
 | 
						|
	/// #HAWK_ENOENT.
 | 
						|
	/// \code
 | 
						|
	/// const hawk_ooch_t* MyHawk::getErrorString (hawk_errnum_t num) const
 | 
						|
	/// {
 | 
						|
	///    if (num == HAWK_ENOENT) return HAWK_T("cannot find '${0}'");
 | 
						|
	///    return Hawk::getErrorString(num);
 | 
						|
	/// }
 | 
						|
	/// \endcode
 | 
						|
	///
 | 
						|
	virtual const hawk_ooch_t* getErrorString (
 | 
						|
		hawk_errnum_t num
 | 
						|
	) const;
 | 
						|
 | 
						|
public:
 | 
						|
	///
 | 
						|
	/// The getErrorNumber() function returns the number of the last
 | 
						|
	/// error occurred.
 | 
						|
	///
 | 
						|
	hawk_errnum_t getErrorNumber () const;
 | 
						|
 | 
						|
	///
 | 
						|
	/// The getErrorLocation() function returns the location of the
 | 
						|
	/// last error occurred.
 | 
						|
	///
 | 
						|
	hawk_loc_t getErrorLocation () const;
 | 
						|
	const hawk_ooch_t* getErrorLocationFile () const;
 | 
						|
	const hawk_uch_t* getErrorLocationFileU () const;
 | 
						|
	const hawk_bch_t* getErrorLocationFileB () const;
 | 
						|
 | 
						|
	///
 | 
						|
	/// The Hawk::getErrorMessage() function returns a message describing
 | 
						|
	/// the last error occurred.
 | 
						|
	///
 | 
						|
	const hawk_ooch_t* getErrorMessage () const;
 | 
						|
	const hawk_uch_t* getErrorMessageU () const;
 | 
						|
	const hawk_bch_t* getErrorMessageB () const;
 | 
						|
 | 
						|
	void setError (
 | 
						|
		hawk_errnum_t       code, ///< error code
 | 
						|
		const hawk_loc_t*   loc   = HAWK_NULL  ///< error location
 | 
						|
	);
 | 
						|
 | 
						|
	void formatError (
 | 
						|
		hawk_errnum_t       code,
 | 
						|
		const hawk_loc_t*   loc,
 | 
						|
		const hawk_bch_t*   fmt,
 | 
						|
		...
 | 
						|
	);
 | 
						|
 | 
						|
	void formatError (
 | 
						|
		hawk_errnum_t       code,
 | 
						|
		const hawk_loc_t*   loc,
 | 
						|
		const hawk_uch_t*   fmt,
 | 
						|
		...
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The clearError() function clears error information
 | 
						|
	///
 | 
						|
	void clearError ();
 | 
						|
 | 
						|
//protected: can't make it protected for borland
 | 
						|
	void retrieveError ();
 | 
						|
	void retrieveError (Run* run);
 | 
						|
	/// \}
 | 
						|
 | 
						|
protected:
 | 
						|
	class NoSource;
 | 
						|
 | 
						|
public:
 | 
						|
	///
 | 
						|
	/// The Source class is an abstract class to encapsulate
 | 
						|
	/// source script I/O. The Hawk::parse function requires a concrete
 | 
						|
	/// object instantiated from its child class.
 | 
						|
	///
 | 
						|
	class HAWK_EXPORT Source
 | 
						|
	{
 | 
						|
	public:
 | 
						|
		///
 | 
						|
		/// The Mode type defines opening mode.
 | 
						|
		///
 | 
						|
		enum Mode
 | 
						|
		{
 | 
						|
			READ,   ///< open for read
 | 
						|
			WRITE   ///< open for write
 | 
						|
		};
 | 
						|
 | 
						|
		///
 | 
						|
		/// The Data class encapsulates information passed in and out
 | 
						|
		/// for source script I/O.
 | 
						|
		///
 | 
						|
		class HAWK_EXPORT Data
 | 
						|
		{
 | 
						|
		public:
 | 
						|
			friend class Hawk;
 | 
						|
 | 
						|
		protected:
 | 
						|
			Data (Hawk* hawk, Mode mode, hawk_sio_arg_t* arg):
 | 
						|
				hawk(hawk), mode(mode), arg(arg)
 | 
						|
			{
 | 
						|
			}
 | 
						|
 | 
						|
		public:
 | 
						|
			Mode getMode() const
 | 
						|
			{
 | 
						|
				return this->mode;
 | 
						|
			}
 | 
						|
 | 
						|
			bool isMaster() const
 | 
						|
			{
 | 
						|
				return this->arg->prev == HAWK_NULL;
 | 
						|
			}
 | 
						|
 | 
						|
			const hawk_ooch_t* getName() const
 | 
						|
			{
 | 
						|
				return this->arg->name;
 | 
						|
			}
 | 
						|
 | 
						|
			// since it doesn't copy the contents,
 | 
						|
			// it should point to something that outlives this object.
 | 
						|
			void setName (const hawk_ooch_t* name)
 | 
						|
			{
 | 
						|
				this->arg->name = name;
 | 
						|
			}
 | 
						|
 | 
						|
			const hawk_ooch_t* getPath() const
 | 
						|
			{
 | 
						|
				return this->arg->path;
 | 
						|
			}
 | 
						|
 | 
						|
			void setPath (const hawk_ooch_t* path)
 | 
						|
			{
 | 
						|
				this->arg->path = (hawk_ooch_t*)path;
 | 
						|
			}
 | 
						|
 | 
						|
			const hawk_ooch_t* getPrevName() const
 | 
						|
			{
 | 
						|
				return this->arg->prev->name;
 | 
						|
			}
 | 
						|
 | 
						|
			const void* getPrevHandle() const
 | 
						|
			{
 | 
						|
				return this->arg->prev->handle;
 | 
						|
			}
 | 
						|
 | 
						|
			void* getHandle () const
 | 
						|
			{
 | 
						|
				return this->arg->handle;
 | 
						|
			}
 | 
						|
 | 
						|
			void setHandle (void* handle)
 | 
						|
			{
 | 
						|
				this->arg->handle = handle;
 | 
						|
			}
 | 
						|
 | 
						|
			operator Hawk* () const
 | 
						|
			{
 | 
						|
				return this->hawk;
 | 
						|
			}
 | 
						|
 | 
						|
			operator hawk_t* () const
 | 
						|
			{
 | 
						|
				return this->hawk->getHandle();
 | 
						|
			}
 | 
						|
 | 
						|
		protected:
 | 
						|
			Hawk* hawk;
 | 
						|
			Mode  mode;
 | 
						|
			hawk_sio_arg_t* arg;
 | 
						|
		};
 | 
						|
 | 
						|
		Source () {}
 | 
						|
		virtual ~Source () {}
 | 
						|
 | 
						|
		virtual int open (Data& io) = 0;
 | 
						|
		virtual int close (Data& io) = 0;
 | 
						|
		virtual hawk_ooi_t read (Data& io, hawk_ooch_t* buf, hawk_oow_t len) = 0;
 | 
						|
		virtual hawk_ooi_t write (Data& io, const hawk_ooch_t* buf, hawk_oow_t len) = 0;
 | 
						|
 | 
						|
		///
 | 
						|
		/// The NONE object indicates no source.
 | 
						|
		///
 | 
						|
		static NoSource NONE;
 | 
						|
 | 
						|
	private:
 | 
						|
		Source (const Source&);
 | 
						|
		Source& operator= (const Source&);
 | 
						|
	};
 | 
						|
 | 
						|
protected:
 | 
						|
	class HAWK_EXPORT NoSource: public Source
 | 
						|
	{
 | 
						|
	public:
 | 
						|
		int open (Data& io) { return -1; }
 | 
						|
		int close (Data& io) { return 0; }
 | 
						|
		hawk_ooi_t read (Data& io, hawk_ooch_t* buf, hawk_oow_t len) { return 0; }
 | 
						|
		hawk_ooi_t write (Data& io, const hawk_ooch_t* buf, hawk_oow_t len) { return 0; }
 | 
						|
	};
 | 
						|
 | 
						|
public:
 | 
						|
	///
 | 
						|
	/// The RIOBase class is a base class to represent runtime I/O
 | 
						|
	/// operations. The Console, File, Pipe classes implement more specific
 | 
						|
	/// I/O operations by inheriting this class.
 | 
						|
	///
 | 
						|
	class HAWK_EXPORT RIOBase
 | 
						|
	{
 | 
						|
	protected:
 | 
						|
		RIOBase (Run* run, hawk_rio_arg_t* riod): run(run), riod(riod) {}
 | 
						|
 | 
						|
	public:
 | 
						|
		const hawk_ooch_t* getName() const { return this->riod->name; }
 | 
						|
 | 
						|
		const void* getHandle () const { return this->riod->handle; }
 | 
						|
		void setHandle (void* handle) { this->riod->handle = handle; }
 | 
						|
 | 
						|
		hawk_uint16_t getUflags () const { return this->riod->uflags; }
 | 
						|
		void setUflags (hawk_uint16_t uflags) { this->riod->uflags = uflags; }
 | 
						|
 | 
						|
		operator Hawk* () const { return this->run->hawk; }
 | 
						|
		operator hawk_t* () const
 | 
						|
		{
 | 
						|
			HAWK_ASSERT (hawk_rtx_gethawk(this->run->rtx) == this->run->hawk->getHandle());
 | 
						|
			return this->run->hawk->getHandle();
 | 
						|
		}
 | 
						|
		operator hawk_rio_arg_t* () const { return this->riod; }
 | 
						|
		operator Run* () const { return this->run; }
 | 
						|
		operator hawk_rtx_t* () const { return this->run->rtx; }
 | 
						|
		operator hawk_gem_t* () const { return hawk_rtx_getgem(this->run->rtx); }
 | 
						|
 | 
						|
	protected:
 | 
						|
		Run* run;
 | 
						|
		hawk_rio_arg_t* riod;
 | 
						|
 | 
						|
	private:
 | 
						|
		RIOBase (const RIOBase&);
 | 
						|
		RIOBase& operator= (const RIOBase&);
 | 
						|
	};
 | 
						|
 | 
						|
	///
 | 
						|
	/// The Pipe class encapsulates the pipe operations indicated by
 | 
						|
	/// the | and || operators.
 | 
						|
	///
 | 
						|
	class HAWK_EXPORT Pipe: public RIOBase
 | 
						|
	{
 | 
						|
	public:
 | 
						|
		friend class Hawk;
 | 
						|
 | 
						|
		/// The Mode type defines the opening mode.
 | 
						|
		enum Mode
 | 
						|
		{
 | 
						|
			/// open for read-only access
 | 
						|
			READ = HAWK_RIO_PIPE_READ,
 | 
						|
			/// open for write-only access
 | 
						|
			WRITE = HAWK_RIO_PIPE_WRITE,
 | 
						|
			/// open for read and write
 | 
						|
			RW = HAWK_RIO_PIPE_RW
 | 
						|
		};
 | 
						|
 | 
						|
		/// The CloseMode type defines the closing mode for a pipe
 | 
						|
		/// opened in the #RW mode.
 | 
						|
		enum CloseMode
 | 
						|
		{
 | 
						|
			/// close both read and write ends
 | 
						|
			CLOSE_FULL = HAWK_RIO_CMD_CLOSE_FULL,
 | 
						|
			/// close the read end only
 | 
						|
			CLOSE_READ = HAWK_RIO_CMD_CLOSE_READ,
 | 
						|
			/// close the write end only
 | 
						|
			CLOSE_WRITE = HAWK_RIO_CMD_CLOSE_WRITE
 | 
						|
		};
 | 
						|
 | 
						|
		class HAWK_EXPORT Handler
 | 
						|
		{
 | 
						|
		public:
 | 
						|
			virtual ~Handler () {}
 | 
						|
 | 
						|
			virtual int open (Pipe& io) = 0;
 | 
						|
			virtual int close (Pipe& io) = 0;
 | 
						|
			virtual hawk_ooi_t read  (Pipe& io, hawk_ooch_t* buf, hawk_oow_t len) = 0;
 | 
						|
			virtual hawk_ooi_t readBytes (Pipe& io, hawk_bch_t* buf, hawk_oow_t len) = 0;
 | 
						|
			virtual hawk_ooi_t write (Pipe& io, const hawk_ooch_t* buf, hawk_oow_t len) = 0;
 | 
						|
			virtual hawk_ooi_t writeBytes (Pipe& io, const hawk_bch_t* buf, hawk_oow_t len) = 0;
 | 
						|
			virtual int flush (Pipe& io) = 0;
 | 
						|
		};
 | 
						|
 | 
						|
	protected:
 | 
						|
		Pipe (Run* run, hawk_rio_arg_t* riod);
 | 
						|
 | 
						|
	public:
 | 
						|
		/// The getMode() function returns the opening mode requested.
 | 
						|
		/// You can inspect the opening mode, typically in the
 | 
						|
		/// openPipe() function, to create a pipe with proper
 | 
						|
		/// access mode. It is harmless to call this function from
 | 
						|
		/// other pipe handling functions.
 | 
						|
		Mode getMode () const;
 | 
						|
 | 
						|
		/// The getCloseMode() function returns the closing mode
 | 
						|
		/// requested. The returned value is valid if getMode()
 | 
						|
		/// returns #RW.
 | 
						|
		CloseMode getCloseMode () const;
 | 
						|
	};
 | 
						|
 | 
						|
	///
 | 
						|
	/// The File class encapsulates file operations by inheriting RIOBase.
 | 
						|
	///
 | 
						|
	class HAWK_EXPORT File: public RIOBase
 | 
						|
	{
 | 
						|
	public:
 | 
						|
		friend class Hawk;
 | 
						|
 | 
						|
		enum Mode
 | 
						|
		{
 | 
						|
			READ = HAWK_RIO_FILE_READ,
 | 
						|
			WRITE = HAWK_RIO_FILE_WRITE,
 | 
						|
			APPEND = HAWK_RIO_FILE_APPEND
 | 
						|
		};
 | 
						|
 | 
						|
		class HAWK_EXPORT Handler
 | 
						|
		{
 | 
						|
		public:
 | 
						|
			virtual ~Handler () {}
 | 
						|
 | 
						|
			virtual int open (File& io) = 0;
 | 
						|
			virtual int close (File& io) = 0;
 | 
						|
			virtual hawk_ooi_t read (File& io, hawk_ooch_t* buf, hawk_oow_t len) = 0;
 | 
						|
			virtual hawk_ooi_t readBytes (File& io, hawk_bch_t* buf, hawk_oow_t len) = 0;
 | 
						|
			virtual hawk_ooi_t write (File& io, const hawk_ooch_t* buf, hawk_oow_t len) = 0;
 | 
						|
			virtual hawk_ooi_t writeBytes (File& io, const hawk_bch_t* buf, hawk_oow_t len) = 0;
 | 
						|
			virtual int flush (File& io) = 0;
 | 
						|
		};
 | 
						|
 | 
						|
	protected:
 | 
						|
		File (Run* run, hawk_rio_arg_t* riod);
 | 
						|
 | 
						|
	public:
 | 
						|
		Mode getMode () const;
 | 
						|
	};
 | 
						|
 | 
						|
	///
 | 
						|
	/// The Console class encapsulates the console operations by
 | 
						|
	/// inheriting RIOBase.
 | 
						|
	///
 | 
						|
	class HAWK_EXPORT Console: public RIOBase
 | 
						|
	{
 | 
						|
	public:
 | 
						|
		friend class Hawk;
 | 
						|
 | 
						|
		/// Console mode enumerators
 | 
						|
		enum Mode
 | 
						|
		{
 | 
						|
			READ = HAWK_RIO_CONSOLE_READ,  ///< open for input
 | 
						|
			WRITE = HAWK_RIO_CONSOLE_WRITE ///< open for output
 | 
						|
		};
 | 
						|
 | 
						|
		///
 | 
						|
		/// The Handler class is an abstract class that can be
 | 
						|
		/// implemented for customized I/O handling.
 | 
						|
		class HAWK_EXPORT Handler
 | 
						|
		{
 | 
						|
		public:
 | 
						|
			virtual ~Handler () {}
 | 
						|
 | 
						|
			/// The open() function is called before the initial
 | 
						|
			/// access to the console for input and output.
 | 
						|
			/// It must return 0 for success and -1 for failure.
 | 
						|
			/// Upon successful opening, it can store information
 | 
						|
			/// required using setHandle() and setUflags().
 | 
						|
			/// The information set here is available in subsequent
 | 
						|
			/// calls to other methods and are accessible with
 | 
						|
			/// getHandle() and getUflags().
 | 
						|
			virtual int open (Console& io) = 0;
 | 
						|
 | 
						|
			/// The close() function is called when the console
 | 
						|
			/// is not needed any more. It must return 0 for success
 | 
						|
			/// and -1 for failure.
 | 
						|
			virtual int close (Console& io) = 0;
 | 
						|
 | 
						|
			/// The read() function is called when the console
 | 
						|
			/// is read for input. It must fill the buffer \a buf with
 | 
						|
			/// data not more than \a len characters and return the
 | 
						|
			/// number of characters filled into the buufer. It can
 | 
						|
			/// return 0 to indicate EOF and -1 for failure.
 | 
						|
			virtual hawk_ooi_t read (Console& io, hawk_ooch_t* buf, hawk_oow_t len) = 0;
 | 
						|
 | 
						|
			virtual hawk_ooi_t readBytes (Console& io, hawk_bch_t* buf, hawk_oow_t len) = 0;
 | 
						|
 | 
						|
			/// The write() function is called when the console
 | 
						|
			/// is written for output. It can write upto \a len characters
 | 
						|
			/// available in the buffer \a buf and return the number of
 | 
						|
			/// characters written. It can return 0 to indicate EOF and -1
 | 
						|
			/// for failure.
 | 
						|
			virtual hawk_ooi_t write (Console& io, const hawk_ooch_t* buf, hawk_oow_t len) = 0;
 | 
						|
 | 
						|
			virtual hawk_ooi_t writeBytes (Console& io, const hawk_bch_t* buf, hawk_oow_t len) = 0;
 | 
						|
 | 
						|
			/// You may choose to buffer the data passed to the write()
 | 
						|
			/// function and perform actual writing when flush() is called.
 | 
						|
			/// It must return 0 for success and -1 for failure.
 | 
						|
			virtual int flush (Console& io) = 0;
 | 
						|
 | 
						|
			/// The next() function is called when \b nextfile or
 | 
						|
			/// \b nextofile is executed. It must return 0 for success
 | 
						|
			/// and -1 for failure.
 | 
						|
			virtual int next  (Console& io) = 0;
 | 
						|
		};
 | 
						|
 | 
						|
		bool getSwitched() const { return this->riod->console_switched; }
 | 
						|
		void setSwitched(bool v) { this->riod->console_switched = v; }
 | 
						|
 | 
						|
	protected:
 | 
						|
		Console (Run* run, hawk_rio_arg_t* riod);
 | 
						|
		~Console ();
 | 
						|
 | 
						|
	public:
 | 
						|
		/// The getMode() function returns if the console is
 | 
						|
		/// opened for reading or writing.
 | 
						|
		Mode getMode () const;
 | 
						|
 | 
						|
		int setFileName (const hawk_ooch_t* name);
 | 
						|
		int setFNR (hawk_int_t fnr);
 | 
						|
 | 
						|
	protected:
 | 
						|
		hawk_ooch_t* filename;
 | 
						|
	};
 | 
						|
 | 
						|
 | 
						|
	///
 | 
						|
	/// The Value class wraps around #hawk_val_t to provide a more
 | 
						|
	/// comprehensive interface.
 | 
						|
	///
 | 
						|
	/// An instance of Value must not outlive the associated run-time
 | 
						|
	/// context and its owning hawk instance. If the close() method is
 | 
						|
	/// called explicity on the owning hawk instance, you must ensure
 | 
						|
	/// that the related values are also destroyed before the call to
 | 
						|
	/// close().
 | 
						|
	///
 | 
						|
	/// The following will end up in a segmentation fault or the like.
 | 
						|
	///   HAWK::HawkStd hawk;
 | 
						|
	///   hawk.open();
 | 
						|
	///   HAWK::HawkStd::SourceString in("BEGIN{}");
 | 
						|
	///   hawk.parse(in, HAWK::Hawk::Source::NONE);
 | 
						|
	///   HAWK::Hawk::Value v(rtx);
 | 
						|
	///   v.setMbs("hello", 5);
 | 
						|
	///   hawk.close();
 | 
						|
	///
 | 
						|
	/// You don't call hawk.close() and rely on the destructor or
 | 
						|
	/// enclose 'v' in another nested scope.
 | 
						|
	///   HAWK::HawkStd hawk;
 | 
						|
	///   hawk.open();
 | 
						|
	///   HAWK::HawkStd::SourceString in("BEGIN{}");
 | 
						|
	///   hawk.parse(in, HAWK::Hawk::Source::NONE);
 | 
						|
	///   {
 | 
						|
	///       HAWK::Hawk::Value v(rtx);
 | 
						|
	///       v.setMbs("hello", 5);
 | 
						|
	///   }
 | 
						|
	///   hawk.close();
 | 
						|
	///
 | 
						|
	class HAWK_EXPORT Value
 | 
						|
	{
 | 
						|
	public:
 | 
						|
		friend class Hawk;
 | 
						|
 | 
						|
	#if defined(HAWK_VALUE_USE_IN_CLASS_PLACEMENT_NEW)
 | 
						|
		// initialization
 | 
						|
		void* operator new (hawk_oow_t n, Run* run) throw ();
 | 
						|
		void* operator new[] (hawk_oow_t n, Run* run) throw ();
 | 
						|
 | 
						|
	#if !defined(__BORLANDC__) && !defined(__WATCOMC__)
 | 
						|
		// deletion when initialization fails
 | 
						|
		void operator delete (void* p, Run* run);
 | 
						|
		void operator delete[] (void* p, Run* run);
 | 
						|
	#endif
 | 
						|
 | 
						|
		// normal deletion
 | 
						|
		void operator delete (void* p);
 | 
						|
		void operator delete[] (void* p);
 | 
						|
	#endif
 | 
						|
 | 
						|
		///
 | 
						|
		/// The Index class encapsulates an index of an arrayed value.
 | 
						|
		///
 | 
						|
		class HAWK_EXPORT Index: protected hawk_oocs_t
 | 
						|
		{
 | 
						|
		public:
 | 
						|
			friend class Value;
 | 
						|
 | 
						|
			/// The Index() function creates an empty array index.
 | 
						|
			Index ()
 | 
						|
			{
 | 
						|
				this->ptr = (hawk_ooch_t*)Value::getEmptyStr();
 | 
						|
				this->len = 0;
 | 
						|
			}
 | 
						|
 | 
						|
			/// The Index() function creates a string array index.
 | 
						|
			Index (const hawk_ooch_t* ptr, hawk_oow_t len)
 | 
						|
			{
 | 
						|
				this->ptr = (hawk_ooch_t*)ptr;
 | 
						|
				this->len = len;
 | 
						|
			}
 | 
						|
 | 
						|
			void set (const hawk_oocs_t* x)
 | 
						|
			{
 | 
						|
				this->ptr = x->ptr;
 | 
						|
				this->len = x->len;
 | 
						|
			}
 | 
						|
 | 
						|
			Index& operator= (const hawk_oocs_t* x)
 | 
						|
			{
 | 
						|
				this->set (x);
 | 
						|
				return *this;
 | 
						|
			}
 | 
						|
 | 
						|
			const hawk_ooch_t* pointer () const
 | 
						|
			{
 | 
						|
				return this->ptr;
 | 
						|
			}
 | 
						|
 | 
						|
			hawk_oow_t length () const
 | 
						|
			{
 | 
						|
				return this->len;
 | 
						|
			}
 | 
						|
		};
 | 
						|
 | 
						|
		///
 | 
						|
		/// Represents a numeric index of an arrayed value
 | 
						|
		///
 | 
						|
		class HAWK_EXPORT IntIndex: public Index
 | 
						|
		{
 | 
						|
		public:
 | 
						|
			IntIndex (hawk_int_t num);
 | 
						|
 | 
						|
		protected:
 | 
						|
			// 2^32: 4294967296
 | 
						|
			// 2^64: 18446744073709551616
 | 
						|
			// 2^128: 340282366920938463463374607431768211456
 | 
						|
			// -(2^32/2): -2147483648
 | 
						|
			// -(2^64/2): -9223372036854775808
 | 
						|
			// -(2^128/2): -170141183460469231731687303715884105728
 | 
						|
		#if HAWK_SIZEOF_LONG_T > 16
 | 
						|
		#	error SIZEOF(hawk_int_t) TOO LARGE.
 | 
						|
		#	error INCREASE THE BUFFER SIZE TO SUPPORT IT.
 | 
						|
		#elif HAWK_SIZEOF_LONG_T == 16
 | 
						|
			hawk_ooch_t buf[41];
 | 
						|
		#elif HAWK_SIZEOF_LONG_T == 8
 | 
						|
			hawk_ooch_t buf[21];
 | 
						|
		#else
 | 
						|
			hawk_ooch_t buf[12];
 | 
						|
		#endif
 | 
						|
		};
 | 
						|
 | 
						|
		///
 | 
						|
		/// The IndexIterator class is a helper class to make simple
 | 
						|
		/// iteration over array elements.
 | 
						|
		///
 | 
						|
		class HAWK_EXPORT IndexIterator: public hawk_val_map_itr_t
 | 
						|
		{
 | 
						|
		public:
 | 
						|
			friend class Value;
 | 
						|
 | 
						|
			///
 | 
						|
			/// The END variable is a special variable to
 | 
						|
			/// represent the end of iteration.
 | 
						|
			///
 | 
						|
			static IndexIterator END;
 | 
						|
 | 
						|
			///
 | 
						|
			/// The IndexIterator() function creates an iterator
 | 
						|
			/// for an arrayed value.
 | 
						|
			///
 | 
						|
			IndexIterator ()
 | 
						|
			{
 | 
						|
				hawk_init_map_itr (this, 0);
 | 
						|
			}
 | 
						|
 | 
						|
			bool operator== (const IndexIterator& ii) const
 | 
						|
			{
 | 
						|
				// the most common use of this operator is to test it against END
 | 
						|
			#if defined(HAWK_MAP_IS_HTB)
 | 
						|
				return this->pair == ii.pair && this->buckno == ii.buckno;
 | 
						|
			#else
 | 
						|
				return this->pair == ii.pair && this->_prev == ii._prev;
 | 
						|
			#endif
 | 
						|
			}
 | 
						|
 | 
						|
			bool operator!= (const IndexIterator& ii) const
 | 
						|
			{
 | 
						|
				return !this->operator==(ii);
 | 
						|
			}
 | 
						|
		};
 | 
						|
 | 
						|
		///
 | 
						|
		/// The Value() function creates an empty value associated
 | 
						|
		/// with no runtime context. To set an actual inner value,
 | 
						|
		/// you must specify a context when calling setXXX() functions.
 | 
						|
		/// i.e., use setInt(run,10) instead of setInt(10).
 | 
						|
		///
 | 
						|
		Value ();
 | 
						|
 | 
						|
		///
 | 
						|
		/// The Value() function creates an empty value associated
 | 
						|
		/// with a runtime context.
 | 
						|
		///
 | 
						|
		Value (Run& run);
 | 
						|
 | 
						|
		///
 | 
						|
		/// The Value() function creates an empty value associated
 | 
						|
		/// with a runtime context.
 | 
						|
		///
 | 
						|
		Value (Run* run);
 | 
						|
 | 
						|
		Value (const Value& v);
 | 
						|
		~Value ();
 | 
						|
 | 
						|
		Value& operator= (const Value& v);
 | 
						|
 | 
						|
		void clear ();
 | 
						|
 | 
						|
		operator hawk_val_t* () const { return this->val; }
 | 
						|
		operator hawk_int_t () const;
 | 
						|
		operator hawk_flt_t () const;
 | 
						|
		operator const hawk_ooch_t* () const;
 | 
						|
	#if defined(HAWK_OOCH_IS_UCH)
 | 
						|
		operator const hawk_bch_t* () const;
 | 
						|
	#endif
 | 
						|
 | 
						|
		hawk_val_t* toVal () const
 | 
						|
		{
 | 
						|
			return this->operator hawk_val_t* ();
 | 
						|
		}
 | 
						|
 | 
						|
		hawk_int_t toInt () const
 | 
						|
		{
 | 
						|
			return this->operator hawk_int_t ();
 | 
						|
		}
 | 
						|
 | 
						|
		hawk_flt_t toFlt () const
 | 
						|
		{
 | 
						|
			return this->operator hawk_flt_t ();
 | 
						|
		}
 | 
						|
 | 
						|
		const hawk_ooch_t* toStr (hawk_oow_t* len) const
 | 
						|
		{
 | 
						|
			const hawk_ooch_t* p;
 | 
						|
			hawk_oow_t l;
 | 
						|
 | 
						|
			if (this->getStr(&p, &l) <= -1)
 | 
						|
			{
 | 
						|
				p = this->getEmptyStr();
 | 
						|
				l = 0;
 | 
						|
			}
 | 
						|
 | 
						|
			if (len) *len = l;
 | 
						|
			return p;
 | 
						|
		}
 | 
						|
 | 
						|
		const hawk_bch_t* toMbs (hawk_oow_t* len) const
 | 
						|
		{
 | 
						|
			const hawk_bch_t* p;
 | 
						|
			hawk_oow_t l;
 | 
						|
 | 
						|
			if (this->getMbs(&p, &l) <= -1)
 | 
						|
			{
 | 
						|
				p = this->getEmptyMbs();
 | 
						|
				l = 0;
 | 
						|
			}
 | 
						|
 | 
						|
			if (len) *len = l;
 | 
						|
			return p;
 | 
						|
		}
 | 
						|
 | 
						|
		const void* toBob (hawk_oow_t* len) const
 | 
						|
		{
 | 
						|
			const void* p;
 | 
						|
			hawk_oow_t l;
 | 
						|
 | 
						|
			if (this->getBob(&p, &l) <= -1)
 | 
						|
			{
 | 
						|
				p = this->getEmptyBob();
 | 
						|
				l = 0;
 | 
						|
			}
 | 
						|
 | 
						|
			if (len) *len = l;
 | 
						|
			return p;
 | 
						|
		}
 | 
						|
 | 
						|
		int getType () const { return hawk_get_val_type(this->val); }
 | 
						|
		const hawk_ooch_t* getTypeName () const { return hawk_get_val_type_name(this->val); }
 | 
						|
 | 
						|
		int getInt (hawk_int_t* v) const;
 | 
						|
		int getFlt (hawk_flt_t* v) const;
 | 
						|
		int getNum (hawk_int_t* lv, hawk_flt_t* fv) const;
 | 
						|
		int getStr (const hawk_ooch_t** str, hawk_oow_t* len) const;
 | 
						|
		int getMbs (const hawk_bch_t** str, hawk_oow_t* len) const;
 | 
						|
		int getBob (const void** str, hawk_oow_t* len) const;
 | 
						|
 | 
						|
		int setVal (hawk_val_t* v);
 | 
						|
		int setVal (Run* r, hawk_val_t* v);
 | 
						|
 | 
						|
		int setInt (hawk_int_t v);
 | 
						|
		int setInt (Run* r, hawk_int_t v);
 | 
						|
		int setFlt (hawk_flt_t v);
 | 
						|
		int setFlt (Run* r, hawk_flt_t v);
 | 
						|
 | 
						|
		int setStr (const hawk_uch_t* str, hawk_oow_t len, bool numeric = false);
 | 
						|
		int setStr (Run* r, const hawk_uch_t* str, hawk_oow_t len, bool numeric = false);
 | 
						|
		int setStr (const hawk_uch_t* str, bool numeric = false);
 | 
						|
		int setStr (Run* r, const hawk_uch_t* str, bool numeric = false);
 | 
						|
		int setStr (const hawk_bch_t* str, hawk_oow_t len, bool numeric = false);
 | 
						|
		int setStr (Run* r, const hawk_bch_t* str, hawk_oow_t len, bool numeric = false);
 | 
						|
		int setStr (const hawk_bch_t* str, bool numeric = false);
 | 
						|
		int setStr (Run* r, const hawk_bch_t* str, bool numeric = false);
 | 
						|
 | 
						|
		int setMbs (const hawk_bch_t* str, hawk_oow_t len);
 | 
						|
		int setMbs (Run* r, const hawk_bch_t* str, hawk_oow_t len);
 | 
						|
		int setMbs (const hawk_bch_t* str);
 | 
						|
		int setMbs (Run* r, const hawk_bch_t* str);
 | 
						|
 | 
						|
		int setBob (const void* str, hawk_oow_t len);
 | 
						|
		int setBob (Run* r, const void* str, hawk_oow_t len);
 | 
						|
 | 
						|
		int setArrayedVal (hawk_ooi_t idx, hawk_val_t* v);
 | 
						|
		int setArrayedVal (Run* r, hawk_ooi_t idx, hawk_val_t* v);
 | 
						|
 | 
						|
		int scaleArrayed (hawk_ooi_t size);
 | 
						|
		int scaleArrayed (Run* r, hawk_ooi_t size);
 | 
						|
 | 
						|
		hawk_ooi_t getArrayedSize () const; // same value as hawk::size() for an array
 | 
						|
		hawk_ooi_t getArrayedLength () const; // same value as hawk::length() for an array
 | 
						|
		hawk_ooi_t getArrayedCapa () const;
 | 
						|
 | 
						|
		bool isArrayed () const;
 | 
						|
		int getArrayed (
 | 
						|
			hawk_ooi_t    idx, ///< array index
 | 
						|
			Value*        val  ///< value holder
 | 
						|
		) const;
 | 
						|
 | 
						|
		int setIndexedVal (const Index& idx, hawk_val_t* v);
 | 
						|
		int setIndexedVal (Run* r, const Index& idx, hawk_val_t* v);
 | 
						|
		int setIndexedInt (const Index& idx, hawk_int_t v);
 | 
						|
		int setIndexedInt (Run* r, const Index& idx, hawk_int_t v);
 | 
						|
		int setIndexedFlt (const Index& idx, hawk_flt_t v);
 | 
						|
		int setIndexedFlt (Run* r, const Index&  idx, hawk_flt_t v);
 | 
						|
 | 
						|
		int setIndexedStr (const Index& idx, const hawk_uch_t* str, hawk_oow_t len, bool numeric = false);
 | 
						|
		int setIndexedStr (Run* r, const Index& idx, const hawk_uch_t* str, hawk_oow_t len, bool numeric = false);
 | 
						|
		int setIndexedStr (const Index& idx, const hawk_uch_t* str, bool  numeric = false);
 | 
						|
		int setIndexedStr (Run* r, const Index&  idx, const hawk_uch_t* str, bool  numeric = false);
 | 
						|
 | 
						|
		int setIndexedStr (const Index& idx, const hawk_bch_t* str, hawk_oow_t len, bool numeric = false);
 | 
						|
		int setIndexedStr (Run* r, const Index& idx, const hawk_bch_t* str, hawk_oow_t len, bool numeric = false);
 | 
						|
		int setIndexedStr (const Index& idx, const hawk_bch_t* str, bool  numeric = false);
 | 
						|
		int setIndexedStr (Run* r, const Index&  idx, const hawk_bch_t* str, bool  numeric = false);
 | 
						|
 | 
						|
		int setIndexedMbs (const Index& idx, const hawk_bch_t* str, hawk_oow_t len);
 | 
						|
		int setIndexedMbs (Run* r, const Index& idx, const hawk_bch_t* str, hawk_oow_t len);
 | 
						|
		int setIndexedMbs (const Index& idx, const hawk_bch_t* str);
 | 
						|
		int setIndexedMbs (Run* r, const Index&  idx, const hawk_bch_t* str);
 | 
						|
 | 
						|
		hawk_ooi_t getIndexedSize () const; // same value as hawk::size() for a map
 | 
						|
		hawk_ooi_t getIndexedLength () const; // same value as hawk::length() for a map
 | 
						|
		hawk_ooi_t getIndexedCapa () const;
 | 
						|
 | 
						|
		///
 | 
						|
		/// The isIndexed() function determines if a value is a map.
 | 
						|
		/// \return true if indexed, false if not.
 | 
						|
		///
 | 
						|
		bool isIndexed () const;
 | 
						|
 | 
						|
		///
 | 
						|
		/// The getIndexed() function gets a value at the given
 | 
						|
		/// index \a idx and sets it to \a val.
 | 
						|
		/// \return 0 on success, -1 on failure
 | 
						|
		///
 | 
						|
		int getIndexed (
 | 
						|
			const Index&  idx, ///< map index
 | 
						|
			Value*        val  ///< value holder
 | 
						|
		) const;
 | 
						|
 | 
						|
		///
 | 
						|
		/// The getFirstIndex() function stores the first index of
 | 
						|
		/// an arrayed value into \a idx.
 | 
						|
		/// \return IndexIterator::END if the arrayed value is empty,
 | 
						|
		///         iterator that can be passed to getNextIndex() if not
 | 
						|
		///
 | 
						|
		IndexIterator getFirstIndex (
 | 
						|
			Index* idx ///< index holder
 | 
						|
		) const;
 | 
						|
 | 
						|
		///
 | 
						|
		/// The getNextIndex() function stores into \a idx the next
 | 
						|
		/// index of an array value from the position indicated by
 | 
						|
		/// \a iter.
 | 
						|
		/// \return IndexIterator::END if the arrayed value is empty,
 | 
						|
		///         iterator that can be passed to getNextIndex() if not
 | 
						|
		///
 | 
						|
		IndexIterator getNextIndex (
 | 
						|
			Index* idx,                 ///< index holder
 | 
						|
			const IndexIterator& curitr ///< current position
 | 
						|
		) const;
 | 
						|
 | 
						|
	protected:
 | 
						|
		Run* run;
 | 
						|
		hawk_val_t* val;
 | 
						|
 | 
						|
		mutable struct
 | 
						|
		{
 | 
						|
			hawk_oocs_t str;
 | 
						|
			hawk_bcs_t mbs;
 | 
						|
		} cached;
 | 
						|
 | 
						|
	public:
 | 
						|
		static const hawk_ooch_t* getEmptyStr();
 | 
						|
		static const hawk_bch_t* getEmptyMbs();
 | 
						|
		static const void* getEmptyBob();
 | 
						|
	};
 | 
						|
 | 
						|
public:
 | 
						|
	///
 | 
						|
	/// The Run class wraps around #hawk_rtx_t to represent the
 | 
						|
	/// runtime context.
 | 
						|
	///
 | 
						|
	class HAWK_EXPORT Run
 | 
						|
	{
 | 
						|
	protected:
 | 
						|
		friend class Hawk;
 | 
						|
		friend class Value;
 | 
						|
		friend class RIOBase;
 | 
						|
		friend class Console;
 | 
						|
 | 
						|
		Run (Hawk* hawk);
 | 
						|
		Run (Hawk* hawk, hawk_rtx_t* run);
 | 
						|
		~Run ();
 | 
						|
 | 
						|
	public:
 | 
						|
		operator Hawk* () const
 | 
						|
		{
 | 
						|
			return this->hawk;
 | 
						|
		}
 | 
						|
 | 
						|
		operator hawk_rtx_t* () const
 | 
						|
		{
 | 
						|
			return this->rtx;
 | 
						|
		}
 | 
						|
 | 
						|
		operator hawk_gem_t* () const
 | 
						|
		{
 | 
						|
			return this->rtx? hawk_rtx_getgem(this->rtx): HAWK_NULL;
 | 
						|
		}
 | 
						|
 | 
						|
		void halt () const;
 | 
						|
		bool isHalt () const;
 | 
						|
 | 
						|
		hawk_errnum_t getErrorNumber () const;
 | 
						|
		hawk_loc_t getErrorLocation () const;
 | 
						|
		const hawk_ooch_t* getErrorMessage () const;
 | 
						|
		const hawk_uch_t* getErrorMessageU () const;
 | 
						|
		const hawk_bch_t* getErrorMessageB () const;
 | 
						|
 | 
						|
		///
 | 
						|
		/// The setError() function sets error information.
 | 
						|
		///
 | 
						|
		void setError (
 | 
						|
			hawk_errnum_t      code, ///< error code
 | 
						|
			const hawk_loc_t*  loc   = HAWK_NULL  ///< error location
 | 
						|
		);
 | 
						|
 | 
						|
		void formatError (
 | 
						|
			hawk_errnum_t       code,
 | 
						|
			const hawk_loc_t*   loc,
 | 
						|
			const hawk_bch_t*   fmt,
 | 
						|
			...
 | 
						|
		);
 | 
						|
 | 
						|
		void formatError (
 | 
						|
			hawk_errnum_t       code,
 | 
						|
			const hawk_loc_t*   loc,
 | 
						|
			const hawk_uch_t*   fmt,
 | 
						|
			...
 | 
						|
		);
 | 
						|
 | 
						|
		///
 | 
						|
		/// The setGlobal() function sets the value of a global
 | 
						|
		/// variable identified by \a id
 | 
						|
		/// to \a v.
 | 
						|
		/// \return 0 on success, -1 on failure
 | 
						|
		///
 | 
						|
		int setGlobal (int id, hawk_int_t v);
 | 
						|
 | 
						|
		///
 | 
						|
		/// The setGlobal() function sets the value of a global
 | 
						|
		/// variable identified by \a id
 | 
						|
		/// to \a v.
 | 
						|
		/// \return 0 on success, -1 on failure
 | 
						|
		///
 | 
						|
		int setGlobal (int id, hawk_flt_t v);
 | 
						|
 | 
						|
		///
 | 
						|
		/// The setGlobal() function sets the value of a global
 | 
						|
		/// variable identified by \a id
 | 
						|
		/// to a string as long as \a len characters pointed to by
 | 
						|
		/// \a ptr.
 | 
						|
		/// \return 0 on success, -1 on failure
 | 
						|
		///
 | 
						|
		int setGlobal (int id, const hawk_uch_t* ptr, hawk_oow_t len, bool mbs = false);
 | 
						|
		int setGlobal (int id, const hawk_bch_t* ptr, hawk_oow_t len, bool mbs = false);
 | 
						|
		int setGlobal (int id, const hawk_uch_t* ptr, bool mbs = false);
 | 
						|
		int setGlobal (int id, const hawk_bch_t* ptr, bool mbs = false);
 | 
						|
 | 
						|
		///
 | 
						|
		/// The setGlobal() function sets a global variable
 | 
						|
		/// identified by \a id to a value \a v.
 | 
						|
		/// \return 0 on success, -1 on failure
 | 
						|
		///
 | 
						|
		int setGlobal (int id, const Value& v);
 | 
						|
 | 
						|
		///
 | 
						|
		/// The getGlobal() function gets the value of a global
 | 
						|
		/// variable identified by \a id and stores it in \a v.
 | 
						|
		/// \return 0 on success, -1 on failure
 | 
						|
		///
 | 
						|
		int getGlobal (int id, Value& v) const;
 | 
						|
 | 
						|
	protected:
 | 
						|
		Hawk* hawk;
 | 
						|
		hawk_rtx_t* rtx;
 | 
						|
	};
 | 
						|
 | 
						|
	///
 | 
						|
	/// Returns the primitive handle
 | 
						|
	///
 | 
						|
	operator hawk_t* () const
 | 
						|
	{
 | 
						|
		return this->hawk;
 | 
						|
	}
 | 
						|
 | 
						|
	operator hawk_gem_t* () const
 | 
						|
	{
 | 
						|
		return this->hawk? hawk_getgem(this->hawk): HAWK_NULL;
 | 
						|
	}
 | 
						|
 | 
						|
	///
 | 
						|
	/// \name Basic Functions
 | 
						|
	/// \{
 | 
						|
	///
 | 
						|
 | 
						|
	/// The Hawk() function creates an interpreter without fully
 | 
						|
	/// initializing it. You must call open() for full initialization
 | 
						|
	/// before calling other functions.
 | 
						|
	Hawk (Mmgr* mmgr = HAWK_NULL);
 | 
						|
 | 
						|
	/// The ~Hawk() function destroys an interpreter. Make sure to have
 | 
						|
	/// called close() for finalization before the destructor is executed.
 | 
						|
	virtual ~Hawk ();
 | 
						|
 | 
						|
	hawk_cmgr_t* getCmgr () const;
 | 
						|
	void setCmgr (hawk_cmgr_t* cmgr);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The open() function initializes an interpreter.
 | 
						|
	/// You must call this function before doing anything meaningful.
 | 
						|
	/// \return 0 on success, -1 on failure
 | 
						|
	///
 | 
						|
	int open ();
 | 
						|
 | 
						|
	///
 | 
						|
	/// The close() function closes the interpreter.
 | 
						|
	///
 | 
						|
	void close ();
 | 
						|
 | 
						|
	///
 | 
						|
	/// The uponClosing() function is called back after Hawk::close()
 | 
						|
	/// has cleared most of the internal data but before destroying
 | 
						|
	/// the underlying hawk object. This maps to the close callback
 | 
						|
	/// of #hawk_ecb_t.
 | 
						|
	///
 | 
						|
	virtual void uponClosing ();
 | 
						|
 | 
						|
	///
 | 
						|
	/// The uponClearing() function is called back when Hawk::close()
 | 
						|
	/// begins clearing internal data. This maps to the clear callback
 | 
						|
	/// of #hawk_ecb_t.
 | 
						|
	///
 | 
						|
	virtual void uponClearing ();
 | 
						|
 | 
						|
	///
 | 
						|
	/// The parse() function parses the source code read from the input
 | 
						|
	/// stream \a in and writes the parse tree to the output stream \a out.
 | 
						|
	/// To disable deparsing, you may set \a out to Hawk::Source::NONE.
 | 
						|
	/// However, it is not allowed to specify Hawk::Source::NONE for \a in.
 | 
						|
	///
 | 
						|
	/// \return Run object on success, #HAWK_NULL on failure
 | 
						|
	///
 | 
						|
	Hawk::Run* parse (
 | 
						|
		Source& in,  ///< script to parse
 | 
						|
		Source& out  ///< deparsing target
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The getRunContext() funciton returns the execution context
 | 
						|
	/// returned by the parse() function. The returned context
 | 
						|
	/// is valid if parse() has been called. You may call this
 | 
						|
	/// function to get the context if you forgot to store it
 | 
						|
	/// in a call to parse().
 | 
						|
	///
 | 
						|
	const Hawk::Run* getRunContext () const
 | 
						|
	{
 | 
						|
		return &this->runctx;
 | 
						|
	}
 | 
						|
 | 
						|
	///
 | 
						|
	/// The getRunContext() funciton returns the execution context
 | 
						|
	/// returned by the parse() function. The returned context
 | 
						|
	/// is valid if parse() has been called. You may call this
 | 
						|
	/// function to get the context if you forgot to store it
 | 
						|
	/// in a call to parse().
 | 
						|
	///
 | 
						|
	Hawk::Run* getRunContext ()
 | 
						|
	{
 | 
						|
		return &this->runctx;
 | 
						|
	}
 | 
						|
 | 
						|
	///
 | 
						|
	/// The resetRunContext() function closes an existing
 | 
						|
	/// execution context and creates a new execution context.
 | 
						|
	/// You may want to call this function if you want to
 | 
						|
	/// reset it without calling the parse() function again
 | 
						|
	/// after the first call to it.
 | 
						|
	Hawk::Run* resetRunContext ();
 | 
						|
 | 
						|
	///
 | 
						|
	/// The loop() function executes the BEGIN block, pattern-action blocks,
 | 
						|
	/// and the END block. The return value is stored into \a ret.
 | 
						|
	/// \return 0 on succes, -1 on failure
 | 
						|
	///
 | 
						|
	int loop (
 | 
						|
		Value* ret  ///< return value holder
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The call() function invokes a function named \a name.
 | 
						|
	///
 | 
						|
	int call (
 | 
						|
		const hawk_bch_t*  name,  ///< function name
 | 
						|
		Value*             ret,   ///< return value holder
 | 
						|
		const Value*       args,  ///< argument array
 | 
						|
		hawk_oow_t         nargs  ///< number of arguments
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The call() function invokes a function named \a name.
 | 
						|
	///
 | 
						|
	int call (
 | 
						|
		const hawk_uch_t*  name,  ///< function name
 | 
						|
		Value*             ret,   ///< return value holder
 | 
						|
		const Value*       args,  ///< argument array
 | 
						|
		hawk_oow_t         nargs  ///< number of arguments
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The exec() function is the same as loop() if no @pragma startup
 | 
						|
	/// is specified. It is the same as call() if it is specifed
 | 
						|
	///
 | 
						|
	int exec (
 | 
						|
		Value*             ret,   ///< return value holder
 | 
						|
		const Value*       args,  ///< argument array
 | 
						|
		hawk_oow_t         nargs  ///< number of arguments
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The halt() function makes request to abort execution
 | 
						|
	///
 | 
						|
	void halt ();
 | 
						|
	/// \}
 | 
						|
 | 
						|
	///
 | 
						|
	/// \name Configuration
 | 
						|
	/// \{
 | 
						|
	///
 | 
						|
 | 
						|
	///
 | 
						|
	/// The getTrait() function gets the current options.
 | 
						|
	/// \return current traits
 | 
						|
	///
 | 
						|
	int getTrait () const;
 | 
						|
 | 
						|
	///
 | 
						|
	/// The setTrait() function changes the current traits.
 | 
						|
	///
 | 
						|
	void setTrait (
 | 
						|
		int trait
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The setMaxDepth() function sets the maximum processing depth
 | 
						|
	/// for operations identified by \a ids.
 | 
						|
	///
 | 
						|
	void setMaxDepth (
 | 
						|
		depth_t id,  ///< depth identifier
 | 
						|
		hawk_oow_t depth ///< new depth
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The getMaxDepth() function gets the maximum depth for an operation
 | 
						|
	/// type identified by \a id.
 | 
						|
	///
 | 
						|
	hawk_oow_t getMaxDepth (
 | 
						|
		depth_t id   ///< depth identifier
 | 
						|
	) const;
 | 
						|
 | 
						|
	int setIncludeDirs (const hawk_uch_t* dirs);
 | 
						|
	int setIncludeDirs (const hawk_bch_t* dirs);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The addArgument() function adds an ARGV string as long as \a len
 | 
						|
	/// characters pointed to
 | 
						|
	/// by \a arg. loop() and call() make a string added available
 | 
						|
	/// to a script through ARGV.
 | 
						|
	/// \return 0 on success, -1 on failure
 | 
						|
	///
 | 
						|
	int addArgument (
 | 
						|
		const hawk_uch_t* arg,  ///< string pointer
 | 
						|
		hawk_oow_t        len   ///< string length
 | 
						|
	);
 | 
						|
 | 
						|
	int addArgument (
 | 
						|
		const hawk_bch_t* arg,  ///< string pointer
 | 
						|
		hawk_oow_t        len   ///< string length
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The addArgument() function adds a null-terminated string \a arg.
 | 
						|
	/// loop() and call() make a string added available to a script
 | 
						|
	/// through ARGV.
 | 
						|
	/// \return 0 on success, -1 on failure
 | 
						|
	///
 | 
						|
	int addArgument (
 | 
						|
		const hawk_uch_t* arg ///< string pointer
 | 
						|
	);
 | 
						|
 | 
						|
	int addArgument (
 | 
						|
		const hawk_bch_t* arg ///< string pointer
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The clearArguments() function deletes all ARGV strings.
 | 
						|
	///
 | 
						|
	void clearArguments ();
 | 
						|
 | 
						|
	hawk_oow_t getArgumentCount () const
 | 
						|
	{
 | 
						|
		return this->runarg.len;
 | 
						|
	}
 | 
						|
 | 
						|
	const hawk_ooch_t* getArgument (hawk_oow_t index, hawk_oow_t* len = HAWK_NULL) const
 | 
						|
	{
 | 
						|
		if (len) *len = this->runarg.ptr[index].len;
 | 
						|
		return this->runarg.ptr[index].ptr;
 | 
						|
	}
 | 
						|
 | 
						|
	///
 | 
						|
	/// The addGlobal() function registers an intrinsic global variable.
 | 
						|
	/// \return integer >= 0 on success, -1 on failure.
 | 
						|
	///
 | 
						|
	int addGlobal (
 | 
						|
		const hawk_bch_t* name ///< variable name
 | 
						|
	);
 | 
						|
 | 
						|
	int addGlobal (
 | 
						|
		const hawk_uch_t* name ///< variable name
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The deleteGlobal() function unregisters an intrinsic global
 | 
						|
	/// variable by name.
 | 
						|
	/// \return 0 on success, -1 on failure.
 | 
						|
	///
 | 
						|
	int deleteGlobal (
 | 
						|
		const hawk_bch_t* name ///< variable name
 | 
						|
	);
 | 
						|
 | 
						|
	int deleteGlobal (
 | 
						|
		const hawk_uch_t* name ///< variable name
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The findGlobal() function returns the numeric ID of an intrinsic
 | 
						|
	//  global variable.
 | 
						|
	/// \return integer >= 0 on success, -1 on failure.
 | 
						|
	///
 | 
						|
	int findGlobal (
 | 
						|
		const hawk_bch_t* name, ///> variable name
 | 
						|
		bool inc_builtins = false
 | 
						|
	);
 | 
						|
	int findGlobal (
 | 
						|
		const hawk_uch_t* name, ///> variable name
 | 
						|
		bool inc_builtins = false
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The setGlobal() function sets the value of a global variable
 | 
						|
	/// identified by \a id. The \a id is either a value returned by
 | 
						|
	/// addGlobal() or one of the #hawk_gbl_id_t enumerators. It is not allowed
 | 
						|
	/// to call this function prior to parse().
 | 
						|
	/// \return 0 on success, -1 on failure
 | 
						|
	///
 | 
						|
	int setGlobal (
 | 
						|
		int          id,  ///< numeric identifier
 | 
						|
		const Value& v    ///< value
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The getGlobal() function gets the value of a global variable
 | 
						|
	/// identified by \a id. The \a id is either a value returned by
 | 
						|
	/// addGlobal() or one of the #hawk_gbl_id_t enumerators. It is not allowed
 | 
						|
	/// to call this function before parse().
 | 
						|
	/// \return 0 on success, -1 on failure
 | 
						|
	///
 | 
						|
	int getGlobal (
 | 
						|
		int    id, ///< numeric identifier
 | 
						|
		Value& v   ///< value store
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The FunctionHandler type defines a intrinsic function handler.
 | 
						|
	///
 | 
						|
	typedef int (Hawk::*FunctionHandler) (
 | 
						|
		Run&              run,
 | 
						|
		Value&            ret,
 | 
						|
		Value*            args,
 | 
						|
		hawk_oow_t        nargs,
 | 
						|
		const hawk_fnc_info_t* fi
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The addFunction() function adds a new user-defined intrinsic
 | 
						|
	/// function.
 | 
						|
	///
 | 
						|
	int addFunction (
 | 
						|
		const hawk_bch_t* name,      ///< function name
 | 
						|
		hawk_oow_t minArgs,          ///< minimum numbers of arguments
 | 
						|
		hawk_oow_t maxArgs,          ///< maximum numbers of arguments
 | 
						|
		const hawk_bch_t* argSpec,   ///< argument specification
 | 
						|
		FunctionHandler handler,     ///< function handler
 | 
						|
		int validOpts = 0            ///< valid if these options are set
 | 
						|
	);
 | 
						|
 | 
						|
	int addFunction (
 | 
						|
		const hawk_uch_t* name,      ///< function name
 | 
						|
		hawk_oow_t minArgs,          ///< minimum numbers of arguments
 | 
						|
		hawk_oow_t maxArgs,          ///< maximum numbers of arguments
 | 
						|
		const hawk_uch_t* argSpec,   ///< argument specification
 | 
						|
		FunctionHandler handler,     ///< function handler
 | 
						|
		int validOpts = 0            ///< valid if these options are set
 | 
						|
	);
 | 
						|
 | 
						|
	///
 | 
						|
	/// The deleteFunction() function deletes a user-defined intrinsic
 | 
						|
	/// function by name.
 | 
						|
	///
 | 
						|
	int deleteFunction (
 | 
						|
		const hawk_ooch_t* name ///< function name
 | 
						|
	);
 | 
						|
	/// \}
 | 
						|
 | 
						|
	Pipe::Handler* getPipeHandler ()
 | 
						|
	{
 | 
						|
		return this->pipe_handler;
 | 
						|
	}
 | 
						|
 | 
						|
	const Pipe::Handler* getPipeHandler () const
 | 
						|
	{
 | 
						|
		return this->pipe_handler;
 | 
						|
	}
 | 
						|
 | 
						|
	///
 | 
						|
	/// The setPipeHandler() function registers an external pipe
 | 
						|
	/// handler object. An external pipe handler can be implemented
 | 
						|
	/// outside this class without overriding various pipe functions.
 | 
						|
	/// Note that an external pipe handler must outlive an outer
 | 
						|
	/// hawk object.
 | 
						|
	///
 | 
						|
	void setPipeHandler (Pipe::Handler* handler)
 | 
						|
	{
 | 
						|
		this->pipe_handler = handler;
 | 
						|
	}
 | 
						|
 | 
						|
	File::Handler* getFileHandler ()
 | 
						|
	{
 | 
						|
		return this->file_handler;
 | 
						|
	}
 | 
						|
 | 
						|
	const File::Handler* getFileHandler () const
 | 
						|
	{
 | 
						|
		return this->file_handler;
 | 
						|
	}
 | 
						|
 | 
						|
	///
 | 
						|
	/// The setFileHandler() function registers an external file
 | 
						|
	/// handler object. An external file handler can be implemented
 | 
						|
	/// outside this class without overriding various file functions.
 | 
						|
	/// Note that an external file handler must outlive an outer
 | 
						|
	/// hawk object.
 | 
						|
	///
 | 
						|
	void setFileHandler (File::Handler* handler)
 | 
						|
	{
 | 
						|
		this->file_handler = handler;
 | 
						|
	}
 | 
						|
 | 
						|
	Console::Handler* getConsoleHandler ()
 | 
						|
	{
 | 
						|
		return this->console_handler;
 | 
						|
	}
 | 
						|
 | 
						|
	const Console::Handler* getConsoleHandler () const
 | 
						|
	{
 | 
						|
		return this->console_handler;
 | 
						|
	}
 | 
						|
 | 
						|
	///
 | 
						|
	/// The setConsoleHandler() function registers an external console
 | 
						|
	/// handler object. An external file handler can be implemented
 | 
						|
	/// outside this class without overriding various console functions.
 | 
						|
	/// Note that an external console handler must outlive an outer
 | 
						|
	/// hawk object.
 | 
						|
	///
 | 
						|
	void setConsoleHandler (Console::Handler* handler)
 | 
						|
	{
 | 
						|
		this->console_handler = handler;
 | 
						|
	}
 | 
						|
 | 
						|
protected:
 | 
						|
	///
 | 
						|
	/// \name Pipe I/O handlers
 | 
						|
	/// Pipe operations are achieved through the following functions
 | 
						|
	/// if no external pipe handler is set with setPipeHandler().
 | 
						|
	/// \{
 | 
						|
 | 
						|
	/// The openPipe() function is a pure virtual function that must be
 | 
						|
	/// overridden by a child class to open a pipe. It must return 1
 | 
						|
	/// on success, 0 on end of a pipe, and -1 on failure.
 | 
						|
	virtual int     openPipe  (Pipe& io);
 | 
						|
 | 
						|
	/// The closePipe() function is a pure virtual function that must be
 | 
						|
	/// overridden by a child class to close a pipe. It must return 0
 | 
						|
	/// on success and -1 on failure.
 | 
						|
	virtual int     closePipe (Pipe& io);
 | 
						|
 | 
						|
	virtual hawk_ooi_t readPipe (Pipe& io, hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	virtual hawk_ooi_t readPipeBytes (Pipe& io, hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	virtual hawk_ooi_t writePipe (Pipe& io, const hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	virtual hawk_ooi_t writePipeBytes (Pipe& io, const hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	virtual int flushPipe (Pipe& io);
 | 
						|
	/// \}
 | 
						|
 | 
						|
	///
 | 
						|
	/// \name File I/O handlers
 | 
						|
	/// File operations are achieved through the following functions
 | 
						|
	/// if no external file handler is set with setFileHandler().
 | 
						|
	/// \{
 | 
						|
	///
 | 
						|
	virtual int openFile (File& io);
 | 
						|
	virtual int closeFile (File& io);
 | 
						|
	virtual hawk_ooi_t readFile (File& io, hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	virtual hawk_ooi_t readFileBytes (File& io, hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	virtual hawk_ooi_t writeFile (File& io, const hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	virtual hawk_ooi_t writeFileBytes (File& io, const hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	virtual int flushFile (File& io);
 | 
						|
	/// \}
 | 
						|
 | 
						|
	///
 | 
						|
	/// \name Console I/O handlers
 | 
						|
	/// Console operations are achieved through the following functions.
 | 
						|
	/// if no external console handler is set with setConsoleHandler().
 | 
						|
	/// \{
 | 
						|
	///
 | 
						|
	virtual int openConsole (Console& io);
 | 
						|
	virtual int closeConsole (Console& io);
 | 
						|
	virtual hawk_ooi_t readConsole (Console& io, hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	virtual hawk_ooi_t readConsoleBytes (Console& io, hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	virtual hawk_ooi_t writeConsole (Console& io, const hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	virtual hawk_ooi_t writeConsoleBytes (Console& io, const hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	virtual int flushConsole (Console& io);
 | 
						|
	virtual int nextConsole (Console& io);
 | 
						|
	/// \}
 | 
						|
 | 
						|
	// primitive handlers
 | 
						|
	virtual hawk_flt_t pow (hawk_flt_t x, hawk_flt_t y) = 0;
 | 
						|
	virtual hawk_flt_t mod (hawk_flt_t x, hawk_flt_t y) = 0;
 | 
						|
 | 
						|
	virtual void* modopen (const hawk_mod_spec_t* spec) = 0;
 | 
						|
	virtual void  modclose (void* handle) = 0;
 | 
						|
	virtual void* modgetsym (void* handle, const hawk_ooch_t* name) = 0;
 | 
						|
 | 
						|
	// static glue members for various handlers
 | 
						|
	static hawk_ooi_t readSource (
 | 
						|
		hawk_t* hawk, hawk_sio_cmd_t cmd, hawk_sio_arg_t* arg,
 | 
						|
		hawk_ooch_t* data, hawk_oow_t count);
 | 
						|
	static hawk_ooi_t writeSource (
 | 
						|
		hawk_t* hawk, hawk_sio_cmd_t cmd, hawk_sio_arg_t* arg,
 | 
						|
		hawk_ooch_t* data, hawk_oow_t count);
 | 
						|
 | 
						|
	static hawk_ooi_t pipeHandler (
 | 
						|
		hawk_rtx_t* rtx, hawk_rio_cmd_t cmd, hawk_rio_arg_t* riod,
 | 
						|
		void* data, hawk_oow_t count);
 | 
						|
	static hawk_ooi_t fileHandler (
 | 
						|
		hawk_rtx_t* rtx, hawk_rio_cmd_t cmd, hawk_rio_arg_t* riod,
 | 
						|
		void* data, hawk_oow_t count);
 | 
						|
	static hawk_ooi_t consoleHandler (
 | 
						|
		hawk_rtx_t* rtx, hawk_rio_cmd_t cmd, hawk_rio_arg_t* riod,
 | 
						|
		void* data, hawk_oow_t count);
 | 
						|
 | 
						|
	static int functionHandler (hawk_rtx_t* rtx, const hawk_fnc_info_t* fi);
 | 
						|
 | 
						|
 | 
						|
	static hawk_flt_t pow (hawk_t* hawk, hawk_flt_t x, hawk_flt_t y);
 | 
						|
	static hawk_flt_t mod (hawk_t* hawk, hawk_flt_t x, hawk_flt_t y);
 | 
						|
 | 
						|
	static void* modopen (hawk_t* hawk, const hawk_mod_spec_t* spec);
 | 
						|
	static void  modclose (hawk_t* hawk, void* handle);
 | 
						|
	static void* modgetsym (hawk_t* hawk, void* handle, const hawk_ooch_t* name);
 | 
						|
 | 
						|
public:
 | 
						|
	// use these with care
 | 
						|
	hawk_t* getHandle() const { return this->hawk; }
 | 
						|
 | 
						|
protected:
 | 
						|
	hawk_t* hawk;
 | 
						|
 | 
						|
	hawk_errstr_t dflerrstr;
 | 
						|
	hawk_errinf_t errinf;
 | 
						|
#if defined(HAWK_OOCH_IS_BCH)
 | 
						|
	mutable hawk_uch_t xerrmsg[HAWK_ERRMSG_CAPA];
 | 
						|
	mutable hawk_uch_t xerrlocfile[128];
 | 
						|
#else
 | 
						|
	mutable hawk_bch_t xerrmsg[HAWK_ERRMSG_CAPA * 2];
 | 
						|
	mutable hawk_bch_t xerrlocfile[256];
 | 
						|
#endif
 | 
						|
 | 
						|
#if defined(HAWK_USE_HTB_FOR_FUNCTION_MAP)
 | 
						|
	hawk_htb_t* functionMap;
 | 
						|
#else
 | 
						|
 | 
						|
	class FunctionMap: public HashTable<Cstr,FunctionHandler>
 | 
						|
	{
 | 
						|
	public:
 | 
						|
		FunctionMap (Hawk* hawk): hawk(hawk) {}
 | 
						|
 | 
						|
	protected:
 | 
						|
		Hawk* hawk;
 | 
						|
	};
 | 
						|
 | 
						|
	FunctionMap functionMap;
 | 
						|
#endif
 | 
						|
 | 
						|
	Source* source_reader;
 | 
						|
	Source* source_writer;
 | 
						|
 | 
						|
	Pipe::Handler* pipe_handler;
 | 
						|
	File::Handler* file_handler;
 | 
						|
	Console::Handler* console_handler;
 | 
						|
 | 
						|
	struct xstrs_t
 | 
						|
	{
 | 
						|
		xstrs_t (): ptr (HAWK_NULL), len (0), capa (0) {}
 | 
						|
 | 
						|
		int add (hawk_t* hawk, const hawk_uch_t* arg, hawk_oow_t len);
 | 
						|
		int add (hawk_t* hawk, const hawk_bch_t* arg, hawk_oow_t len);
 | 
						|
 | 
						|
		void clear (hawk_t* hawk);
 | 
						|
 | 
						|
		hawk_oocs_t* ptr;
 | 
						|
		hawk_oow_t   len;
 | 
						|
		hawk_oow_t   capa;
 | 
						|
	};
 | 
						|
 | 
						|
	xstrs_t runarg;
 | 
						|
 | 
						|
private:
 | 
						|
	hawk_cmgr_t* _cmgr;
 | 
						|
	Run runctx;
 | 
						|
 | 
						|
	int init_runctx ();
 | 
						|
	void fini_runctx ();
 | 
						|
	int dispatch_function (Run* run, const hawk_fnc_info_t* fi);
 | 
						|
 | 
						|
	static const hawk_ooch_t* xerrstr (hawk_t* a, hawk_errnum_t num);
 | 
						|
};
 | 
						|
 | 
						|
 | 
						|
 | 
						|
// ----------------------------------------------------------------------------------------
 | 
						|
 | 
						|
class HAWK_EXPORT MmgrStd: public Mmgr
 | 
						|
{
 | 
						|
public:
 | 
						|
	MmgrStd () HAWK_CXX_NOEXCEPT: Mmgr () {}
 | 
						|
 | 
						|
	void* allocMem (hawk_oow_t n) HAWK_CXX_NOEXCEPT;
 | 
						|
	void* reallocMem (void* ptr, hawk_oow_t n) HAWK_CXX_NOEXCEPT;
 | 
						|
	void freeMem (void* ptr) HAWK_CXX_NOEXCEPT;
 | 
						|
 | 
						|
#if 0
 | 
						|
	/// The getInstance() function returns the stock instance of the MmgrStd class.
 | 
						|
	static MmgrStd* getInstance () HAWK_CXX_NOEXCEPT;
 | 
						|
#endif
 | 
						|
};
 | 
						|
 | 
						|
 | 
						|
// ----------------------------------------------------------------------------------------
 | 
						|
 | 
						|
///
 | 
						|
/// The HawkStd class provides an easier-to-use interface by overriding
 | 
						|
/// primitive methods, and implementing the file handler, the pipe handler,
 | 
						|
/// and common intrinsic functions.
 | 
						|
///
 | 
						|
class HAWK_EXPORT HawkStd: public Hawk
 | 
						|
{
 | 
						|
public:
 | 
						|
	///
 | 
						|
	/// The SourceFile class implements script I/O from and to a file.
 | 
						|
	///
 | 
						|
	class HAWK_EXPORT SourceFile: public Source
 | 
						|
	{
 | 
						|
	public:
 | 
						|
		SourceFile (const hawk_uch_t* name, hawk_cmgr_t* cmgr = HAWK_NULL): _type(NAME_UCH), _name(name), cmgr(cmgr)
 | 
						|
		{
 | 
						|
			dir.ptr = HAWK_NULL; dir.len = 0;
 | 
						|
		}
 | 
						|
 | 
						|
		SourceFile (const hawk_bch_t* name, hawk_cmgr_t* cmgr = HAWK_NULL): _type(NAME_BCH), _name(name), cmgr(cmgr)
 | 
						|
		{
 | 
						|
			dir.ptr = HAWK_NULL; dir.len = 0;
 | 
						|
		}
 | 
						|
 | 
						|
		~SourceFile () {};
 | 
						|
 | 
						|
		int open (Data& io);
 | 
						|
		int close (Data& io);
 | 
						|
		hawk_ooi_t read (Data& io, hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
		hawk_ooi_t write (Data& io, const hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
 | 
						|
	protected:
 | 
						|
		enum
 | 
						|
		{
 | 
						|
			NAME_UCH,
 | 
						|
			NAME_BCH
 | 
						|
		} _type;
 | 
						|
		const void* _name;
 | 
						|
		hawk_oocs_t dir;
 | 
						|
		hawk_cmgr_t* cmgr;
 | 
						|
	};
 | 
						|
 | 
						|
	///
 | 
						|
	/// The SourceString class implements script input from a string.
 | 
						|
	/// Deparsing is not supported.
 | 
						|
	///
 | 
						|
	class HAWK_EXPORT SourceString: public Source
 | 
						|
	{
 | 
						|
	public:
 | 
						|
		SourceString (const hawk_uch_t* str, hawk_cmgr_t* cmgr = HAWK_NULL): _type(STR_UCH), _str(str), _hawk(HAWK_NULL), str(HAWK_NULL), ptr(HAWK_NULL), cmgr(cmgr) {}
 | 
						|
		SourceString (const hawk_bch_t* str, hawk_cmgr_t* cmgr = HAWK_NULL): _type(STR_BCH), _str(str), _hawk(HAWK_NULL), str(HAWK_NULL), ptr(HAWK_NULL), cmgr(cmgr) {}
 | 
						|
		~SourceString ();
 | 
						|
 | 
						|
		int open (Data& io);
 | 
						|
		int close (Data& io);
 | 
						|
		hawk_ooi_t read (Data& io, hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
		hawk_ooi_t write (Data& io, const hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
 | 
						|
	protected:
 | 
						|
		enum
 | 
						|
		{
 | 
						|
			STR_UCH,
 | 
						|
			STR_BCH
 | 
						|
		} _type;
 | 
						|
		const void* _str;
 | 
						|
		hawk_t* _hawk;
 | 
						|
 | 
						|
		hawk_ooch_t* str;
 | 
						|
		const hawk_ooch_t* ptr;
 | 
						|
		hawk_cmgr_t* cmgr; // for reading included files
 | 
						|
	};
 | 
						|
 | 
						|
	HawkStd (Mmgr* mmgr = HAWK_NULL): Hawk(mmgr), cmgrtab_inited(false), stdmod_up(false), console_cmgr(HAWK_NULL)
 | 
						|
	{
 | 
						|
	}
 | 
						|
 | 
						|
	~HawkStd();
 | 
						|
 | 
						|
	int open ();
 | 
						|
	void close ();
 | 
						|
 | 
						|
	void uponClosing ();
 | 
						|
 | 
						|
	Run* parse (Source& in, Source& out);
 | 
						|
 | 
						|
	/// The setConsoleCmgr() function sets the encoding type of
 | 
						|
	/// the console streams. They include both the input and the output
 | 
						|
	/// streams. It provides no way to specify a different encoding
 | 
						|
	/// type for the input and the output stream.
 | 
						|
	void setConsoleCmgr (const hawk_cmgr_t* cmgr);
 | 
						|
 | 
						|
	/// The getConsoleCmgr() function returns the current encoding
 | 
						|
	/// type set for the console streams.
 | 
						|
	const hawk_cmgr_t* getConsoleCmgr () const;
 | 
						|
 | 
						|
	/// The addConsoleOutput() function adds a file to form an
 | 
						|
	/// output console stream.
 | 
						|
	int addConsoleOutput (const hawk_uch_t* arg, hawk_oow_t len);
 | 
						|
	int addConsoleOutput (const hawk_uch_t* arg);
 | 
						|
	int addConsoleOutput (const hawk_bch_t* arg, hawk_oow_t len);
 | 
						|
	int addConsoleOutput (const hawk_bch_t* arg);
 | 
						|
 | 
						|
	void clearConsoleOutputs ();
 | 
						|
 | 
						|
protected:
 | 
						|
	#define HAWK_STD_ENV_CHAR_IS_BCH
 | 
						|
	typedef hawk_bch_t env_char_t;
 | 
						|
 | 
						|
	int make_additional_globals (Run* run);
 | 
						|
	int build_argcv (Run* run);
 | 
						|
	int build_environ (Run* run, env_char_t* envarr[]);
 | 
						|
 | 
						|
	// intrinsic functions
 | 
						|
	hawk_cmgr_t* getiocmgr (const hawk_ooch_t* ioname);
 | 
						|
 | 
						|
	int setioattr (Run& run, Value& ret, Value* args, hawk_oow_t nargs, const hawk_ooch_t* name, hawk_oow_t len);
 | 
						|
	int getioattr (Run& run, Value& ret, Value* args, hawk_oow_t nargs, const hawk_ooch_t* name, hawk_oow_t len);
 | 
						|
 | 
						|
	// pipe io handlers
 | 
						|
	int openPipe (Pipe& io);
 | 
						|
	int closePipe (Pipe& io);
 | 
						|
	hawk_ooi_t readPipe (Pipe& io, hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	hawk_ooi_t readPipeBytes (Pipe& io, hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	hawk_ooi_t writePipe (Pipe& io, const hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	hawk_ooi_t writePipeBytes (Pipe& io, const hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	int flushPipe (Pipe& io);
 | 
						|
 | 
						|
	// file io handlers
 | 
						|
	int openFile (File& io);
 | 
						|
	int closeFile (File& io);
 | 
						|
	hawk_ooi_t readFile (File& io, hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	hawk_ooi_t readFileBytes (File& io, hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	hawk_ooi_t writeFile (File& io, const hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	hawk_ooi_t writeFileBytes (File& io, const hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	int flushFile (File& io);
 | 
						|
 | 
						|
	// console io handlers
 | 
						|
	int openConsole (Console& io);
 | 
						|
	int closeConsole (Console& io);
 | 
						|
	hawk_ooi_t readConsole (Console& io, hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	hawk_ooi_t readConsoleBytes (Console& io, hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	hawk_ooi_t writeConsole (Console& io, const hawk_ooch_t* buf, hawk_oow_t len);
 | 
						|
	hawk_ooi_t writeConsoleBytes (Console& io, const hawk_bch_t* buf, hawk_oow_t len);
 | 
						|
	int flushConsole (Console& io);
 | 
						|
	int nextConsole (Console& io);
 | 
						|
 | 
						|
	// primitive handlers
 | 
						|
	void* allocMem (hawk_oow_t n);
 | 
						|
	void* reallocMem (void* ptr, hawk_oow_t n);
 | 
						|
	void  freeMem (void* ptr);
 | 
						|
 | 
						|
	hawk_flt_t pow (hawk_flt_t x, hawk_flt_t y);
 | 
						|
	hawk_flt_t mod (hawk_flt_t x, hawk_flt_t y);
 | 
						|
 | 
						|
	void* modopen (const hawk_mod_spec_t* spec);
 | 
						|
	void  modclose (void* handle);
 | 
						|
	void* modgetsym (void* handle, const hawk_ooch_t* name);
 | 
						|
 | 
						|
protected:
 | 
						|
	hawk_htb_t cmgrtab;
 | 
						|
	bool cmgrtab_inited;
 | 
						|
	bool stdmod_up;
 | 
						|
 | 
						|
	hawk_cmgr_t* console_cmgr;
 | 
						|
 | 
						|
	// global variables
 | 
						|
	int gbl_argc;
 | 
						|
	int gbl_argv;
 | 
						|
	int gbl_environ;
 | 
						|
 | 
						|
	// standard input console - reuse runarg
 | 
						|
	hawk_oow_t runarg_index;
 | 
						|
	hawk_oow_t runarg_count;
 | 
						|
 | 
						|
	// standard output console
 | 
						|
	xstrs_t ofile;
 | 
						|
	hawk_oow_t ofile_index;
 | 
						|
	hawk_oow_t ofile_count;
 | 
						|
 | 
						|
public:
 | 
						|
	struct ioattr_t
 | 
						|
	{
 | 
						|
		hawk_cmgr_t* cmgr;
 | 
						|
		hawk_ooch_t cmgr_name[64]; // i assume that the cmgr name never exceeds this length.
 | 
						|
		hawk_ntime_t tmout[4];
 | 
						|
 | 
						|
		ioattr_t (): cmgr (HAWK_NULL)
 | 
						|
		{
 | 
						|
			this->cmgr_name[0] = HAWK_T('\0');
 | 
						|
			for (hawk_oow_t i = 0; i < HAWK_COUNTOF(this->tmout); i++)
 | 
						|
			{
 | 
						|
				this->tmout[i].sec = -999;
 | 
						|
				this->tmout[i].nsec = 0;
 | 
						|
			}
 | 
						|
		}
 | 
						|
	};
 | 
						|
 | 
						|
	static ioattr_t default_ioattr;
 | 
						|
 | 
						|
protected:
 | 
						|
	ioattr_t* get_ioattr (const hawk_ooch_t* ptr, hawk_oow_t len);
 | 
						|
	ioattr_t* find_or_make_ioattr (const hawk_ooch_t* ptr, hawk_oow_t len);
 | 
						|
 | 
						|
 | 
						|
private:
 | 
						|
	int open_console_in (Console& io);
 | 
						|
	int open_console_out (Console& io);
 | 
						|
 | 
						|
	int open_pio (Pipe& io);
 | 
						|
	int open_nwio (Pipe& io, int flags, void* nwad);
 | 
						|
};
 | 
						|
 | 
						|
/////////////////////////////////
 | 
						|
HAWK_END_NAMESPACE(HAWK)
 | 
						|
/////////////////////////////////
 | 
						|
 | 
						|
 | 
						|
HAWK_EXPORT void* operator new (hawk_oow_t size, HAWK::Mmgr* mmgr);
 | 
						|
 | 
						|
#if defined(HAWK_CXX_NO_OPERATOR_DELETE_OVERLOADING)
 | 
						|
HAWK_EXPORT void hawk_operator_delete (void* ptr, HAWK::Mmgr* mmgr);
 | 
						|
#else
 | 
						|
HAWK_EXPORT void operator delete (void* ptr, HAWK::Mmgr* mmgr);
 | 
						|
#endif
 | 
						|
 | 
						|
HAWK_EXPORT void* operator new (hawk_oow_t size, HAWK::Mmgr* mmgr, void* existing_ptr);
 | 
						|
 | 
						|
#if 0
 | 
						|
// i found no way to delete an array allocated with
 | 
						|
// the placement new operator. if the array element is an instance
 | 
						|
// of a class, the pointer returned by the new operator call
 | 
						|
// may not be the actual pointer allocated. some compilers
 | 
						|
// seem to put some information about the array at the
 | 
						|
// beginning of the allocated memory and return the pointer
 | 
						|
// off a few bytes from the beginning.
 | 
						|
void* operator new[] (hawk_oow_t size, HAWK::Mmgr* mmgr);
 | 
						|
void operator delete[] (void* ptr, HAWK::Mmgr* mmgr);
 | 
						|
#endif
 | 
						|
 | 
						|
#define HAWK_CXX_DELETE_WITH_MMGR(ptr, class_name, mmgr) \
 | 
						|
	do { \
 | 
						|
		HAWK_CXX_CALL_DESTRUCTOR (ptr, class_name); \
 | 
						|
		HAWK_CXX_CALL_PLACEMENT_DELETE1(ptr, mmgr); \
 | 
						|
	} while(0);
 | 
						|
 | 
						|
#endif
 |