% basic.jam
% last changed by Stone, January 26, 1984 4:57:39 pm PST
% last changed by Doug Wyatt, August 24, 1983 7:55 pm

($help) .dup .where {.pop .pop} {100 .dict .def} .ifelse .cvx .exec

(/def)
{3 .copy .exch .pop .def .pop $help 3 1 .roll .put} .cvx .def

(/xdef)
{3 .copy .exch .pop .cvx .def .pop $help 3 1 .roll .put} .cvx .def

(/def)
("/def" accepts three entries on the stack: a key, string, and value.
	the string is stored under the key in the $help dictionary, and
	the value is stored as a noun under the key in the current dictionary.)
(/def).load /def

(/xdef)
("/xdef" accepts three entries on the stack: a key, string, and value.
	the string is stored under the key in the $help dictionary, and
	the value is stored as a verb under the key in the current dictionary.)
(/xdef).load /xdef

(?)
("?"	prints the explanation of the given key from the $help dictionary)
{$help .exch .get =}/xdef

(??)
("??" 	prints the names of all the utility commands found in the $help 
dictionary.)
{$help /kdir}/xdef

(/cr)
("/cr"	prints a carriage return)
{"\n" .print}/xdef

(/sp)
("/sp"	prints a space)
{" " .print}/xdef

(/tab)
("/tab"	prints a tab)
{"\t" .print}/xdef

(/lp)
("/lp"	prints a left parenthesis)
{"(" .print}/xdef

(/rp)
("/rp"	prints a right parenthesis)
{")" .print}/xdef

(/quote)
("/quote"	prints a quotation mark)
{"\"" .print}/xdef

(=)
("="	prints the top of the stack and a carriage return)
{.print /cr}/xdef

(/stk)
("/stk"	prints (without destroying) the contents of the operand stack.)
{.count .copy .count 2 .idiv .array .astore {.print /sp} .cvx .arrayforall}/xdef

(/pstk)
("/stk"	pretty prints the contents of the operand stack.)
{.count .copy .count 2 .idiv .array .astore {==} .cvx .arrayforall}/xdef

(/clr)
("/clr"	clears the operand stack)
{.count (.pop) .load .rept} /xdef

(/dir)
("/dir"	prints the contents of the dictionary on top of the operand stack.)
{{.exch .print (		).print .dup .type .print (	).print =}.cvx .dictforall}/xdef

(/kdir)
("/kdir" prints the keys found in the dictionary on the top of the operand
stack.)
{{.pop =}.cvx .dictforall}/xdef

(/if)
("/if" is equivalent to ".cvx .if")
{.cvx .if}/xdef

(/ifelse)
("/ifelse" is equivalent to ".ifelse .cvx .exec")
{.ifelse .cvx .exec}/xdef

([)
("[" is a command that marks the operand stack for use by the command "]".
This pair of commands is use to create arrays.  For example:
[ 1 2 (hello) ] 
will create an array containing two integers (1 and 2) and the string
"hello".)
{.mark}/xdef

(])
("]" is a command that counts the elements after the mark on the stack and 
puts these elements into an array which is left on the stack. 
The pair of commands ( "[" and "]" ) is use to create arrays.  For example:
[ 1 2 (hello) ] 
will create an array containing two integers (1 and 2) and the string
"hello".)
{.cnttomrk .array .astore .exch .pop}/xdef

(/run){(Running ).print .dup .print .run (.)=}.cvx .def
(/loadbcd){(Loading ).print .dup .print .loadbcd (.)=}.cvx .def

(==)
(== is used to print all types of objects in a manner which can easily be read.)
{.dup .type .dup .print /tab $ptypes .exch .get .exec}/xdef

($ptypes) .dup .where {.pop .pop} {15 .dict .def} /ifelse

$ptypes .begin
(.nil){.pop /cr}.cvx .def
(.int){=}.cvx .def
(.real){=}.cvx .def
(.atom){=}.cvx .def
(.rope){/lp .print /rp /cr}.cvx .def
(.stream){.pop /cr}.cvx .def
(.cmd){.commandname =}.cvx .def
(.op){.cvlit =}.cvx .def
(.array){"{ " .print (==) .load .arrayforall "} " .print}.cvx .def
(.dict){.length =}.cvx .def
(.mark){.pop /cr}.cvx .def
(.other){.pop /cr}.cvx .def
.end