## TODO:
	can we allow commas between arguments in xlist/mlist to make it more like conventional programming langauges?
	make literal frame in the compiler not use  object momory. ask VM to take the byte codes and create literal frame using object memory
		-> hcl->code.lit.arr must be composed of plain data. not using object memory
		-> it must ask VM(locally via a function call, remotely via some communication) to create objects in the object memory
	static class -> collect class info(variables information) in the compiler
	dyna-class -> compiler doesn't know about classes in advance
	for static cleases, super.var-name can be allowed.
	for dyna-clases, the super prefix is now allowed for varibles. it's allowed for method calls only.
	double-check symbol and dsymbol resolution in set, set-r, defun, defclass to decide how to make it more logical and reasonable


	assignment syntax
		(k := 20) -> (set k 20)
		k := 20  -> (set k 20)
		[a, b] := (multi-retvar-fun 10 20) -> (set-r a b (multi-retvar-fun 10 20))

	implement module -> ::, ., or what notation?
	implement namespace -> ::, ., or what notation?
	review the . notation used for C-module loading... may have to change it

	dynamic byte array is supported but we need yet to support byte-string(byte-array) constant
		b"..." or B"..." for an byte string constant notation
		u"..." or U"..." for an explicit unicode string constant notation?
		-> change u to c???

		#[ ] normal array?
		#b[ ] byte array??
		#c[ ] charcter array??
		#w[ ] word array??
		#hw[ ] half-word array??
		#u8[ ]
		#u16[ ]
		#u32[ ]
		#u64[ ]
		#i8[ ]
		#i16[ ]
		#i32[ ]
		#i64[ ]

	allow b'X' or 'X' in byte array in #b[] notation?

	signal handling

	full oop

	make basic branded types to an object if possible.
	for example (#[10 20]:at 1)

	isn't : for method call  confliting with key value spearator in a dictionary?

	default return value for some class methods.
		:: method -> return what??
		:* method -> return the new instance
		normal method -> return the last evaluated value?


## dictionary list (DIC)
	#{ 1 2 3 4 }
	#{ 1: 2, 3: 4}
	#{} -> empty dictionary
	#{ 1 } -> error, no value.  dictionary requires even number of items.

## array list
	[ 1 2 3 4]
	[ 1, 2, 3, 4 ]
	[] -> empty array

## byte array list
	#[ 1 2 3 4 ]
	#[  1, 2, 3, 4 ]
	each item must be in the byte range.
	if a given value is not a number in the allowed range, an exception error is raised.
	(try
		(set a 20)
		#[ 1 2 3 (+ a 300)]  ; this throws an catchable exception.
	catch(e)
		(printf "EXCEPTION - %O\n" e)
	)

## non-executable list (QLIST)
	#(1 2 3 4)
	#(1 2 3 4 . 5)
	#() -> same as null
	comma not allowed to seperate items.

## varaible declaration list (VLIST)
	| a b c |


## class declaration with methods.

	(defclass X 

		| x y |                 ; instance variables 
		:: | bob jim |             ; class variables

		; instance variables and class variables must not collide with those of parent classes.
		; they must not collide with method names of parent classes
	
		(set bob "Bob")         ; can access class variables. disallowed to access instance variables

		(defun setX (a)
			(set x a)
		)

		; instance method. a method name must not collide with instance variable names and class variable names.
		; the name can be the same as method names of parent classes.
		(defun K (a b)
			(self:Y a)
			(return (+ a b x y))
		)
	
		(defun Y (a)
			(printf "Y=>%d [%s]\n" a bob) 
		)

		(defun :: KK (a b)
			(printf "K=>%s\n" bob) ; a class method can access class variables but not instance variables
			(return (+ a b))
		)

		(set jim (lambda (a b) (+ a b))) ; an anonymous function created 
	)

	(set r (object-new X))
	(r:Y 10)
	(printf ">>%d\n" (X:KK 77 99))


## method invocation

send the message aaa to the receiver
	(self:aaa)

send the message aaa to the receiver but let it resolve the method in the superclass side.
	(super:aaa)

send the message dump to the object pointed to by x with arguments 1, 2, 3.
	(x:dump 1 2 3)

## method types

- class method


- class instantiation method

	(defclass P
		| x y |
		(defun :* new ()
			(set x 1)	
			(set y 1)	
			(return self)
		)
		(defun get-x() x)
		(defun get-y() y)
	)
	(defclass X :: P
		| x y |
		(defun :* new (a b)
			(super:new)
			x = a
			y = b
			(return self)
		)
		(defun get-xx() x)
		(defun get-yy() y)
	)

	(set t (X:new 10 20)) ;t is an instance of X
	(printf "%d %d %d %d\n" (t:get-x) (t:get-y) (t:get-xx) (t:get-yy)) ; must print 1 1 10 20
	(t:new 100 300)  ;the x, y in the X part get reset to 100 and 300. doesn't create a new instance
	(printf "%d %d %d %d\n" (t:get-x) (t:get-y) (t:get-xx) (t:get-yy)) ; must print 1 1 100 300

- instance method



## dynamic dispatching by method name
	(defclass X
		(defun t1 (x) (printf "t1 = %d\n" (+ x x x)))
		(defun t2 (x) (printf "t2 = %d\n" (* x x x)))
	)

	(defun get-name-1() "t1")
	(defun get-name-2() "t2")

	(set x (object-new X))

	(x:(get-name-1) 100) ; must be same as (x:t1 100)
	(x:(get-name-2) 100) ; must be same as (x:t2 100)

## Something to look into..

normal function call
(f arg1 arg2 arg3)
(rcv f arg1 arg2)

## dynamic method invocation???
(X:(f) arg1 arg2)
as long as f returns a symbol, it can also invoke a method??


(defun getX() X) ; ->it must return an object
((getX)->show "hello")

X.Y
 push X
 push_symbol Y
 lookup

(X.Y)
 push X
 push_symbol Y
 lookup
 call 0

X.Y.Z
 push X
 push_symbol Y
 lookup
 push_symbol Z
 lookup
 
 --- if this is within a method, it must become push_instvar
 self.x
  push self
  push symbol x
  lookup




fun f(a, b) 
{
}

fun f(a, b) -> (c, d)
{

}

class X
{
	var x, y, z
	var! printer;

	printer := Printer.new();

	fun! new(a, b)
	{
		return super.new().init(a, b);
	}

	fun init(a, b)
	{
	}

	fun show(a, b)
	{
		Printer.dump(a, b);
	}

}

x := X.new(10, 20);
x.show (40, 50);



---------------


variadic arguments -> supported

multiple return variables -> supported
        (defun ff(a b :: x y z)
                (set x (+ a b))
                (set y (+ x x))
                (set z (+ 999 x))
        )
        (set-r v1 v2 v3 (ff 10 20))
	(printf "%d %d %d\n" v1 v2 v3)

variadic multiple return variables -> not supported as of now
	
        (defun ff(a b :: x y z ...) <--- can i support something like this???
                (set x (+ a b))
                (set y (+ x x))
                (set z (+ 999 x))
        )
        (set-r v1 v2 v3 (ff 10 20))
	(printf "%d %d %d\n" v1 v2 v3)

	since va-get is used to get a variadic argument, can i create vr-put
	to set a variadic return variable?
