home *** CD-ROM | disk | FTP | other *** search
/ Gold Fish 2 / goldfish_vol2_cd2.bin / bbs / dev / amiga_e-3.0a.lha / Amiga_E / Docs / E.doc < prev    next >
Text File  |  1992-09-02  |  190KB  |  5,515 lines

  1.  
  2.         +-----------------------------------------------+
  3.         |                        |
  4.         |                 Amiga E v3.0a                 |
  5.         |          Compiler for The E Language          |
  6.         |           By Wouter van Oortmerssen           |
  7.         |                        |
  8.         +-----------------------------------------------+
  9.  
  10.  
  11. Contents:
  12.  
  13.      0. compiler and introduction
  14.         A. introduction
  15.         B. the distribution
  16.         C. demo restrictions and registration
  17.         D. using the compiler
  18.         E. changes from v2.1b to v3.0a
  19.         F. additional information
  20.  
  21.      1. format
  22.         A. tabs,lf etc.
  23.         B. comments
  24.         C. identifiers and types
  25.  
  26.      2. immediate values
  27.         A. decimal (1)
  28.         B. hexadecimal ($1)
  29.         C. binary (%1)
  30.         D. float (1.0)
  31.         E. character
  32.         F. strings ('bla')
  33.         G. lists ([1,2,3]) and typed lists
  34.         H. lisp-cells (<a|b>)
  35.  
  36.      3. expressions
  37.         A. format
  38.         B. precedence and grouping
  39.         C. types of expressions
  40.         D. function calls
  41.  
  42.      4. operators
  43.         A. math (+ - * /)
  44.         B. comparison (= <> > < >= <=)
  45.         C. logical and bitwise (AND OR)
  46.         D. unary (SIZEOF ` ^ {} ++ -- -)
  47.         E. triple (IF THEN ELSE)
  48.         F. structure (.)
  49.         G. array ([])
  50.         H. float operator (!)
  51.         I. assignments expressions (:=)
  52.         J. sequencing (BUT)
  53.         K. dynamic memory allocation (NEW)
  54.         L. unification (<=>)
  55.         M. pointer typing (::)
  56.  
  57.      5. statements
  58.         A. format (;)
  59.         B. statement labels and gotos (JUMP)
  60.         C. assignment (:=)
  61.         D. assembly mnemonics
  62.         E. conditional statement (IF)
  63.         F. for-statement (FOR)
  64.         G. while-statement (WHILE)
  65.         H. repeat-statement (REPEAT)
  66.         I. loop-statement (LOOP)
  67.         J. select-case-statement (SELECT)
  68.         K. increase statement (INC/DEC)
  69.         L. void expressions (VOID)
  70.         M. memory deallocation (END)
  71.  
  72.      6. function definitions and declarations
  73.         A. proc definition and arguments (PROC)
  74.         B. local and global definitions: scope (DEF)
  75.         C. endproc/return
  76.         D. the `main' function
  77.         E. built-in system variables
  78.         F. default arguments to functions
  79.         G. multiple return values
  80.         H. function values
  81.  
  82.      7. declaration of constants
  83.         A. const (CONST)
  84.         B. enumerations (ENUM)
  85.         C. sets (SET)
  86.         D. built-in constants
  87.  
  88.      8. types
  89.         A. about the `type' system
  90.         B. the basic type (LONG/PTR)
  91.         C. the simple type (CHAR/INT/LONG)
  92.         D. the array type (ARRAY)
  93.         E. the complex type (STRING/LIST)
  94.         F. the compound type (OBJECT)
  95.         G. initialisation
  96.         H. the essentials of the E typesystem
  97.  
  98.      9. built-in functions
  99.         A. io functions
  100.         B. strings and string functions
  101.         C. lists and list functions
  102.         D. intuition support functions
  103.         E. graphics support functions
  104.         F. system support functions
  105.         G. math and other functions
  106.         H. string and list linking functions
  107.         I. lisp-cells and cell functions
  108.  
  109.     10. library functions and modules
  110.         A. built-in library calls
  111.         B. interfacing to the amiga system with the v39 modules
  112.         C. compiling own modules
  113.         D. the modulecache
  114.  
  115.         11. quoted expressions
  116.         A. quoting and scope
  117.         B. Eval()
  118.         C. built-in functions
  119.  
  120.         12. floating point support
  121.         A. float values
  122.         B. computing with floats
  123.         C. builtin float functions
  124.         D. float implementation issues
  125.  
  126.     13. Exception handling
  127.         A. defining exception handlers (HANDLE/EXCEPT)
  128.         B. using the Raise() function
  129.         C. defining exceptions for built-in functions (RAISE/IF)
  130.         D. use of exception-ID's
  131.  
  132.         14. OO programming
  133.         A. OO features in E
  134.         B. object inheritance
  135.         C. data hiding (EXPORT/PRIVATE/PUBLIC)
  136.         D. methods and virtual methods
  137.  
  138.     15. inline assembly
  139.         A. identifier sharing
  140.         B. the inline assembler compared to a macro assembler
  141.         C. ways using binary data (INCBIN/CHAR..)
  142.         D. OPT ASM
  143.         E. Inline asm and register variables
  144.  
  145.     16. technical and implementation issues
  146.         A. the OPT keyword
  147.         B. small/large model
  148.         C. stack organisation
  149.         D. hardcoded limits
  150.         E. error messages, warnings and the unreferenced check
  151.         F. compiler buffer organisation and allocation
  152.         G. register allocation
  153.  
  154.     17. Essential E Utilities
  155.         A. ShowModule
  156.         B. ShowHunk
  157.         C. Pragma2Module / Iconvert
  158.         D. ShowCache / FlushCache
  159.         E. ecompile.rexx
  160.         F. o2m
  161.         G. E-Yacc
  162.         H. SrcGen
  163.         I. EBuild
  164.  
  165.     18. Appendices
  166.         A. E Grammar description
  167.         B. Tutorial
  168.         C. Mapping E to C/C++/Pascal/Ada/Lisp etc.
  169.  
  170.  
  171.  
  172.  
  173. +-----------------------------------------------------------------------+
  174. |                    0. COMPILER AND INTRODUCTION            |
  175. +-----------------------------------------------------------------------+
  176.  
  177. 0A. introduction
  178. ----------------
  179. E is an object oriented / procedural / unpure functional higher programming
  180. language, mainly influenced by languages such as C++, Ada, Lisp etc. It is
  181. a general-purpose programming language, and the Amiga implementation is
  182. specifically targeted at programming system applications. The number of
  183. features of the language is really to great to sum up entirely (see 0E where
  184. some of the features new in v3 are enlisted), and include:
  185. speed of >20000 lines/minute on a 7 Mhz amiga, inline assembler and linker
  186. integrated into compiler, large set of integrated functions, great module
  187. concept with v39 includes as modules, flexible type-system, quoted
  188. expressions, immediate and typed lists, low-level and object polymorphism,
  189. exception handling, inheritance, data-hiding, methods, multiple return
  190. values, default arguments, register allocation, fast memory manegement,
  191. unification, LISP-Cells, and much more...
  192.  
  193. This is what 'HelloWorld' looks like in E:
  194.  
  195. /* nominated for Most Boring Example */
  196.  
  197. PROC main()
  198.   WriteF('Hello, World!\n')
  199. ENDPROC
  200.  
  201.  
  202. 0B. the distribution
  203. --------------------
  204. The distribution includes:
  205.  
  206. bin/        contains the compiler EC and the support utilities
  207. modules/    Directory containing all Amiga v39 E modules and
  208.         useful tools as linkable modules
  209. docs/        documentation on E
  210. src/        example sources in E
  211.  
  212. This distribution of Amiga E v3.0 including the demo version of the
  213. compiler is FreeWare, and maybe freely copied. The compiler archive some
  214. of you may have received together with this archive, however, is not
  215. FreeWare and should NOT be copied for anyone but yourself.
  216.  
  217. Distributing copies of E for more than the price of disk+postage
  218. (generally <$3), or any other way of distribution with only the
  219. slightest aim of making profit, is not allowed.
  220.  
  221. This distribution should always be distributed as a whole, i.e. in the
  222. form of the original .lha archive. No additions, modifications,
  223. partial distributions or whatever are allowed without my explicit
  224. permission.
  225.  
  226. No guarantees, no warranty. If you manage to drown your pet goldfish
  227. using E, or E fails to be suitable for ordering pizza's, that's
  228. entirely your problem. Whatever happens, don't blame it on me.
  229.  
  230. Fred Fish has special permission to distribute E on his CD-ROM's.
  231.  
  232.  
  233. 0C. demo restrictions and registration
  234. --------------------------------------
  235. The Amiga E distribution is PD, and contains the demo version of
  236. the compiler. registered programmers obtain the full compiler as
  237. a seperate archive, with only "EC" in it.
  238.  
  239. If you have received the registered EC already, you may wish to put
  240. it in the bin directory. The distribution archive may be freely
  241. copied for anyone (see 0B on that), but please make sure you do not
  242. distribute your registered copy of EC to anyone, not even to friends.
  243. I haven't serialised these copies because of the confidence I have
  244. in my registered users, so don't break it. Registration is very
  245. affordable, and v2.1b is still available, so there's no excuse left
  246. for pirating E.
  247.  
  248. So what's "demo" about the included compiler?
  249. The compiler will only spit out executables <12k, above that it
  250. will present you with a "workspace full" error. Other than that
  251. it's fully functional.
  252.  
  253. You are allowed to evaluate this demo for two weeks, after which
  254. you decide either to register or quit using this demo version.
  255.  
  256. updates.
  257. distribution updates can be found in the PD as normal, and updates
  258. to the registered EC will be distributed as patches, also in the PD.
  259.  
  260. ordering a copy.
  261. The basic price is $40.
  262. - substract $5 if you are prepared to receive your registered EC
  263.   per uuencoded E-mail instead of on disk. This requires a _reliable_
  264.   E-mail connection. This is the fastest way to get v3.
  265.  
  266. I will allow payment in some other currencies as well, to simplify
  267. payment for some people. No rare currencies please.
  268.  
  269. examples (US$):                40
  270.  
  271. Dutch Guilders (highly preferred)    65
  272. English Pound Sterling            26
  273. German DeutchMark            60
  274. French Frank                210
  275. Italian Lire                63000
  276.  
  277. NOTE: these are calculated from transaction prices on 30 june 94,
  278. if your currency starts to plummet, you'll have to adjust. making
  279. sure you're $1 above the guilder-price seems ok.
  280.  
  281. Getting the money to me.
  282. This is not simple, since most banks charge a lot for foreign money
  283. transfers. Some options:
  284.  
  285. - Sending cash (preferred). This may sound spooky, but it actually
  286.   is the most succesfull way of getting money across. Changing your
  287.   money to dutch paper-money is always a good idea. If you feel insecure
  288.   about mailing money, most post-offices offer a service that will
  289.   report back to you that everything safely arrived at my place.
  290.  
  291. - Transferring directly to my bank account:
  292.     427875951, ABN-AMRO bank, the netherlands
  293.   or my post-giro account:
  294.     6030387, PostBank, the netherlands
  295.   make sure you cover any transfer costs your bank may charge you.
  296.  
  297. - within Europe, send a EuroCheque (in guilders). I believe there are
  298.   no costs for this, but check locally.
  299.  
  300. - You may choose any other method, but in general realise that it's YOUR
  301.   task to make sure I am able to cash the full amount of money _easily_.
  302.  
  303. - Do **NOT** send CHEQUES. Cheques (other than the EuroCheques above)
  304.   banks here ask $15 tranfer costs for to cash (if I can cash them at all).
  305.  
  306. Make sure you send as complete infos with the money as possible, i.e.
  307. full address, internet E-mail, maybe even Amiga-config etc. I'm not
  308. going to write out one of them silly registration forms here :-)
  309.  
  310. my address: (see 0F)
  311.  
  312.  
  313. 0D. using the compiler
  314. ----------------------
  315.  
  316. To install Amiga E on your system, just copy the whole distribution to
  317. some place in your system, extend your path to the BIN directory, and
  318. assign EMODULES: to the MODULES directory.
  319.  
  320. syntax of the compiler (2.04+):
  321.  
  322. SOURCE/A,REG=NUMREGALLOC/N/K,LARGE/S,SYM=SYMBOLHUNK/S,
  323. NOWARN/S,QUIET/S,ASM/S,ERRLINE/S,ERRBYTE/S,SHOWBUF/S,
  324. ADDBUF/N/K,IGNORECACHE/S,HOLD/S,WB/S,LINEDEBUG/S,OPTI/S:
  325.  
  326. for 1.2 to 2.03:
  327.  
  328. EC [-opts] <sourcefile>
  329.  
  330. As an example we'll compile the program 'HelloWorld.e'. The compiler will
  331. produce an executable 'HelloWorld'.
  332.  
  333. E:>  ec helloworld
  334. Amiga E Compiler/Assembler/Linker v2.4f (c) 91/92/93 $#%!
  335. lexical analysing ...
  336. parsing and compiling ...
  337. no errors
  338. E:>  helloworld
  339. Hello, World!
  340. E:>  list
  341. HelloWorld.e                  89 ----rwed Oggi      17:37:00
  342. helloworld                   656 ----rwed Oggi      17:37:00
  343. 2 files - 4 blocks used
  344. E:>
  345.  
  346. note: the compiler cannot be made resident
  347.  
  348. Last note on compiling the examples: if a program uses module files
  349. for library definitions like:
  350.  
  351. MODULE 'GadTools', 'Reqtools'
  352.  
  353. the compiler needs to know where to find them. Two possible solutions:
  354. 1. you make the assignment "emodules:" to the modules directory (best).
  355. 2. you state in the source code where to look for modules, like:
  356.    OPT DIR='dh0:src/e/modules'
  357.  
  358. Options.
  359. These are standard AmigaDos options. You can see them at any time by typing
  360. 'EC ?'. For 1.2 options the old unix-like switches are used (need to be
  361. written together, preceded by a "-"):
  362.  
  363. LARGE        -l    compiles with large code/data model (see 16A, OPT LARGE).
  364. ASM        -a    puts EC into assembler mode (see 15D, OPT ASM).
  365. NOWARN        -n    suppresses warnings (see 16A, OPT NOWARN)
  366. SYM        -s    adds a symbolhunk to the executable, for use with
  367.             profilers, debuggers, disassemblers etc.
  368. LINEDEBUG    -L    adds a "LINE" debughunk to the executable, for use
  369.             with profilers, debuggers etc.
  370. REG N        -rN    uses N regs per PROC for register-allocation.
  371.             (default is 0 for the time being, read elsewhere
  372.             about how to use this!)
  373. QUIET        -q    if there are no errors or warnings, EC won't output
  374.             anything.
  375. WB        -w    puts wb to front (for scripts)
  376. SHOWBUF        -b    shows buffer memory usage information
  377. ADDBUF X    -mX    forces EC to allocate more memory for its buffers.
  378.             X ranges 1..9, the minimum number of 100k blocks to allocate.
  379.                 default is 1 (never needed).
  380. ERRLINE        -e    give the line# the error was on as returnvalue
  381. ERRBYTE        -E    give the byte-offset in the file the error was on
  382.             as returnvalue
  383. IGNORECACHE    -c    don't use the module-cache in any way
  384. HOLD        -h    wait for a <return> on the commandline before
  385.             exiting EC.
  386. OPTI            enable all optimisations (currently equals REG=5)
  387.  
  388. example:  ec large blabla
  389. compiles blabla.e with large model.
  390. NOTE: in most standard cases you won't need to use any of these options
  391.  
  392.  
  393. 0E. changes from v2.1b to v3.0a
  394. -------------------------------
  395.  
  396. What's new in v3.0a:
  397. [seperated in four sections. for the description of these refer to the
  398.  actual chapter]
  399.  
  400. 1. BIG NEW FEATURES.
  401.  
  402. - compilation to modules [!] (see 10C)
  403. - oo: object inheritance, private/public, methods etc. (see 14A)
  404. - default arguments for PROCs (see 6F) (and some builtins, too).
  405. - multiple return values (see 6G)
  406. - register variables / allocation (see 16G, 15E, ...).
  407. - builtin REALs (see 12)
  408. - NEW operator (see 4K), and END (see 5M) (with superfast memory manegement)
  409. - powerful syntactic variation of SELECT (see 5J)
  410. - unification (see 4L)
  411. - allows for more complex types in OBJECTs, PTR TO <type> etc. (see 8F)
  412.   together with more powerfull dereferencing (see 4F, x.y[a].z etc.)
  413. - garbage collected Lisp-Cells (see 9I)
  414. - function values (call ptrs to PROCs) (see 6H)
  415. - module caching (see 17D, showcache)
  416. - error reconstruction: pinpoint error at exact spot in line
  417. - whole bunch of new builtin functions (see 9A,...)
  418. - whole bunch of useful modules (will get loads more soon)
  419. - various compiler optimisations to make EC significantly faster
  420. - several code optimisations
  421. - intelligent linker / module system (see 10C, amongst others)
  422. - compiler uses a lot less memory.
  423. - symbol and linedebug hunks (see 0D above for switches).
  424. - various utilities, such as EE (Barry Wills great E Editor),
  425.   Build (a make), o2m (converts assembly .o files to modules), E-Yacc etc.
  426. - new docs, GREAT tutorial by Jason Hulance (known as 'The Guide').
  427.  
  428. 2. SMALLER NEW FEATURES.
  429.  
  430. - pointertyping "::" operator (see 4M)
  431. - EXCEPT DO: continue at handler (see 13C)
  432. - EXIT <boolexp> in WHILE/FOR (see 5F)
  433. - single line comments (see 1B)
  434. - for some: os v39 modules.
  435. - character constants may contain "\n\t\e\a" "\0\\\b\q" now. (\q = ")
  436. - warning for flakey "assignments" now with linenum.
  437. - dereferencing a PTR TO <object> with a just a [] results
  438.   in a pointer now (for example x[1] = next object)
  439. - variety of smaller code-optimisations.
  440. - a lot of string/list/io functions now return useful returnvalues (see 9A,...).
  441. - EC's command line is now ReadArgs() style for 2.04+ users (see 0D).
  442. - better line-endings (see 5A)
  443. - several new builtins (see 9A,...)
  444.  
  445. 3. BUGS / PROBLEMS FIXED.
  446.  
  447. - recognises '.e' also on the command line.
  448. - various bugs fixed (and new ones introduced, obviously)
  449. - now also a 'stdin' variable is available
  450. - dereferencing a PTR TO INT with [] would result in an unsigned
  451.   integer instead of a signed one (NOTE: this may change behaviour!)
  452. - EC could crash on missing ENDIFs: fixed.
  453. - CHAR would align incorrectly.
  454. - RAISE accepts negative constants.
  455. - Div() didn't handle negative numbers.
  456. - inline asm bugs: ADD.L ...,Ax became ADDX, various silly little problems.
  457. - StringF documentation was missing, InStr() incorrect.
  458. - SIZEOF handles CHAR/INT/LONG now too
  459. - WaitIMessage() did something silly
  460. - EC wouldn't consume some very large sources (>500k)
  461. - a WHILE or a UNTIL with an IF-exp as boolean could generate wrong code.
  462. - [exp]:CHAR would generate wrong code
  463. - some syntactical bugs could previously go unnoticed
  464. - console would open in READWRITE mode
  465.  
  466. 4. OTHER CHANGES ONE NEEDS TO BE AWARE OF.
  467.  
  468. - v2.1b "-s" option deleted.
  469. - 'OPT' now needs to be first thing in a source; other constructs
  470.   (like 'CONST', 'RAISE') have stricter checking on their position
  471.   in a source.
  472. - EC may generate 'internal errors' for some cases. If this
  473.   happens, report, with source what cause it.
  474. - keyword "IS" is equivalent to "RETURN" directly after a "PROC"
  475. - The inline-assembly register conventions have changed (see 15B)
  476.  
  477.  
  478. Hint for v2.1b users: do a diff over both versions of reference.doc
  479.  
  480.  
  481. 0F. additional information
  482. --------------------------
  483.  
  484. The Amiga E Compiler was developed over the course of more than two and a
  485. half year, after the author's idea of a good programming language, and
  486. a quality amiga-specific compiler for it. It was programmed (as you might
  487. have guessed) in 100% assembly, using the AsmOne assembler v1.02. All other
  488. support programs were written in E itself.
  489.  
  490. Special thanks go to the following people:
  491.  
  492. Barry Wills - for being the best best betatester ever.
  493. Jason Hulance - for his work on 'The Beginners Guide', and betatesting.
  494. Rob Verver - for comments/inspiration.
  495. Erwin van Breemen - for betatesting
  496.  
  497. I also would like to thank the following people for various reasons:
  498.  
  499. Raymond Hoving, Michael Zuchhi, James Cooper, Jens Gelhar, Paolo Silvera,
  500. Jeroen Vermeulen, Jan van den Baard, Joerg Wach, Norman Kraft,
  501. Urban Mueller, Charles McCreary, Olivier Anh, and many more...
  502.  
  503. This compiler was programmed with great care towards reliability, and
  504. even more so the code it generates, additionally it has been tested and
  505. debugged for a long period. However, it is not impossible that it contains
  506. bugs. if you happen to find one, or have other comments/questions,
  507. write me at the address below: I _strongly_ prefer E-mail above
  508. conventional mail.
  509.  
  510. NOTE WELL: due to the immense popularity of the previous version of
  511. Amiga E, I get an almost unreplyable amount of Email, some of which
  512. (>75%) are questions that would not have been necessary if people
  513. read all the docs carefully. What I mean to say is that I like
  514. to receive Email, and I don't mind answering questions and helping
  515. people out with programming problems, but be sure to check all other
  516. information at your disposal (like the Amiga E docs or the RKRM's) to
  517. see if your question is relevant, before mailing me. Especially
  518. questions that are not E specific but Amiga specific should not be
  519. directed to me.
  520.  
  521. registrations (see 0C) and donations are welcome at the following address:
  522.  
  523.  
  524.     Wouter van Oortmerssen ($#%!)
  525.     Levendaal 87
  526.     2311 JG  Leiden
  527.     HOLLAND
  528.  
  529. or better if you have access to Email:
  530.  
  531.     wouter@alf.let.uva.nl        (E-programming support)
  532.     wouter@mars.let.uva.nl        (personal)
  533.     oortmers@gene.fwi.uva.nl    (other)
  534.  
  535.  
  536. +---------------------------------------------------------------+
  537. |                           1. FORMAT                |
  538. +---------------------------------------------------------------+
  539.  
  540. 1A. tabs,lf etc.
  541. ----------------
  542. E-sources are pure ascii format files, with the linefeed <lf> and
  543. semicolon ";" being the separators for two statements. Statements
  544. that have particulary many arguments, may be spread over several lines
  545. by ending a line with a comma (or any other lexical element that can
  546. normally never occur at the end of a line), thus ignoring the following
  547. <lf> (see 5A for line endings). Any lexical element in a source code
  548. file may be separated from another by any number of spaces, tabs etc.
  549.  
  550.  
  551. 1B. comments
  552. ------------
  553. comments may be placed anywhere in a source file where normally a space
  554. would have been correct. They start with '/*' and end with '*/'
  555. and may be nested infinitely. The same goes for one-line comments,
  556. which start with a '->' and end at the first <lf>.
  557.  
  558. /* this, is a comment */
  559. -> this one too.
  560.  
  561.  
  562. 1C. identifiers and types
  563. -------------------------
  564. identifiers are strings that the programmer uses to denote certain
  565. objects, in most cases variables, or even keywords or function names
  566. predefined by the compiler. An identifier may consist of:
  567.  
  568. - upper and lowercase characters
  569. - "0" .. "9" (except as first character)
  570. - "_" (the underscore)
  571.  
  572. All characters are significant, but the compiler just looks at the
  573. first two to identify the type of identifier it is dealing with:
  574.  
  575. both uppercase:               - keyword like IF, PROC etc.
  576.                               - constant, like MAX_LENGTH
  577.                               - assembly mnemonic, like MOVE
  578. first lowercase:              - identifier of variable/label/object etc.
  579. first upper and second lower: - E system function like: WriteF()
  580.                               - library call: OpenWindow()
  581.  
  582. Note that all identifiers obey this syntax, for example:
  583. WBenchToFront() becomes WbenchToFront()
  584.  
  585.  
  586. +---------------------------------------------------------------+
  587. |                      2. IMMEDIATE VALUES            |
  588. +---------------------------------------------------------------+
  589.  
  590. Immediate values in E all evaluate to a 32bit result; the only
  591. difference among these values (A-G) is either their internal
  592. representation, or the fact that they return a pointer rather than
  593. a value.
  594.  
  595. 2A. decimal (1)
  596. ---------------
  597. A decimal value is a sequence of characters "0" .. "9", possibly
  598. preceded by a minus "-" sign to denote negative numbers.
  599. examples: 1, 100, -12, 1024
  600.  
  601. 2B. hexadecimal ($1)
  602. --------------------
  603. A hexadecimal value uses the additional characters "A" .. "F" (or
  604. "a" .. "f") and is preceded by a "$" character.
  605. Examples: $FC, $DFF180, -$ABCD
  606.  
  607. 2C. binary (%1)
  608. ---------------
  609. Binary numbers start with a "%" character and use only "1" and "0"
  610. to form a value.
  611. Examples: %111, %1010100001, -%10101
  612.  
  613. 2D. float (1.0)
  614. ---------------
  615. Floats differ only from normal decimal numbers in that they have
  616. a "." to separate their two parts. Either one may be omitted,
  617. not both. Note that floats have a different internal 32bit (IEEE)
  618. representation (see 12A for more information on floats).
  619. Examples: 3.14159, .1 (=0.1), 1. (=1.0)
  620.  
  621. 2E. character
  622. -------------------
  623. The value of a character (enclosed in double "" quotes) is their
  624. ascii value, i.e. "A" = 65. In E, character immediate values
  625. may be a short string up to 4 characters, for example "FORM",
  626. where the first character "F" will be the MSB of the 32bit
  627. representation, and "M" the LSB (least significant byte).
  628.  
  629. 2F. string ('bla')
  630. ------------------
  631. Strings are any ascii representation, enclosed in single '' quotes.
  632. The value of such a string is a pointer to the first character of it.
  633. More specific: 'bla' yields a 32bit pointer to a memory area where
  634. we find the bytes "b", "l" and "a". ALL strings in E are terminated
  635. by a zero byte.
  636. Strings may contain format signs introduced by a slash "\", either
  637. to introduce characters to the string that are for some reason
  638. not displayable, or for use with string formatting functions
  639. like WriteF(), TextF() and StringF(), or kick2 Vprintf().
  640.  
  641. \n        a linefeed (ascii 10)
  642. \a or ''    an apostrophe ' (the one used for enclosing the string)
  643. \q        a doublequote: "
  644. \e        escape (ascii 27)
  645. \t        tab (ascii 9)
  646. \\        a backslash
  647. \0        a zero byte. Of rare use, as ALL strings are 0-terminated
  648. \b        a carriage return (ascii 13)
  649.  
  650. Additionally, when used with formatting functions:
  651.  
  652. \d    print a decimal number
  653. \h    print a hexadecimal
  654. \s    print a string
  655. \c    print a character
  656. \z    set fill byte to '0' character
  657. \l    format to left of field
  658. \r    format to right of field
  659.  
  660. Field specifiers may follow the \d,\h and \s codes:
  661.  
  662. [x]    specify exact field width x
  663. (x,y)    specify minimum x and maximum y (strings only)
  664.  
  665. Example: print a hexadecimal number with 8 positions and leading zeroes:
  666. WriteF('\z\h[8]\n',num)
  667.  
  668. A string may be extended over several lines by trailing them with a "+"
  669. sign and a <lf>:
  670.  
  671. 'this specifically long string ' +
  672. 'is separated over two lines'
  673.  
  674.  
  675. 2G. lists ([1,2,3]) and typed lists
  676. -----------------------------------
  677. An immediate list is the constant counterpart of the LIST datatype,
  678. just as a 'string' is the constant counterpart for the STRING or
  679. ARRAY OF CHAR datatype. Example:
  680.  
  681. [3,2,1,4]
  682.  
  683. is an expression that has as value a PTR to an already initialised list,
  684. a list as a representation in memory is compatible with an ARRAY OF LONG,
  685. with some extra length information at a negative offset. You may use these
  686. immediate lists anywhere a function expects a PTR to an array of
  687. 32bits values, or a list. Examples:
  688.  
  689. ['string',1.0,2.1]
  690. [WA_FLAGS,1,WA_IDCMP,$200,WA_WIDTH,120,WA_HEIGHT,150,TAG_DONE]
  691.  
  692. (see 9C on list-functions for a discussion on typed-immediate
  693. lists and detailed information).
  694.  
  695.  
  696. 2H. lisp-cells (<a|b>)
  697. ----------------------
  698. (see 9I to read about cells in detail)
  699.  
  700.  
  701. +---------------------------------------------------------------+
  702. |                         3. EXPRESSIONS             |
  703. +---------------------------------------------------------------+
  704.  
  705. 3A. format
  706. ----------
  707. An expression is a piece of code held together by operators, functions
  708. and parentheses to form a value.
  709. They mostly consist of:
  710.  
  711. - immediate values (see 2A,...)
  712. - operators (see 4A,...)
  713. - function calls (see 3D)
  714. - parentheses () (see 3B)
  715. - variables or variable-expressions (see 3C)
  716.  
  717. examples of expressions:
  718. 1
  719. 'hello'
  720. $ABCD+(2*6)+Abs(a)
  721. (a<1) OR (b>=100)
  722.  
  723. 3B. precedence and grouping
  724. ---------------------------
  725. The E language has _no_ precedence whatsoever. This means that
  726. expressions are evaluated left to right. You may change
  727. precedence by parenthesizing some (sub-)expression:
  728. 1+2*3 /* =9 */     1+(2*3) /* =7 */       2*3+1  /* =7 */
  729.  
  730. 3C. types of expressions
  731. ------------------------
  732. There are three types of expressions that may be used for different
  733. purposes;
  734.  
  735. - <var>, consisting of just a variable
  736. - <varexp>, consisting of a variable, possibly with unary operators
  737.   with it, like "++" (increment) "." (member selection) or [] (array
  738.   operator). (see 4D, 4G). It denotes a modifiable expression, like
  739.   Lvalues in C.
  740.   Note that those (unary) operators are not part of any precedence.
  741. - <exp>. This includes <var> and <varexp>, and any other expression.
  742.  
  743. 3D. function calls
  744. ------------------
  745. A function call is a temporary suspension of the current code for a
  746. jump to a function, this may be either a self-written function (PROC),
  747. or a function provided by the system. The format of a function call
  748. is the name of the function, followed by two parentheses () enclosing
  749. zero to unlimited arguments, separated by commas ",". Note that arguments
  750. to functions are again expressions. (see 6A) on how to make your own
  751. functions, (see 9A and 10A)
  752. on built-in functions. Examples:
  753.  
  754. foo(1,2)
  755. Gadget(buffer,glist,2,0,40,80+offset,100,'Cancel')
  756. Close(handle)
  757.  
  758.  
  759. +---------------------------------------------------------------+
  760. |                          4. OPERATORS                |
  761. +---------------------------------------------------------------+
  762.  
  763. 4A. math (+ - * /)
  764. ------------------
  765. These infix operators combine an expression with another value
  766. to yield a new value. Examples:
  767.  
  768. 1+2, MAX-1*5
  769.  
  770. (see 12A on how to overload these operators for use with floats).
  771. "-" may be used as the first part of an expression, with an implied 0,
  772. i.e.    -a    or    -b+1      is legal.
  773. Note that * and / are by default 16bit operators: (see 9G, Mul())
  774.  
  775. 4B. comparison (= <> > < >= <=)
  776. -------------------------------
  777. Equal to math operators, with the difference that they result in either
  778. TRUE (32bit value -1), or FALSE. These can also be overloaded for floats.
  779.  
  780. 4C. logical and bitwise (AND OR)
  781. --------------------------------
  782. These operators either combine truth values to new ones, or perform
  783. bitwise AND and OR operations. Examples:
  784. (a>1) AND ((b=2) OR (c>=3))         /* logical */
  785. a:=b AND $FF                        /* bitwise */
  786.  
  787. 4D. unary (SIZEOF ^ {} ++ -- `)
  788. ---------------------------------
  789. - SIZEOF <objectident>
  790.   simply returns the size of a certain object or CHAR/INT/LONG.
  791.   Example: SIZEOF newscreen + SIZEOF INT
  792. - {<var>}
  793.   Returns the address of a variable or label. This is the operator
  794.   you would use to give a variable as argument to a function by
  795.   reference, instead of by value, which is default in E. See "^".
  796.   Example:  Val(input,{x})
  797. - ^<var>
  798.   The counterpart of {}, writes or reads variables that were given by
  799.   reference, examples:      ^a:=1     b:=^a
  800.   it may also be used to plainly "peek" or "poke" LONG values from
  801.   memory, if <var> is pointer to such a value.
  802.   Example for {} and ^: write your own assignment function;
  803.  
  804.   PROC set(var,exp)
  805.     ^var:=exp
  806.   ENDPROC
  807.  
  808.   and call it with:     set({a},1)     /* equals a:=1 */
  809. - <varexp>++   and  <varexp>--
  810.   Increases (++) or decreases (--) the pointer that is denoted by
  811.   <varexp> by the size of the data it points to. This has the effect
  812.   that that pointer points to the next or previous item. When used
  813.   on variables that are not pointers, these will simply be changed
  814.   by one. Note that ++ always takes effect _after_ the calculation
  815.   of <varexp>, -- always _before_. Examples:
  816.  
  817.   a++          /* return value of a, then increase by one */
  818.   sp[]--       /* decrease pointer sp by 4 (if it were an array of long),
  819.                   and read value pointed at by sp */
  820. - `<exp>
  821.   This is called a quoted expression, from LISP. <exp> is not evaluated,
  822.   but instead returns the address of the expression, which can later be
  823.   evaluated when required. More on this special feature in chapter 11
  824.  
  825. 4E. triple (IF THEN ELSE)
  826. -------------------------
  827. The IF operator has quite the same function as the IF statement, only
  828. it selects between two expressions instead of two statements or blocks
  829. of statements. It equals the x?y:z operator in C.
  830.  
  831. IF <boolexp> THEN <exp1> ELSE <exp2>
  832.  
  833. returns exp1 or exp2, according to boolexp. For example, instead of:
  834.  
  835. IF a<1 THEN b:=2 ELSE b:=3
  836. IF x=3 THEN WriteF('x is 3\n') ELSE WriteF('x is something else\n')
  837.  
  838. write:
  839.  
  840. b:=IF a<1 THEN 2 ELSE 3
  841. WriteF(IF x=3 THEN 'x is 3\n' ELSE 'x is something else\n')
  842.  
  843. 4F. structure (.)
  844. -----------------
  845. <ptr2object>.<memberofobject> builds a <varexp>
  846. The pointer has to be declared as PTR TO <object> or ARRAY OF <object>
  847. (see 8D for these), and the member has to be a legal
  848. object identifier. Note that reading a subobject in an object this
  849. way results in a pointer to that object. Examples:
  850.  
  851. thistask.userdata:=1
  852. rast:=myscreen.rastport
  853.  
  854. If the member you select is of type PTR TO <type>, you may use "."
  855. and "[]" to dereference further values. If you select an ARRAY or
  856. substructure in an OBJECT, the result is again a PTR.
  857.  
  858. 4G. array ([])
  859. --------------
  860. <var>[<indexexp>] (is a <varexp>)
  861. This operator reads the value from the array <var> points to, with
  862. index <indexexp>. The index may be just about any expression.
  863. Note1: "[]" is a shortcut for "[0]"
  864. Note2: with an array of n elements, the index is  0 .. n-1
  865. Examples:
  866.  
  867. a[1]:=10           /* sets second element to 10 */
  868. x:=table[y*4+1]    /* reads from array */
  869. x.y[3]             /* accesses array in an object */
  870.  
  871. 4H. float operator (!)
  872. ----------------------
  873. <exp>!<exp>
  874. Converts expressions from integer to float and back, and
  875. overloads operators + - * / = <> < > <= >= with float equivalents.
  876. (see 12A to read all about floats and this operator).
  877.  
  878. 4I. assignments expressions (:=)
  879. --------------------------------
  880. Assignments (setting a variable to a value) exist as statement
  881. and as expression. The only difference is that the statement
  882. version has the form <varexp>:=<exp> and the expression <var>:=<exp>.
  883. The latter has the value of <exp> as result.
  884. Note that as <var>:= takes on an expression, you will often need
  885. parentheses to force correct interpretation, like:
  886.  
  887. IF mem:=New(100)=NIL THEN error()
  888.  
  889. is interpreted like:
  890.  
  891. IF mem:=(New(100)=NIL) THEN error()
  892.  
  893. which is not what you mean: mem should be a pointer, not a boolean.
  894. but you should write:
  895.  
  896. IF (mem:=New(100))=NIL THEN error()
  897.  
  898. it's a good habit to parenthesize any assignment expression that is
  899. part of anotherone, if not already disambiguated by other constructs
  900. such as "bla(a:=1)", "b:=a:=1" etc.
  901.  
  902. 4J. sequencing (BUT)
  903. --------------------
  904. The sequencing operator "BUT" allows two expressions to be written
  905. in a construction that allows for only one. Often in writing
  906. complex expressions/function calls, one would like to do a second
  907. thing on the spot, like an assignment. Syntax:
  908.  
  909. <exp1> BUT <exp1>
  910.  
  911. this says: evaluate exp1, but return the value of exp2.
  912. Example:
  913.  
  914. myfunc((x:=2) BUT x*x)
  915.  
  916. assign 2 to x and then calls myfunc with x*x. The () around the
  917. assignment are again needed to prevent the := operator from taking
  918. (2 BUT x*x) as an expression.
  919.  
  920. 4K. dynamic memory allocation (NEW)
  921. -----------------------------------
  922. the NEW operator is a powerful operator for dynamic memory allocation.
  923. it has various forms:
  924.  
  925. (assuming DEF p:PTR TO whateverobj, q:PTR TO INT)
  926.  
  927. NEW p
  928.  
  929. is an expression that will allocate zero-ised memory for the object-size
  930. p points to. the resulting pointer will be put in p, and is also
  931. the value of the expression. if NEW fails to get memory, it raises
  932. a "NEW" exception. 'NEW p' is therefore roughly equivalent with:
  933.  
  934. IF (p:=New(SIZEOF whateverobj))=NIL THEN Raise("MEM")
  935.  
  936. with the difference that p never gets any value if an exception
  937. is raised, and that the former is ofcourse an expression, not
  938. a statement
  939.  
  940. but there's more: one can also allocate an array dynamically:
  941.  
  942. NEW p[10]       /* array of 10 objects */
  943.  
  944. NEW q[a+1]      /* array of INT, size is runtime computed */
  945.  
  946. A problem with list [1,2,3] expressions sometimes is that they are static,
  947. and when using these to build large datastructures they would need to be
  948. created at run-time. one may then use the dynamic equivalent to static
  949. lists:
  950.  
  951. p:=[1,2,3]:whateverobj           /* static structure */
  952.  
  953. p:=NEW [1,2,3]:whateverobj       /* dynamicly allocated! */
  954.  
  955. this works with both lists and typed-lists, and also with arrays:
  956.  
  957. NEW [1,2,3]        /* constant-list, dyn. (note: not a like a listvar!) */
  958. NEW [1,2,3]:obj    /* object */
  959. NEW [1,2,3]:INT    /* array of INTs */
  960.  
  961. freeing memory allocated with any variations of NEW is done
  962. automatically at the end of the program, or by hand with Dispose(p)
  963. (note: the only exception is NEW <list>, use <another_function>)
  964.  
  965. If you use NEW [...]:obj, and the number of fields is less than the
  966. one present in the object, additional 0/NIL/"\0" whatever fields will
  967. be added. this allows one to extend objects without getting into
  968. trouble with allocations like these. (note that this is different
  969. from the static [...]:obj)
  970.  
  971. when you use NEW as a statement, multiple pointers may follow, i.e.:
  972.  
  973.     NEW a,b.create(),c
  974.  
  975. is valid.
  976. (see 5M, END)
  977. (see 9F for the fast memory allocation functions NEW makes use of)
  978.  
  979. 4L. unification (<=>)
  980. ---------------------
  981. Unification allows a totally different style of programming
  982. that will be familiar to you if you're used to either Logic
  983. (ProLog), equational or functional (Miranda/Gofer/Haskell)
  984. programming. Most of us when using structures/arrays whatever
  985. are used to get values from it by selection ("." and "[]"),
  986. in these languages however pattern matching is used.
  987.  
  988. in E:
  989.  
  990. exp <=> uni_exp
  991.  
  992. exp can be any expression, but in v3 it's only really useful
  993. if it somehow is a pointer to a list. uni_exp is the pattern
  994. that is used to match exp. All constanst in uni_exp much
  995. match to values in exp, variables are set to their repective
  996. values. if something doesn't match, no variables get a value,
  997. and the expression has the result FALSE. otherwise TRUE.
  998. example:
  999.  
  1000. a:=[1,2,3]
  1001. ...
  1002. IF a <=> [1,x,y] THEN ...
  1003.  
  1004. this will succeed with x=2 and y=3. If list a were to be another
  1005. lenght than 3, the match would fail too. The fact that a is a list
  1006. in the first place is something you need to assure by yourself, EC
  1007. simply tries to fit the uni_exp on whatever value it gets as exp.
  1008. examples of FALSE:
  1009.  
  1010. a <=> [1,x]        -> wrong list-len
  1011. a <=> [1,4,x]        -> 4=2 fails
  1012. 'bla' <=> [1,2]        -> unpredictable result / crash ?
  1013.  
  1014. The fun thing with unification is that you can do very complex matches,
  1015. and that if you take the first field or so as a constant telling what the
  1016. structure is, you have a nice form of dynamic typing. And, all the time
  1017. without using PTRs!
  1018.  
  1019. a slightly nicer example:
  1020.  
  1021. [BLA,[1,'burp'],['bla',"bla"]] <=> [BLA,[1,x],y]
  1022.  
  1023. binds:
  1024.  
  1025. x='burp', y=['bla',"bla"]
  1026.  
  1027. or even:
  1028.  
  1029. IF myexp <=> [PLUS,[MUL,a,1],[SUBS,[PLUS,c,d],e]] THEN RETURN a+c+d-e
  1030.  
  1031. maybe a silly example, but one could imagine doing complex stuff
  1032. like this in a compiler's code-optimizer. it equals this traditional code:
  1033.  
  1034. IF ListLen(myexp)=3
  1035.   IF myexp[]=PLUS
  1036.     IF ListLen(dummy:=myexp[1])=3
  1037.       IF (dummy[]=MUL) AND (dummy[2]=1)
  1038.         a:=dummy[1]
  1039.         IF ListLen(dummy:=myexp[2])=3
  1040.           IF dummy[]=SUBS
  1041.             e:=dummy[2]
  1042.             IF ListLen(dummy2:=dummy[1])=3
  1043.               IF dummy2[]=PLUS
  1044.                 c:=dummy2[1]
  1045.                 d:=dummy2[2]
  1046.                 RETURN a+c+d-e
  1047.               ENDIF
  1048.             ENDIF
  1049.           ENDIF
  1050.         ENDIF
  1051.       ENDIF
  1052.     ENDIF
  1053.   ENDIF
  1054. ENDIF
  1055.  
  1056. only then a bit more optimal. As you see there's a lot of expressive
  1057. power involved in unification as compared to traditional selection-based
  1058. programming.
  1059.  
  1060. For now, the only thing allowed in unification are untyped lists,
  1061. (integer) constansts, variables and LISP-Cells (see 9I for that).
  1062. The future will see this expanded with strings, typed-lists/objects,
  1063. and even expressions [!]
  1064.  
  1065.  
  1066. 4M. pointer typing (::)
  1067. -----------------------
  1068. when you write an expression like 'p' where p is a PTR TO object,
  1069. this allows you to dereference it as such. The pointer typing
  1070. operator allows you to change such a type on the fly:
  1071.  
  1072. DEF p:PTR TO mp            -> message port
  1073.  
  1074. p.sigbit            -> access it
  1075. p::ln.name            -> access pointer as if it were a node
  1076.  
  1077. this is very useful for pointers that can point to different sorts
  1078. of things or objects that are part of eachother, where of course
  1079. only one declaration is possible.
  1080.  
  1081. A second handy use is in OBJECTs that have members declared as LONG,
  1082. which are actually pointers. You may type it on the fly to dereference
  1083. it anyway:
  1084.  
  1085. mywindow.userport::mp.sigbit
  1086.  
  1087. here the window OBJECT has userport defined as LONG, so you wouldn't
  1088. be able to dereference it normally.
  1089.  
  1090.  
  1091. +---------------------------------------------------------------+
  1092. |                          5. STATEMENTS            |
  1093. +---------------------------------------------------------------+
  1094.  
  1095.  
  1096. 5A. format (;)
  1097. --------------
  1098. As suggested in chapter 1A, a statement generally stands in its
  1099. own line, but several of them may be put together on one line
  1100. by separating them with semicolon, or one may be spread over
  1101. more than one line by ending each line in a comma ",". Examples:
  1102.  
  1103. a:=1; WriteF('hello!\n')
  1104. DEF a,b,c,d,                      /* too many args for one line (faked) */
  1105.     e,f,g
  1106.  
  1107. statements may be:
  1108. - assignments
  1109. - conditional statements, for statements and the like, (see 5E-5K)
  1110. - void expressions
  1111. - labels
  1112. - assembly instructions
  1113.  
  1114. The comma is the primary character to show that you do not wish to
  1115. end the statement with the next linefeed, but from v3 on, any token
  1116. that cannot legally be the end of a line causes the statement to
  1117. continue. Furthermore, if not all "[" and "(" occuring in a statement
  1118. have been closed of, a statement will continue also.
  1119. examples of such tokens:
  1120.  
  1121. + - * / =
  1122. < >= <=
  1123. := . <=> ::
  1124. { [ (
  1125. AND OR BUT THEN IS        -> others too, but these are most useful
  1126.  
  1127. example of bracketing:
  1128.  
  1129. a:=[
  1130.     [1,2],
  1131.     [3,4]
  1132.    ]            -> assignment ends here.
  1133.  
  1134. 5B. statement labels and gotos (JUMP)
  1135. -------------------------------------
  1136. Labels are global-scoped identifiers with a ':' added to it, as in:
  1137.  
  1138. mylabel:
  1139.  
  1140. they may be used by instructions such as JUMP, and to reference
  1141. static data. They may be used to jump out of all types of loops (although
  1142. this technique is not encouraged, (see 5F, EXIT), but not out of
  1143. procedures. In normal E programs they are mostly used with inline assembly.
  1144. Labels are always globally visible.
  1145.  
  1146. Usage of JUMP:    JUMP <label>
  1147. continues execution at <label>. You are not encouraged to use this
  1148. instruction, it's there for situations that would otherwise increase
  1149. the complexity of the program. Example:
  1150.  
  1151. IF done THEN JUMP stopnow
  1152.  
  1153. /* other parts of program */
  1154.  
  1155. stopnow:
  1156.  
  1157. 5C. assignment (:=)
  1158. -------------------
  1159. The basic format of an assignment is:   <var> := <exp>
  1160. Examples: a:=1,  a:=myfunc(),  a:=b*3
  1161.  
  1162. In E one can assign multiple variables at once, when <exp> is
  1163. a function that returns multiple returnvalues. (see 6G)
  1164.  
  1165. 5D. assembly mnemonics
  1166. ----------------------
  1167. In E, inline assembly is a true part of the language, they need not
  1168. be enclosed in special "ASM" blocks or the like, as is usual in
  1169. other languages, nor are separate assemblers necessary to assemble
  1170. the code. This also means that it obeys the E syntax rules, etc.
  1171. (see 15A to read all about the inline assembler). Example:
  1172.  
  1173. DEF a,b
  1174. b:=2
  1175. MOVEQ  #1,D0             /* just use some assembly statements */
  1176. MOVE.L D0,a              /* a:=1+b  */
  1177. ADD.L  b,a
  1178. WriteF('a=\d\n',a)       /* a will be 3 */
  1179.  
  1180. 5E. conditional statement (IF)
  1181. ------------------------------
  1182. IF, THEN, ELSE, ELSEIF, ENDIF
  1183.  
  1184. syntax:        IF <exp> THEN <statement> [ ELSE <statement> ]
  1185. or:        IF <exp>
  1186.                   <statements>
  1187.         [ ELSEIF <exp>           /* multiple elseifs may occur */
  1188.                   <statements> ]
  1189.         [ ELSE ]
  1190.                   <statements>
  1191.         ENDIF
  1192.  
  1193. builds a conditional block. Note that there are two general forms of
  1194. this statement, a single-line and a multiple-line version.
  1195.  
  1196.  
  1197. 5F. for-statement (FOR)
  1198. -----------------------
  1199. FOR, TO, STEP, DO, ENDFOR
  1200.  
  1201. syntax:        FOR <var> := <exp> TO <exp> STEP <step> DO <statement>
  1202. or:        FOR <var> := <exp> TO <exp> STEP <step>
  1203.                   <statements>
  1204.         ENDFOR
  1205.  
  1206. builds a for-block, note the two general forms. <step> may be
  1207. any positive or negative constant, excluding 0, and is optional. Example:
  1208.  
  1209. FOR a:=1 TO 10 DO WriteF('\d\n',a)
  1210.  
  1211. The body of FOR may contain EXIT statements with the following syntax:
  1212.  
  1213. EXIT <boolexp>
  1214.  
  1215. Which allows you to exit the loop if boolexp is true.
  1216.  
  1217.  
  1218. 5G. while-statement (WHILE)
  1219. ---------------------------
  1220. WHILE, DO, ENDWHILE
  1221.  
  1222. syntax:        WHILE <exp> DO <statement>
  1223. or:        WHILE <exp>
  1224.                   <statements>
  1225.         ENDWHILE
  1226.  
  1227. builds a while-loop, which is repeated as long as <exp> is TRUE. Note
  1228. the one-line/one-statement version and the multiple line version.
  1229.  
  1230. WHILE may also contain EXIT statements, like FOR.
  1231.  
  1232.  
  1233. 5H. repeat-statement (REPEAT)
  1234. -----------------------------
  1235. REPEAT, UNTIL
  1236.  
  1237. syntax:        REPEAT
  1238.         UNTIL <exp>
  1239.  
  1240. builds a repeat-until block: it will continue to loop this block until
  1241. <exp>=TRUE. Example:
  1242.  
  1243. REPEAT
  1244.   WriteF('Do you really, really wish to exit this program?\n')
  1245.   ReadStr(stdout,s)
  1246. UNTIL StrCmp(s,'yes please!')
  1247.  
  1248.  
  1249. 5I. loop-statement (LOOP)
  1250. -------------------------
  1251. LOOP, ENDLOOP
  1252.  
  1253. syntax:        LOOP
  1254.           <statements>
  1255.         ENDLOOP
  1256.  
  1257. builds an infinite loop.
  1258.  
  1259.  
  1260. 5J. select-case-statement (SELECT)
  1261. ---------------------------------
  1262. SELECT, CASE, DEFAULT, ENDSELECT
  1263.  
  1264. syntax:        SELECT <var>
  1265.         [ CASE <exp>
  1266.           <statements> ]
  1267.         [ CASE <exp>
  1268.           <statements> ]   /* any number of these blocks */
  1269.         [ DEFAULT
  1270.           <statements> ]
  1271.         ENDSELECT
  1272.  
  1273. builds a select-case block. Various expressions will be matched against
  1274. the variable, and only the first matching block executed. If nothing matches,
  1275. a default block may be executed.
  1276.  
  1277. SELECT character
  1278.   CASE 10
  1279.     WriteF('Gee, I just found a linefeed\n')
  1280.   CASE 9
  1281.     WriteF('Wow, this must be a tab!\n')
  1282.   DEFAULT
  1283.     WriteF('Do you know this one: \c ?\n',character)
  1284. ENDSELECT
  1285.  
  1286. next to the old SELECT <var> which works on expressions
  1287. in the CASE statements, E has a SELECT <maxrange> OF <exp>
  1288. which works with constants and or ranges of constants
  1289. in a CASE. not only is this for many applications more
  1290. powerfull, it is also much faster. It assumes however,
  1291. that all CASEs lie within a small integer range from 0 TO n,
  1292. where n is something reasonable, for example 10 or 255 for characters.
  1293.  
  1294. example:
  1295.  
  1296. SELECT 127 OF Fgetc(stream)
  1297.   CASE "\n","\b"
  1298.     WriteF('line ending\n')
  1299.   CASE "\t"," "
  1300.     WriteF('whitepace\n')
  1301.   CASE "0" TO "9"
  1302.     WriteF('Integer\n')
  1303.   CASE "A" TO "Z", "a" TO "z", "_"
  1304.     WriteF('Identifier\n')
  1305.   DEFAULT
  1306.     WriteF('some other character\n')
  1307. ENDSELECT
  1308.  
  1309. DEFAULT will be hit not only for those for which there is no CASE,
  1310. but also for the chars that fall out of the range, i.e. 128 TO 255
  1311. (and >255, and <0).
  1312. note that speed costs: because this SELECT uses a jump-table
  1313. to quickly get at the right CASE, it'll use 2*<maxrange> bytes,
  1314. 256 in this case.
  1315.  
  1316.  
  1317. 5K. increase statement (INC/DEC)
  1318. --------------------------------
  1319. INC, DEC
  1320.  
  1321. syntax:        INC <var>
  1322.         DEC <var>
  1323.  
  1324. short for <var>:=<var>+1 and <var>:=<var>-1. Only difference with
  1325. var++ and var-- is that these are statements, and do not return a value.
  1326.  
  1327.  
  1328. 5L. void expressions (VOID)
  1329. ---------------------------
  1330. VOID
  1331.  
  1332. syntax:        VOID <exp>
  1333.  
  1334. calculates the expression without the result going anywhere. Only useful
  1335. for a clearer syntax, as expressions may be used as statements without
  1336. VOID in E anyway. This may cause subtle bugs though, as "a:=1" assigns
  1337. a the value 1, but "a=1" as a statement will do nothing. E will give you
  1338. a warning if this happens.
  1339.  
  1340.  
  1341. 5M. memory deallocation (END)
  1342. -----------------------------
  1343. END is the complement to NEW. any pointer obtained should be
  1344. deallocated (and only!) with END
  1345.  
  1346.     END a
  1347.  
  1348. or even
  1349.  
  1350.     END a,b,c
  1351.  
  1352. where the arguments are PTRs to some type. END frees the amount of space
  1353. that is being pointed to, so if a is PTR TO LONG it will only free 4
  1354. bytes. so if you allocated a with NEW a[NUM], free it with
  1355.  
  1356.     END a[NUM]
  1357.  
  1358. NIL-pointers may safely be passed to NEW. Pointers are also
  1359. nuked to NIL afterwards.
  1360. If a is a PTR to an object that is an instance of a class, END
  1361. will dynamically get the size to be freed from the class-object,
  1362. so if you have an object of class b which is 32 bytes, put the
  1363. pointer you're freeing with is a baseclass pointer (only 24
  1364. bytes), END will correctly deallocate 32 bytes. this only works
  1365. for classes.
  1366.  
  1367. You can imagine END p as a macro for:
  1368.  
  1369.     IF p
  1370.       p.end()
  1371.       FastDispose(p,p.classobject.virtuallen)
  1372.       p:=NIL
  1373.     ENDIF
  1374.  
  1375. note that the NEW and END make use of the FastNew() and FastDispose()
  1376. functions (described elsewhere) which work quite differently from
  1377. NewR() and Dispose(). (see 9F for details).
  1378.  
  1379.  
  1380. +---------------------------------------------------------------+
  1381. |            6. FUNCTION DEFINITIONS AND DECLARATIONS        |
  1382. +---------------------------------------------------------------+
  1383.  
  1384. 6A. proc definition and arguments (PROC)
  1385. ----------------------------------------
  1386.  
  1387. You may use PROC and ENDPROC to collect statements into your own functions.
  1388. Such a function may have any number of arguments, and several return values.
  1389.  
  1390. PROC, ENDPROC
  1391.  
  1392. syntax:        PROC <label> ( <args> , ... )
  1393.         ENDPROC <returnvalue>, ...
  1394.  
  1395. defines a procedure with any number of arguments. Arguments are of type LONG
  1396. or optionally of type PTR TO <type> (see 8B) and need no further
  1397. declaration. The end of a procedure is designated by ENDPROC. If no
  1398. return value is given, 0 is returned. Example: write a function that
  1399. returns the sum of two arguments:
  1400.  
  1401. PROC add(x,y)         /* x and y are local variables */
  1402. ENDPROC x+y           /* return the result  */
  1403.  
  1404. a short version:
  1405.  
  1406. PROC add(x,y) IS x+y
  1407.  
  1408.  
  1409. 6B. local and global definitions: scope (DEF)
  1410. ---------------------------------------------
  1411. You may define additional local variables besides those which are
  1412. arguments with the DEF statement. The easiest way is simply like:
  1413.  
  1414. DEF a,b,c
  1415.  
  1416. declares the identifiers a, b and c as variables of your function.
  1417. Note that such declarations should be at the start of your function.
  1418.  
  1419. DEF
  1420.  
  1421. syntax:        DEF <declarations>,...
  1422.  
  1423. declares variables. A declaration has one of the forms:
  1424.  
  1425.         <var>
  1426.         <var>:<type>              where <type>=LONG,<objectident>,...
  1427.         <var>[<size>]:<type>      where <type>=ARRAY,STRING,LIST
  1428.  
  1429. (see 8A for more examples, as that is where the types are introduced).
  1430. For now, we'll use the <var> form.
  1431. Arguments to functions are restricted to basic types; (see 8B).
  1432. A declaration of a basic type can have an initialisation, in the current
  1433. version this must be an integer (not an expression):
  1434.  
  1435. DEF a=1,b=2
  1436.  
  1437. A program consists of a set of functions, called procedures, PROCs. Each
  1438. procedure may have Local variables, and the program as a whole may have
  1439. Global variables. At least one procedure should be the PROC main(), as
  1440. this is the module where execution begins. A simple program could look like:
  1441.  
  1442. DEF a, b                            /* definition of global vars */
  1443.  
  1444. PROC main()                         /* all functions in random order */
  1445.   bla(1)
  1446. ENDPROC
  1447.  
  1448. PROC bla(x)
  1449.   DEF y,z                           /* possibly with own local vars */
  1450. ENDPROC
  1451.  
  1452. To summarize, local definitions are the ones you make at the start of
  1453. procedures, and which are only visible within that function. Global
  1454. definitions are made before the first PROC, at the start of your
  1455. source code, and they are globally visible. Global and local variables
  1456. (and of course local variables of two different functions) may have the
  1457. same name, local variables always have priority.
  1458.  
  1459. 6C. endproc/return
  1460. ------------------
  1461. As stated before, ENDPROC marks the end of a function definition, and may
  1462. return a value. Optionally RETURN may be used at any point in the function
  1463. to exit, if used in main(), it will exit the program. (see 9F, CleanUp()).
  1464.  
  1465. RETURN [<returnvalue>]          /* optional */
  1466.  
  1467. Example:
  1468.  
  1469. PROC getresources()
  1470.   /* ... */
  1471.   IF error THEN RETURN FALSE  /* something went wrong, so exit and fail */
  1472.   /* ... */
  1473. ENDPROC TRUE   /* we got this far, so return TRUE */
  1474.  
  1475. a very short version of a function definition is:
  1476.  
  1477. PROC <label> ( <arg> , ... ) RETURN <exp>
  1478.  
  1479. (or "IS" instead of "RETURN")
  1480. These are function definitions that only make small computations, like
  1481. faculty functions and the like:  (one-liners :-)
  1482.  
  1483. PROC fac(n) IS IF n=1 THEN 1 ELSE fac(n-1)*n
  1484.  
  1485.  
  1486. 6D. the `main' function
  1487. -----------------------
  1488. The PROC called main is only of importance because it is called as first
  1489. function; it behaves exactly the same as other functions, and may also
  1490. have local variables. Main has no arguments: the command-line arguments
  1491. are supplied in the system-variable "arg", or can be checked with
  1492. ReadArgs() (dos.library function)
  1493.  
  1494. 6E. built-in system variables
  1495. ----------------------------
  1496. Following global variables are always available in you program,
  1497. they're called system variables.
  1498.  
  1499. arg        As discussed above, contains a pointer to a zero-terminated
  1500.         string, containing the command-line arguments. Don't use this
  1501.         variable if you wish to use ReadArgs() instead.
  1502. stdout        Contains a file-handle to the standard output (and input).
  1503.         If your program was started from the workbench, so no
  1504.         shell-output is available, WriteF() will open a
  1505.         CON: window for you and put its file handle here.
  1506. stdin        file-handle of standard input
  1507. conout        This is where that file handle is kept, and the console
  1508.         window will be automatically closed upon exit of your
  1509.         program. (see 9A, WriteF(), on how to use these two variables
  1510.         properly).
  1511. execbase,    These five variables are always provided with their
  1512. dosbase,    correct values.
  1513. gfxbase,
  1514. intuitionbase
  1515. stdrast        Pointer to standard rastport in use with your program,
  1516.         or NIL. The built-in graphics functions like Line()
  1517.         make use of this variable.
  1518. wbmessage    Contains a ptr to a message you got if you started
  1519.         from wb, else NIL. May be used as a boolean to detect
  1520.         if you started from workbench, or even check any
  1521.         arguments that were shift-selected with your icon.
  1522.         See WbArgs.e in the Src/Args dir how to
  1523.         make good use of wbmessage.
  1524.  
  1525. 6F. default arguments to functions
  1526. ----------------------------------
  1527.  
  1528. default arguments allows you to specify for one or more
  1529. arguments of a procedure which is the default value, if the
  1530. procedure is called with less args than parameters. for example,
  1531. a procedure like:
  1532.  
  1533. PROC bla(a,b=1,c=NIL)
  1534.  
  1535. can be called like:            is equivalent with:
  1536.  
  1537. bla(a,b,c)                bla(a,b,c)
  1538. bla(a,b)                bla(a,b,NIL)
  1539. bla(a)                    bla(a,1,NIL)
  1540.  
  1541. This can be usefull and also express something about the
  1542. procedures function, i.e. that most of the time one would
  1543. call it with NIL anyway, so why not leave it out for clarity.
  1544. That's also why you should not overdo it with D.A.: do not
  1545. start specifying non-sensicall values for procedures
  1546. out of pure laziness, if you feel a certain parameter really
  1547. has no default value.
  1548.  
  1549. to make calls with fewer args unambiguous, D.A. declarations
  1550. can only apply to the last 0..n parameters of a PROC of n parameters.
  1551.  
  1552. for example, illegal is:  PROC bla(a,b=1,c)
  1553.  
  1554. (you should then simply reorder the parameters, of course).
  1555. arguments supplied in a call are filled in from left to right,
  1556. missing arguments are added with D.A.'s as needed.
  1557.  
  1558. 6G. multiple return values
  1559. --------------------------
  1560. In E you can return any number of return values (max 3 in
  1561. Amiga E because of implementation reasons). How?
  1562.  
  1563. RETURN <exp>,<exp>,<exp>                 (or ENDPROC, of course)
  1564.  
  1565. example:
  1566.  
  1567. PROC sincos(rad)
  1568.   DEF sin,cos
  1569.   /* whatever computation is needed */
  1570. ENDPROC sin,cos
  1571.  
  1572. call with:
  1573.  
  1574. s,c:=sincos(3.14)
  1575. s:=sincos(1.00)
  1576.  
  1577. as you can see, there's a new statement of the form:
  1578.  
  1579. <var> , ... := <exp>
  1580.  
  1581. where <exp> makes mostly only sense as function call.
  1582. note two things:
  1583. - you can decide yourself howmany values you wish to receive.
  1584.   this makes sense when the first retval is the main one,
  1585.   and the second/third optional infos, which might only be
  1586.   important to some callers.
  1587. - this form is a _statement_. this means that when you would
  1588.   call sincos() as part of another expression, only the
  1589.   first (the regular) return value is used:   fun(sincos(1.0))
  1590.  
  1591.  
  1592. 6H. function values
  1593. -------------------
  1594. With v3, you can also have functions as values, and pass these
  1595. freely around. they're different from quoted expression, since
  1596. they're called just like normal PROCs. example:
  1597.  
  1598. fun:={myproc}            -> get PROC ptr
  1599.  
  1600. ...
  1601.  
  1602. fun(1,2,3)            -> apply to args, just like normal PROC
  1603.  
  1604. notes:
  1605. - you have to be sure that the PROC you have a ptr to and the
  1606.   number of args are the same. the compiler can't check this for you.
  1607. - even worse: you have to be sure the ptr is a PROC at all.
  1608.   there is a compiler warning that may help you with this.
  1609.  
  1610.  
  1611. +---------------------------------------------------------------+
  1612. |                  7. DECLARATION OF CONSTANTS            |
  1613. +---------------------------------------------------------------+
  1614.  
  1615. 7A. const (CONST)
  1616. -----------------
  1617. syntax:        CONST <declarations>,...
  1618.  
  1619. Enables you to declare a constant. A declaration looks like:
  1620. <ident>=<value>
  1621. constants must be uppercase, and will in the rest of the program be
  1622. treated as <value>. Example:
  1623.  
  1624. CONST MAX_LINES=100, ER_NOMEM=1, ER_NOFILE=2
  1625.  
  1626. You cannot declare constansts in terms of others that are being
  1627. declared in the same CONST statement: put these in the next.
  1628.  
  1629. CONST, ENUM and SET declarations are always global, i.e. it is not
  1630. possible to declare constants local to a PROC. The best place for
  1631. constant declarations is at the top of your source, but EC also
  1632. allows you to put them between two PROCs, for example.
  1633.  
  1634. 7B. enumerations (ENUM)
  1635. -----------------------
  1636. Enumerations are a specific type of constant that need not be given values,
  1637. as they simply range from 0 .. n, the first being 0. At any given point
  1638. in an enumeration, you may use the '=<value>' notation to set or reset
  1639. the counter value. Example:
  1640.  
  1641. ENUM ZERO, ONE, TWO, THREE, MONDAY=1, TUESDAY, WEDNESDAY
  1642.  
  1643. ENUM ER_NOFILE=100, ER_NOMEM, ER_NOWINDOW
  1644.  
  1645. 7C. sets (SET)
  1646. --------------
  1647. Sets are again like enumerations, with the difference that instead of
  1648. increasing a value (0,1,2,...) they increase a bitnumber (0,1,2,...) and
  1649. thus have values like (1,2,4,8,...). This has the added advantage that
  1650. they may be used as sets of flags, as the keyword says.
  1651. Suppose a set like the one below to describe properties of a window:
  1652.  
  1653. SET SIZEGAD,CLOSEGAD,SCROLLBAR,DEPTH
  1654.  
  1655. to initialise a variable to properties DEPTH and SIZEGAD:
  1656.  
  1657. winflags:=DEPTH OR SIZEGAD
  1658.  
  1659. to set an additional SCROLLBAR flag:
  1660.  
  1661. winflags:=winflags OR SCROLLBAR
  1662.  
  1663. and to test if two properties hold:
  1664.  
  1665. IF winflags AND (SCROLLBAR OR DEPTH) THEN /* whatever */
  1666.  
  1667.  
  1668. 7D. built-in constants
  1669. ---------------------
  1670. Following are built-in constants that may be used:
  1671.  
  1672. TRUE,FALSE    Represent the boolean values (-1,0)
  1673. NIL        (=0), the uninitialised pointer.
  1674. ALL        Used with string functions like StrCopy() to copy all characters
  1675. GADGETSIZE    Minimum size in bytes to hold one gadget; (see 9D, Gadget())
  1676. OLDFILE,NEWFILE    Mode-parameters for use with Open()
  1677. EMPTY        used with methods (might be keyword in the future)
  1678. STRLEN        Always has the value of the length of the last immediate
  1679.         string used. Example:
  1680.  
  1681.         Write(handle,'hi folks!',STRLEN)      /* =9 */
  1682.  
  1683.  
  1684.  
  1685. +---------------------------------------------------------------+
  1686. |                           8. TYPES                |
  1687. +---------------------------------------------------------------+
  1688.  
  1689. 8A. about the `type' system
  1690. ---------------------------
  1691. E doesn't have a rigid type-system like Pascal or Modula2, it's even more
  1692. flexible than C's type system: you might as well call it a datatype-system.
  1693. This goes hand in hand with the philosophy that in E all datatypes are
  1694. equal: all basic small values like characters, integers etc. All have
  1695. the same 32bit size, and all other datatypes like arrays and strings
  1696. are represented by 32bit pointers to them. This way, the e compiler can
  1697. generate code in a very polymorphic way.
  1698. The (dis)advantages are obvious:
  1699.  
  1700. disadvantages of the E-type system
  1701. - less compiler checking on silly errors you make
  1702.  
  1703. advantages:
  1704. - low-level polymorphism, easier to make powerful generic functions.
  1705. - flexible way of programming: no problem that some types of return values
  1706.   don't match, no superfluous "casts" etc., no unnecessary errormessages.
  1707. - no hard to find errors when mixing data of different sizes in expressions
  1708.  
  1709.  
  1710. 8B. the basic type (LONG/PTR)
  1711. -----------------------------
  1712. There's only one basic, non-complex variable type in E, which is the
  1713. 32bit type LONG. As this is the default type, it may be declared as:
  1714.  
  1715. DEF a:LONG             or just:            DEF a
  1716.  
  1717. This variable type may hold what's known as CHAR/INT/PTR/LONG types in other
  1718. languages. A special variation of LONG is the PTR type. This type
  1719. is compatible with LONG, with the only difference that it specifies
  1720. to what type it is a pointer. By default, the type LONG is specified
  1721. as PTR TO CHAR. Syntax:
  1722.  
  1723. DEF <var>:PTR TO <type>
  1724.  
  1725. where type is either a simple type or a compound type. Example:
  1726.  
  1727. DEF x:PTR TO INT, myscreen:PTR TO screen
  1728.  
  1729. Note that 'screen' is the name of an object as defined in intuition/screens.m
  1730. For example, if you open your own screen with:
  1731.  
  1732. myscreen:=OpenS(...   etc.
  1733.  
  1734. you may use the pointer myscreen as in 'myscreen.rastport'. However,
  1735. if you do not wish to do anything with the variable until you call
  1736. CloseS(myscreen), you may simply declare it as
  1737.  
  1738. DEF myscreen
  1739.  
  1740. Variable declarations may have optional initialisations, but only
  1741. integer constants, i.e. no full expression:
  1742.  
  1743. DEF a=1, b=NIL:PTR TO textfont
  1744.  
  1745.  
  1746. 8C. the simple type (CHAR/INT/LONG)
  1747. -----------------------------------
  1748. The simple types CHAR (8bit) and INT (16bit) may not be used as types
  1749. for a basic (single) variable; the reason for this must be clear by now.
  1750. However they may be used as data type to build ARRAYs from, set PTRs to,
  1751. use in the definition of OBJECTs etc. See those for examples.
  1752.  
  1753.  
  1754. 8D. the array type (ARRAY)
  1755. --------------------------
  1756. ARRAYs are declared by specifying their length (in bytes):
  1757.  
  1758. DEF b[100]:ARRAY
  1759.  
  1760. this defines an array of 100 bytes. Internally, 'b' is a variable of
  1761. type LONG and a PTR to this memory area.
  1762. Default type of an array-element is CHAR, it may be anything by specifying:
  1763.  
  1764. DEF x[100]:ARRAY OF LONG
  1765. DEF mymenus[10]:ARRAY OF newmenu
  1766.  
  1767. where "newmenu" is an example of a structure, called OBJECTs in E.
  1768. Array access is very easy with:   <var>[<sexp>]
  1769.  
  1770. b[1]:="a"
  1771. z:=mymenus[a+1].mutualexclude
  1772.  
  1773. Note that the index of an array of size n ranges from 0 to n-1,
  1774. and not from 1 to n.
  1775. Note that ARRAY OF <type> is compatible with PTR TO <type>, with the
  1776. only difference that the variable that is an ARRAY is already
  1777. initialised.
  1778.  
  1779.  
  1780. 8E. the complex type (STRING/LIST)
  1781. ----------------------------------
  1782. - STRINGs. Similar to arrays, but different in the respect that they may
  1783.   only be changed by using E string functions, and that they contain
  1784.   length and maxlength information, so string functions may alter them in a
  1785.   safe fashion, i.e: the string can never grow bigger than the memory
  1786.   area it is in. Definition:
  1787.  
  1788.   DEF s[80]:STRING
  1789.  
  1790.   The STRING datatype (called an estring) is backwards compatible with
  1791.   PTR TO CHAR and of course ARRAY OF CHAR, but not the other way around.
  1792.   (see 9B on string functions for more details).
  1793.  
  1794. - LISTs. These may be interpreted as a mix between a STRING and an ARRAY
  1795.   OF LONG. I.e: this data structure holds a list of LONG variables which may
  1796.   be extended and shortened as STRINGs. Definition:
  1797.  
  1798.   DEF x[100]:LIST
  1799.  
  1800.   A powerful addition to this datatype is that it also has a 'constant'
  1801.   equivalent [], like STRINGs have ''. LIST is backward compatible with
  1802.   PTR TO LONG and of course ARRAY OF LONG, but not the other way around.
  1803.   (see 9C and 2G) for more on this.
  1804.  
  1805.  
  1806. 8F. the compound type (OBJECT)
  1807. ------------------------------
  1808. OBJECTs are like a struct/class in C/C++ or a RECORD in pascal. Example:
  1809.  
  1810. OBJECT myobj
  1811.   a:LONG
  1812.   b:CHAR
  1813.   c:INT
  1814. ENDOBJECT
  1815.  
  1816. This defines a data structure consisting of three elements. Syntax:
  1817.  
  1818. OBJECT <objname>
  1819.   <membername> [ : <type> ]           /* any number of these */
  1820. ENDOBJECT
  1821.  
  1822. where type is one of the following:
  1823.  
  1824. CHAR/INT/LONG/<object>
  1825. PTR TO CHAR/INT/LONG/<object>
  1826. ARRAY OF CHAR/INT/LONG/<object>
  1827.  
  1828. (ARRAY is short for ARRAY OF CHAR)
  1829.  
  1830. like DEF declarations, omitting the type means :LONG.
  1831.  
  1832. Note that <membername> need not be a unique identifier,
  1833. it may be in other objects too. There are lots of ways to use objects:
  1834.  
  1835. DEF x:myobj                      /* x is a structure */
  1836. DEF y:PTR TO myobj               /* y is just a pointer to it */
  1837. DEF z[10]:ARRAY OF myobj
  1838.  
  1839. y:=[-1,"a",100]:myobj            /* typed lists */
  1840.  
  1841. IF y.b="a" THEN /* ... */
  1842.  
  1843. z[4].c:=z[d+1].b++
  1844.  
  1845. (see 4F and other parts of chapter 4 for these)
  1846.  
  1847. ARRAYs in objects are always rounded to even sizes, and put on
  1848. even offsets:
  1849.  
  1850. OBJECT mystring
  1851.   len:CHAR, data[9]:ARRAY
  1852. ENDOBJECT
  1853.  
  1854. SIZEOF mystring is 12, and "data" starts at offset 2.
  1855.  
  1856. 'PTR TO' is the only type in OBJECTs that may refer to yet undeclared
  1857. other objects.
  1858.  
  1859. (see 14A for all other OBJECT features that are somehow OO related)
  1860.  
  1861. 8G. initialisation
  1862. ------------------
  1863.  
  1864. 1. Always initialised to NIL (or else, if explicitly stated)
  1865.    - global variables
  1866.      NOTE: for documentation purposes, it's always nicer if you
  1867.      write =NIL in the definitions of variables that you expect to be NIL.
  1868. 2. Initialised to '' and [] resp.
  1869.    - global and local STRINGs
  1870.    - global and local LISTs
  1871. 3. Not initialised
  1872.    - local variables (unless explicitly stated)
  1873.    - global and local ARRAYs
  1874.    - global and local OBJECTs
  1875.  
  1876.  
  1877.  
  1878. 8H. the essentials of the E typesystem
  1879. --------------------------------------
  1880. This section tries to explain how the E typesystem works from
  1881. another perspective.
  1882.  
  1883. Most problems people have while programming in E stem from their incorrect
  1884. view of how the E type-system works, Also, many people have an idea how types
  1885. work from their previous programming language, and try to apply this to E,
  1886. which is often fatal, because E is quite different when it come to types.
  1887.  
  1888. The Type System.
  1889. but E is in essense a TYPELESS language. Indeed, variables may have a type,
  1890. but this is only used as a specification how to dereference a variable when
  1891. it is used as a pointer. In almost ALL other language constructions,
  1892. variables are treated as all being of the same type, namely the 32bit
  1893. typeless value.
  1894.  
  1895. In practise this means that for example in expressions with the exception
  1896. of the ".", "[]" and "++" operators etc., all operators and functions work
  1897. on 32bit values, regardless of wether they represent booleans, integers,
  1898. reals or pointers to something.
  1899.  
  1900. Pointer Types.
  1901. In the E type-system only 4 types exist, PTR TO CHAR, PTR TO INT,
  1902. PTR TO LONG and PTR TO <object>, where <object> is a name of a previously
  1903. defined OBJECT. When a variable (or an object member, as we'll see later)
  1904. is declared as being of this type, It means that if the variable contains
  1905. a value that is a legal pointer, this is how it should be dereferenced.
  1906.  
  1907. LONG, ARRAY etc.
  1908. All other types one may see in a DEF declaration a not really types, as
  1909. they really are only other ways of writing one of the above four. As an
  1910. example, ARRAY OF <type> is just another way of writing PTR TO <type>, with
  1911. the only difference that the former is automatically assigned the address
  1912. of an area of stackspace which is big enough to hold data for the #of
  1913. elements specified in square brackets.
  1914.  
  1915. Here's a table that shows all E 'types' in terms of the basic four:
  1916.  
  1917. ARRAY OF CHAR, ARRAY, STRING, LONG   (are equal to)   PTR TO CHAR
  1918. ARRAY OF INT                         (is equal to)    PTR TO INT
  1919. ARRAY OF LONG, LIST                  (are equal to)   PTR TO LONG
  1920. ARRAY OF <object>, <object>          (are equal to)   PTR TO <object>
  1921.  
  1922. - LONG is for variables that are not intended to be used as a pointer,
  1923.   i.e integers. It's equivalence with PTR TO CHAR is quite logical, as
  1924.   conceptually both talk about things that are measured in units of 1.
  1925.   (for example, "++" has the same effect on both)
  1926. - LIST and STRING are the same as their ARRAY equivalents, in respect
  1927.   to the fact that they're initialised to a piece of stack-space, but
  1928.   they're stack representation is a little more complex to facilitate
  1929.   runtime bounds-checking (when used with the correct functions).
  1930. - an <object> is equivalent to [1]:ARRAY OF <object>. both represent
  1931.   an initialised PTR TO <object>.
  1932.  
  1933. In an OBJECT one can have the same declarations, with the addition of CHAR
  1934. and INT (similar to LONG), and the ommission of LIST and STRING, as these
  1935. are complex objects in their own right, and cannot be part of an object.
  1936.  
  1937. Deferencing.
  1938. Given a pointer p of some type,
  1939.  
  1940. "[]" may index other elements that are sequentially ordered next to
  1941.      the element it is currently pointing to. note that this allows for
  1942.      both positive and negative indices, and also no assumptions are made
  1943.      about where and howmany elements are actually allocated.
  1944.  
  1945. "++" sets the pointer to the next element in memory, "--" to the previous
  1946.      one. note that these operators always operate on the pointer and
  1947.      never on the the element the pointer is pointing to.
  1948.  
  1949. "."  works similar to "[]", only now indexes the pointer by name, i.e. the
  1950.      pointer must be a PTR TO <object>.
  1951.  
  1952. "[]" and "." may be concatenated to a pointer p in any sequence, given the
  1953. fact that the previous resulting value again is known to be of a "PTR TO"
  1954. type.
  1955.  
  1956. One does not need to write out a de-reference in total, as in other
  1957. languages, e.g. if p is an ARRAY OF obj, instead of having to write
  1958. p[index].member you can write just p[index], which logically results
  1959. in in the address of that object. This also explains why p[].member
  1960. is equivalent to p.member, since p[] is the same as p when it points
  1961. to an object.
  1962.  
  1963. Reference Semantics.
  1964. Another type-related issue that makes E somewhat different from other
  1965. languages and thus harder to grasp is it's accent on Reference Semantics
  1966. rather than Value Semantics. I'll try to argue why that's good here.
  1967.  
  1968. Informally, Reference Semantics means that objects in a language (mostly
  1969. other than the simple ones like LONGs) are represented by pointers, while
  1970. Value Semantics treats these objects as just being themselves. An example
  1971. of a language that has only Value Semantics is BASIC, examples of
  1972. languages that have them both are the C/C++ and Pascal type-of languages,
  1973. and examples of Reference only are newer Object Oriented languages,
  1974. functional languages like LISP and ofcourse E.
  1975.  
  1976. Using Reference Semantics doesn't mean being occupied with pointers
  1977. all the time, rather you're worrying about them a lot less then in the
  1978. mixed case or the Value-only case, especially since in real life programs
  1979. most non-trivial data-structures get allocated dynamically which implies
  1980. pointers. The best example of this is LISP, where one programs heavily
  1981. with pointers without noticing. In E, one could easily forget STRING
  1982. is a pointer, given the easy by which one can pass it around to other
  1983. functions; in C often lots of "&" are needed where in the equivalent E
  1984. case non are, and the Oberon equivalent of bla('hallo') looks like
  1985. bla(sys.ADR('hallo')) because the string doesn't represent a pointer,
  1986. but a value as a whole...
  1987.  
  1988.  
  1989. +---------------------------------------------------------------+
  1990. |                     9. BUILT-IN FUNCTIONS            |
  1991. +---------------------------------------------------------------+
  1992.  
  1993. 9A. io functions
  1994. ----------------
  1995.  
  1996.     WriteF(formatstring,args,...)
  1997.     PrintF(formatstring,args,...)
  1998.  
  1999. prints a string (which may contain formatting codes) to stdout. Zero
  2000. to unlimited arguments may be added. Note that, as formatstrings may
  2001. be created dynamically, no check on the correct number of arguments
  2002. is (can be) made. Examples:
  2003.  
  2004. WriteF('Hello, World!\n')    /* just write a lf terminated string */
  2005.  
  2006. WriteF('a = \d \n',a)        /* writes: "a = 123", if a was 123 */
  2007.  
  2008. (see 2F about strings for more).
  2009. NOTE: if stdout=NIL, for example if your program was started from the
  2010. Workbench, WriteF() will create an output window, and put the handle
  2011. in conout and stdout. This window will automatically be closed on
  2012. exit of the program, after the user typed a <return>. WriteF() is the
  2013. only function that will open this window, so if you want to do IO
  2014. on stdout, and want to be sure stdout<>NIL, perform a "WriteF('')"
  2015. as first instruction of your program to ensure output. If you want
  2016. to open a console window yourself, you may do so by placing the resulting
  2017. file handle in the 'stdout' and 'conout' variables, as your window will
  2018. then be closed automatically upon exit. If you wish to close this window
  2019. manually, make sure to set 'conout' back to NIL, to signal E that there's
  2020. no console window to be closed. PrintF() is the same as WriteF only
  2021. uses the v37+ buffered IO.
  2022. both return the length of the string that was printed.
  2023.  
  2024.     Out(filehandle,char)      and      char:=Inp(filehandle)
  2025.  
  2026. Either write or read one single byte to some file or stdout
  2027. if char=-1 then an EOF was reached, or an error occurred.
  2028. Out returns the number of bytes actually written (<>1 is error).
  2029.  
  2030.     len:=FileLength(namestring)
  2031.  
  2032. lets you determine the length of a file you *may* wish to load, and
  2033. also, if it exists (returns -1 upon error/file not found).
  2034.  
  2035.     ok:=ReadStr(filehandle,estring)
  2036.  
  2037. (see 9B)
  2038.  
  2039.     oldout:=SetStdOut(newstdout)
  2040.     oldin:=SetStdIn(newstdin)
  2041.  
  2042. Sets the standard output variable 'stdout'. Equivalent for:
  2043. oldout:=stdout; stdout:=newstdout. Same goes for the stdin
  2044. variable.
  2045.  
  2046.  
  2047.  
  2048. 9B. strings and string functions
  2049. --------------------------------
  2050.  
  2051. E has a datatype STRING. This is a string, from now on called 'Estring',
  2052. that may be modified and changed in size, as opposed to normal 'strings',
  2053. which will be used here for any zero-terminated sequence. Estrings are
  2054. downward compatible with strings, but not the other way around, so if an
  2055. argument requests a normal string, it can be either of them. If an Estring
  2056. is requested, don't use normal strings. Example of usage:
  2057.  
  2058. DEF s[80]:STRING, n                -> s is an estring with a maxlen of 80
  2059. ReadStr(stdout,s)                  -> read input from the console
  2060. n:=Val(s)                          -> get a number out of it
  2061.   -> etc.
  2062.  
  2063. Note that all string functions will handle cases where string tends to
  2064. get longer than the maximum length correctly;
  2065.  
  2066. DEF s[5]:STRING
  2067. StrAdd(s,'this string is longer than 5 characters',ALL)
  2068.  
  2069. s will contain just 'this '.
  2070. A string may also be allocated dynamically from system memory
  2071. with the function String(), (note: the pointer returned from this function
  2072. must always be checked against NIL)
  2073.  
  2074.     s:=String(maxlen)
  2075.  
  2076. DEF s[80]:STRING     is equivalent to     DEF s     and     s:=String(10)
  2077.  
  2078.  
  2079.     bool:=StrCmp(string,string,len=ALL)
  2080.  
  2081. compares two strings. len must be the number of bytes to compare,
  2082. or 'ALL' if the full length is to be compared. Returns TRUE or FALSE
  2083. (len is a default argument (see 6F))
  2084.  
  2085.     StrCopy(estring,string,len=ALL)
  2086.  
  2087. copies the string into the estring. If len=ALL, all will be copied.
  2088. returns the estring.
  2089.  
  2090.     StrAdd(estring,string,len=ALL)
  2091.  
  2092. same as StrCopy(), only now the string is concatenated to the end.
  2093. returns the estring.
  2094.  
  2095.     len:=StrLen(string)
  2096.  
  2097. calculates the length of any zero-terminated string
  2098.  
  2099.     len:=EstrLen(estring)
  2100.  
  2101. returns the length of an estring
  2102.  
  2103.     max:=StrMax(estring)
  2104.  
  2105. returns the maximum length of a estring
  2106.  
  2107.         StringF(estring,fmtstring,args,...)
  2108.  
  2109. similar to WriteF, only now output goes to estring instead of stdout.
  2110. example:
  2111.  
  2112. StringF(s,'result: \d\n',123)
  2113.  
  2114. 's' will be 'result: 123\n'
  2115. returns the estring, and length as second returnvalue.
  2116.  
  2117.     RightStr(estring,estring,n)
  2118.  
  2119. fills estring with the last n characters of the second estring
  2120. returns the estring.
  2121.  
  2122.     MidStr(estring,string,pos,len=ALL)
  2123.  
  2124. copies any number of characters (including all if len=ALL) from
  2125. position pos in string to estring
  2126. NOTEZ BIEN: in all string related functions where a position in a
  2127. string is used, the first character in a string has position 0,
  2128. not 1, as is common in languages like BASIC.
  2129. returns the estring.
  2130.  
  2131.     value,read:=Val(string,read=NIL)
  2132.  
  2133. finds an integer encoded in ascii out of a string. Leading spaces/tabs
  2134. etc. will be skipped, and also hexadecimal numbers (1234567890ABCDEFabcdef)
  2135. and binary numbers (01) may be read this way if they are preceded by a
  2136. "$" or a "%" sign respectively. A minus "-" may indicate a negative integer.
  2137. Val() returns the number of characters read in the second argument, which
  2138. must be given by reference (<-!!!), or can be received as second returnvalue.
  2139. If "read" returns 0 (value will be 0 too) then the string did not contain an
  2140. integer, or the value was too sizy to fit in 32bit. "read" may be NIL.
  2141.  
  2142. examples of strings that would be parsed correctly:
  2143. '-12345', '%10101010', '   -$ABcd12'
  2144.  
  2145. these would return both as "value" and in read a 0:
  2146. '', 'hello!'
  2147.  
  2148.  
  2149.     foundpos:=InStr(string1,string2,startpos=0)
  2150.  
  2151. searches string1 for the occurrence of string2, possibly starting from
  2152. another position than 0. Returned is the offset at which the substring
  2153. was found, else -1.
  2154.  
  2155.     newstringadr:=TrimStr(string)
  2156.  
  2157. returns the *address* of the first character in a string, i.e., after
  2158. leading spaces, tabs etc.
  2159.  
  2160.     UpperStr(string)     and      LowerStr(string)
  2161.  
  2162. changes the case of a string.
  2163. TAKE NOTE: these functions modify the contents of 'string', so they may
  2164. only be used on estrings, and strings that are part of your programs data.
  2165. Effectively this means that if you obtain the address of a string through
  2166. some amiga-system function, you must first StrCopy() it to a string of
  2167. your program, then use these functions.
  2168. they return the string.
  2169.  
  2170.     ok:=ReadStr(filehandle,estring)
  2171.  
  2172. will read a string (ending in ascii 10) from any file or stdout.
  2173. ok contains -1 if an error occurred, or an EOF was reached.
  2174. Note: the contents of the string read so far is still valid.
  2175. Also note that, like Inp() Out(), etc. this function makes use
  2176. of unbuffered 1.3 style IO, and thus may be slow. The dos.library
  2177. Fgets() function forms a nice alternative.
  2178.  
  2179.     SetStr(estring,newlen)
  2180.  
  2181. manually sets the length of a string. This is only handy when you read
  2182. data into the estring by a function other then an E string function,
  2183. and want to continue using it as an Estring. For example, after
  2184. using a function that just puts a zero-terminated string at the
  2185. address of estring, use   SetStr(mystr,StrLen(mystr))  to make
  2186. it manipulatable again
  2187.  
  2188.     AstrCopy(string1,string2,size)
  2189.  
  2190. 'Array String Copy' copies string2 into the memory area denoted by string1.
  2191. string1 is typically not an estring but an ARRAY. size is the total #of chars
  2192. string1 can hold, i.e. if you write 5 and string2='helloworld', string1 will
  2193. be 'hell' + 0termination.
  2194.  
  2195.     order:=OstrCmp(string1,string2,max=ALL)
  2196.  
  2197. 'Ordered String Compare' returns 1 if string2>string1, 0 for equal and -1
  2198. for less. only max chars are compared.
  2199.  
  2200. for string linking functions (see 9H)
  2201.  
  2202.  
  2203. 9C. lists and list functions
  2204. ----------------------------
  2205.  
  2206. Lists are like strings, only they consist of LONGs, not CHARs.
  2207. They may also be allocated either global, local or dynamic:
  2208.  
  2209. DEF mylist[100]:LIST         /* local or global */
  2210. DEF a
  2211. a:=List(10)                  /* dynamic */
  2212.  
  2213. (note that in the latter case, pointer 'a' may contain NIL)
  2214. Just as strings may be represented as constants in expressions, lists
  2215. have their constant equivalent:
  2216.  
  2217. [1,2,3,4]
  2218.  
  2219. The value of such an expression is a pointer to a ready initialised list.
  2220. Special feature is that they may have dynamic parts, i.e, which will
  2221. be filled in at runtime:
  2222.  
  2223. a:=3
  2224. [1,2,a,4]
  2225.  
  2226. moreover, lists may have some other type than the default LONG, like:
  2227.  
  2228. [1,2,3]:INT
  2229. [65,66,67,0]:CHAR                    /* equivalent with   'ABC'   */
  2230. ['topaz.font',8,0,0]:textattr
  2231. OpenScreenTagList(NIL,[SA_TITLE,'MyScreen',TAG_DONE])
  2232.  
  2233. As shown in the latter examples, lists are extremely useful with
  2234. system functions: they are downward compatible with an ARRAY OF LONG,
  2235. and object-typed ones can be used wherever a system function needs
  2236. a pointer to some structure, or an array of those.
  2237. Taglists and vararg functions may also be used this way.
  2238. NOTEZ BIEN: all list functions only work with LONG lists, typed-lists
  2239. are only convenient in building complex data structures and expressions.
  2240.  
  2241. As with strings, a certain hierarchy holds:
  2242. list variables -> constant lists -> array of long/ptr to long
  2243. When a function needs an array of long you might just as well give a list
  2244. as argument, but when a function needs a listvar, or a constant list,
  2245. then an array of long won't do.
  2246.  
  2247. It's important that one understands the power of lists and in particular
  2248. typed-lists: these can save you lots of trouble when building just
  2249. about any data-structure. Try to use these lists in your own programs,
  2250. and see what function they have in the example-programs.
  2251.  
  2252. summary:
  2253.  
  2254. [<item>,<item>,... ]        immediate list (of LONGs, use with listfuncs)
  2255. [<item>,<item>,... ]:<type>    typed list (just to build data structures)
  2256.  
  2257. If <type> is a simple type like INT or CHAR, you'll just have the
  2258. initialised equivalent of ARRAY OF <type>, if <type> is an object-name,
  2259. you'll be building initialised objects, or ARRAY OF <object>, depending
  2260. on the length of the list.
  2261.  
  2262. If you write    [1,2,3]:INT   you'll create a data structure of 6 bytes,
  2263. of 3 16bit values to be precise. The value of this expression then
  2264. is a pointer to that memory area. Same works if, for example, you have
  2265. an object like:
  2266.  
  2267. OBJECT myobject
  2268.   a:LONG, b:CHAR, c:INT
  2269. ENDOBJECT
  2270.  
  2271. writing    [1,2,3]:myobject     would then mean creating a data structure
  2272. in memory of 8 bytes, with the first four bytes being a LONG with value 1,
  2273. the following byte a CHAR with value 2, then a pad byte, and the last
  2274. two bytes an INT (2 bytes) with value 3. you could also write:
  2275.  
  2276. [1,2,3,4,5,6,7,8,9]:myobject
  2277.  
  2278. you would be creating an ARRAY OF myobject with size 3. Note that such
  2279. lists don't have to be complete (3,6,9 and so on elements), you may
  2280. create partial objects with lists of any size
  2281.  
  2282. One last note on data size: on the amiga, you may rely on the fact that
  2283. a structure like 'myobject' has size 8, and that it has a pad byte
  2284. to have word (16bit) alignment. It is however very likely that an
  2285. E-compiler for 80x86 architectures will not use the pad byte and make
  2286. it a 7byte structure, and that an E-compiler for a sun-sparc architecture
  2287. (if I'm not mistaken) will try to align on 32bit boundaries, thus make
  2288. it a 10 or 12 byte structure. Some microprocessors (they are rare, but
  2289. they exist) even use (36:18:9) as numbers of bits for their types
  2290. (LONG:INT:CHAR), instead of (32:16:8) as we're used to. So don't make too
  2291. great an assumption on the structure of OBJECTs and LISTs if you want to
  2292. write code that stands a chance of being portable or doesn't rely on side
  2293. effects.
  2294.  
  2295.     ListCopy(listvar,list,num=ALL)
  2296.  
  2297. Copies num elements from list to listvar. example:
  2298. DEF mylist[10]:LIST
  2299. ListCopy(mylist,[1,2,3,4,5],ALL)
  2300. returns listvar.
  2301.  
  2302.     ListAdd(listvar,list,num=ALL)
  2303.  
  2304. Copies num items of list to the tail of listvar.
  2305. returns listvar.
  2306.  
  2307.     ListCmp(list,list,num=ALL)
  2308.  
  2309. Compares two lists, or some part of them.
  2310.  
  2311.     len:=ListLen(list)
  2312.  
  2313. Returns length of list, like     ListLen([a,b,c])    would return 3
  2314.  
  2315.     max:=ListMax(listvar)
  2316.  
  2317. returns maximum possible length of a listvar.
  2318.  
  2319.     value:=ListItem(list,index)
  2320.  
  2321. functions as    value:=list[index]    with the difference that
  2322. list may also be a constant value instead of a pointer. This is
  2323. very usefull in situations like this where we directly want to
  2324. use a list of values:
  2325.  
  2326. WriteF(ListItem(['ok!','no mem!','no file!'],error))
  2327.  
  2328. this prints an errormessage according to "error". it's similar to:
  2329.  
  2330. DEF dummy:PTR TO LONG
  2331. dummy:=['ok!','no mem!','no file!']
  2332. WriteF(dummy[error])
  2333.  
  2334.     SetList(listvar,newlen)
  2335.  
  2336. manually sets the length of a list. This will only be useful when you read
  2337. data into the list by a function other then a list-specific function,
  2338. and want to continue using it as a true list.
  2339.  
  2340. for list functions that make use of quoted expressions (see 11C).
  2341. for list linking functions (see 9H).
  2342.  
  2343.  
  2344. 9D. intuition support functions
  2345. -------------------------------
  2346.  
  2347.     wptr:=OpenW(x,y,width,height,IDCMP,wflags,title,
  2348.                     screen,sflags,gadgets,taglist=NIL)
  2349.  
  2350. creates a window where wflags are flags for window layout
  2351. (like BACKDROP, SIMPLEREFRESH e.d, usually $F) and sflags are
  2352. for specifying the type of screen to open on (1=wb,15=custom).
  2353. screen must only be valid if sflags=15, else NIL will do.
  2354. gadgets may point to a glist structure, which you can easily
  2355. create with the Gadget() function, else NIL.
  2356.  
  2357.     CloseW(wptr)
  2358.  
  2359. closes that screen again. Only difference from CloseWindow()
  2360. is that it accepts NIL-pointers and sets stdrast back to NIL.
  2361.  
  2362.     sptr:=OpenS(width,height,depth,sflags,title,taglist=NIL)
  2363.  
  2364. opens a custom screen for you. depth is number of bitplanes (1-6, 1-8 AGA).
  2365.  
  2366.     CloseS(sptr)
  2367.  
  2368. as CloseW(), now for screens.
  2369.  
  2370.     nextbuffer:=Gadget(buffer,glist,id,flags,x,y,width,string)
  2371.  
  2372. [warning: this function is a bit out of date]
  2373. This function creates a list of gadgets, which can then be put in your
  2374. window by giving them as an argument to OpenW(), or afterwards with
  2375. intuition functions like AddGlist().
  2376. buffer is mostly an ARRAY of at least GADGETSIZE bytes to hold all the
  2377. structures associated with one gadget, id is any number that may help you
  2378. remember which gadget was pressed when an IntuiMessage arrives.
  2379. Flags are: 0=normal gadget, 1=boolean gadget, 3=boolean gadget that is
  2380. selected. Width is width in pixels, that should be large enough to hold
  2381. the string, which will be auto-centered. glist should be NIL for the first
  2382. gadget, and glistvar for all others, so E may link all gadgets.
  2383. The function returns a pointer to the next buffer (=buffer+GADGETSIZE).
  2384. Example for three gadgets:
  2385.  
  2386. CONST MAXGADGETS=GADGETSIZE*3
  2387.  
  2388. DEF buf[MAXGADGETS]:ARRAY, next, wptr
  2389.  
  2390. next:=Gadget(buf,NIL,1,0,10,20,80,'bla')   /* the 1st gadget */
  2391. next:=Gadget(next,buf,... )
  2392. next:=Gadget(next,buf,... )                /* any amount linked 2 1st */
  2393.  
  2394. wptr:=OpenW( ...,buf)
  2395.  
  2396.     code:=Mouse()
  2397.  
  2398. gives you the current state of all 2 or 3 mouse buttons; left=1,
  2399. right=2 and middle=4. If for example code=3 then left and right were
  2400. pressed together.
  2401. NOTEZ BIEN: this is not a real intuition function, if you want to
  2402. know about mouse-events the proper way, you'll have to check the
  2403. intuimessages that your window receives. This is the only E
  2404. function that directly checks the hardware, and thus only usefull
  2405. in demo-like programs and for testing. (DO NOT USE THIS FUNCTION
  2406. IN PROGRAMS THAT ARE SUPPOSED TO WORK UNDER THE OS)
  2407.  
  2408.     bool:=LeftMouse(win)     WaitLeftMouse(win)
  2409.  
  2410. intuition Mouse() alternatives for programs that only want to test for
  2411. a mouseclick.
  2412.  
  2413.     x:=MouseX(win)     y:=MouseY(win)
  2414.  
  2415. enables you to read the mouse coordinates. win is the window
  2416. they need to be relative to.
  2417.  
  2418.     class:=WaitIMessage(window)
  2419.  
  2420. This function makes it easier to just wait for a window event. It simply
  2421. waits until a intuimessage arrives, and returns the class of the event.
  2422. It stores other variables like code and qualifiers as private global
  2423. variables, for access with functions described below.
  2424. WaitIMessage() represents the following code:
  2425.  
  2426. PROC waitimessage(win:PTR TO window)
  2427.   DEF port,mes:PTR TO intuimessage,class,code,qual,iaddr
  2428.   port:=win.userport
  2429.   IF (mes:=GetMsg(port))=NIL
  2430.     REPEAT
  2431.       WaitPort(port)
  2432.     UNTIL (mes:=GetMsg(port))<>NIL
  2433.   ENDIF
  2434.   class:=mes.class
  2435.   code:=mes.code             /* stored internally */
  2436.   qual:=mes.qualifier
  2437.   iaddr:=mes.iaddress
  2438.   ReplyMsg(mes)
  2439. ENDPROC class
  2440.  
  2441. as you see, it gets exactly one message, and does not forget about
  2442. multiple messages arriving in one event, if called more than once.
  2443. For example, say you opened a window that displays something and just
  2444. waits for a closegadget (you specified IDCMP_CLOSEWINDOW only):
  2445.  
  2446. WaitIMessage(mywindow)
  2447.  
  2448. or, you have a program that waits for more types of events, handles
  2449. them in a loop, and ends on a closewindow event:
  2450.  
  2451. WHILE (class:=WaitIMessage(win))<>IDCMP_CLOSEWINDOW
  2452.   /* handle other classes */
  2453. ENDWHILE
  2454.  
  2455.     code:=MsgCode()    qual:=MsgQualifier()    iaddr:=MsgIaddr()
  2456.  
  2457. These all supply you with the private global variables as mentioned
  2458. before. the values returned are all defined by the most recent call
  2459. to WaitIMessage(). Example:
  2460.  
  2461. IF class:=IDCMP_GADGETUP
  2462.   mygadget:=MsgIaddr()
  2463.   IF mygadget.userdata=1 THEN  /* ... user pressed gadget #1 */
  2464. ENDIF
  2465.  
  2466.  
  2467.  
  2468. 9E. graphics support functions
  2469. ------------------------------
  2470.  
  2471. All graphics support functions that do not explicitly ask for a rastport,
  2472. make use of the system-variable 'stdrast'. It is automatically defined by
  2473. the last call to OpenW() or OpenS(), and is set to NIL by CloseW() and
  2474. CloseS(). Calling these routines while stdrast is still NIL is legal.
  2475. stdrast may be manually set by SetStdRast() or stdrast:=myrast
  2476.  
  2477.     Plot(x,y,colour=1)
  2478.  
  2479. Draws a single dot on your screen/window in one of the colours available.
  2480. colour ranges from 0-255, or 0-31 on pre-AGA machines.
  2481.  
  2482.     Line(x1,y1,x2,y2,colour=1)
  2483.  
  2484. Draws a line
  2485.  
  2486.     Box(x1,y1,x2,y2,colour=1)
  2487.  
  2488. Draws a box
  2489.  
  2490.     Colour(foreground,background=0)
  2491.  
  2492. sets the colours for all graphics functions (from the library) that
  2493. do not take a colour as argument. This is the colour *register*
  2494. (i.e 0-31) and not colour *value*
  2495. NOTE: functions that have "colour" as an argument, change the Apen
  2496. of stdrast.
  2497.  
  2498.     TextF(x,y,formatstring,args,...)
  2499.  
  2500. exactly the same function as WriteF(), only outputs to some (x,y) on
  2501. your stdrast, instead of stdout. (see 9A, WriteF() and strings in the language
  2502. reference). returns the length of the resulting string.
  2503.  
  2504.     oldrast:=SetStdRast(newrast)
  2505.  
  2506. changes the output rastport of the E graphics functions
  2507.  
  2508.     SetTopaz(size=8)
  2509.  
  2510. lets you set the font of the rastport "stdrast" to topaz, just to be sure
  2511. that some custom system font of the user won't skrew up your window layout.
  2512. size is of course 8 or 9. Only to be used as last resort if you can't
  2513. support font-sensitivity.
  2514.  
  2515.     SetColour(screen,colourreg,r,g,b)
  2516.  
  2517. set colour register (0..255) of screen to certain RGB values.
  2518. each rgb value has a range of 0..255, i.e. 24bit colour. this
  2519. function will automatically rescale to 12bit colour if no AGA
  2520. is present, and also use the correct function.
  2521.  
  2522.  
  2523. 9F. system support functions
  2524. ----------------------------
  2525.  
  2526.     bool:=KickVersion(vers)
  2527.  
  2528. Will give TRUE if the kickstart in the machine your program is running
  2529. on is equal or higher than vers, else FALSE
  2530.  
  2531.     mem:=New(n)
  2532.  
  2533. This dynamically creates an array (or memory area, if you wish) of
  2534. n bytes. Difference with AllocMem() is that it is called automatically
  2535. with flags $10000 (i.e cleared mem, any type) and that no calls to
  2536. Dispose() are necessary, as it is linked to a memory list that is
  2537. automatically de-allocated upon exit of your program.
  2538. (see 4K, also)
  2539.  
  2540.     mem:=NewR(n)
  2541.  
  2542. same as New(), only now automatically raises the "MEM" exception
  2543. instead of return if no memory could be allocated.
  2544.  
  2545.     mem:=NewM(n,flags)
  2546.  
  2547. same as NewR(), but also allows you to specify flags (MEMF_CHIP etc.)
  2548.  
  2549.     Dispose(mem)
  2550.  
  2551. Frees any mem allocated by New(). You only have to use this function
  2552. if you explicitly wish to free memory _during_ your program, as all
  2553. is freed at the end anyway.
  2554.  
  2555.     CleanUp(returnvalue=0)
  2556.  
  2557. Exits the program from any point. It is the replacement for the DOS
  2558. call Exit(): never use it! instead use CleanUp(), which allows
  2559. for the deallocation of memory, closing libraries correctly etc.
  2560. The return value will be given to dos as returncode.
  2561.  
  2562.     amount:=FreeStack()
  2563.  
  2564. returns the amount of free stack space left. This should always be 1000 or
  2565. more. (see 16C on how E organizes its stack. If you don't do heavy recursion,
  2566. you need not worry about your free stack space.
  2567.  
  2568.     bool:=CtrlC()
  2569.  
  2570. Returns TRUE if Ctrl-C was pressed since you last checked, else FALSE.
  2571. This only works for programs running on a console, i.e. cli-programs.
  2572.  
  2573. Example of how these last three functions may be used:
  2574.  
  2575. /* calculate faculty from command-line argument */
  2576.  
  2577. OPT STACK=100000
  2578.  
  2579. PROC main()
  2580.   DEF num,r
  2581.   num:=Val(arg,{r})
  2582.   IF r=0 THEN WriteF('bad args.\n') ELSE WriteF('result: \d\n',fac(num))
  2583. ENDPROC
  2584.  
  2585. PROC fac(n)
  2586.   DEF r
  2587.   IF FreeStack()<1000 OR CtrlC() THEN CleanUp(5)    /* xtra check */
  2588.   IF n=1 THEN r:=1 ELSE r:=fac(n-1)*n
  2589. ENDPROC r
  2590.  
  2591. Of course, this recursion will hardly run out of stack space, and when it
  2592. does, it's halted by FreeStack() so fast you won't have time to press
  2593. CtrlC, but it's the idea that counts here.
  2594. A definition of fac(n) like:
  2595.  
  2596. PROC fac(n) IS IF n=1 THEN 1 ELSE fac(n-1)*n
  2597.  
  2598. would be less safe.
  2599.  
  2600.  
  2601.     mem:=FastNew(size)    FastDispose(mem,size)
  2602.  
  2603. FastNew() and FastDispose() are replacements for NewR(size) and
  2604. Dispose(ptr) (they are used by NEW and END). this is what they have
  2605. in common:
  2606. - "NEW" exceptions may be Raised
  2607. - memory is always cleared
  2608. - auto-dealloc at end of program
  2609. but the following differences should be noted (positive):
  2610. - they are varying from 10 to 50 times faster (!)
  2611. - they use way less memory for small objects
  2612. - they do not fragment memory
  2613. [all this is for objects <=256 bytes, for bigger ones NewR() and
  2614.  Dispose() are used].
  2615. negative:
  2616. - they do not free mem, but recycle it.
  2617. - FastDispose() needs exact size of allocation. END also.
  2618.  
  2619.  
  2620. 9G. math and other functions
  2621. -------------------
  2622.  
  2623.     a:=And(b,c)           a:=Or(b,c)           a:=Not(b)
  2624.     a:=Eor(b,c)
  2625.  
  2626. These work with the usual operations, boolean as well as arithmetic.
  2627. Note that for And() and Or() an operator exists.
  2628.  
  2629.     a:=Mul(b,c)           a:=Div(a,b)
  2630.  
  2631. Performs the same operation as the '*' and '/' operators, but now in
  2632. full 32bit. For speed reasons, normal operations are 16bit*16bit=32bit
  2633. and 32bit/16bit=16bit. This is sufficient for nearly all calculations,
  2634. and where it's not, you may use Mul() and Div(). NOTE: in the Div
  2635. case, a is divided by b, not b by a.
  2636.  
  2637.         bool:=Odd(x)          bool:=Even(x)
  2638.  
  2639. Return TRUE or FALSE if some expression is Odd or Even
  2640.  
  2641.     Min(a,b)    Max(a,b)
  2642.  
  2643. compute min and max of the two given ints.
  2644.  
  2645.     randnum:=Rnd(max)    seed:=RndQ(seed)
  2646.  
  2647. Rnd() computes a random number from an internal seed in range 0 .. max-1.
  2648. For example,  Rnd(1000)   returns an integer from 0..999
  2649. To initialise the internal seed, call Rnd() with a negative value;
  2650. the Abs() of that value will be the initial seed.
  2651.  
  2652. RndQ() computes a random number "Q"uicker than Rnd() does, but returns
  2653. only full range 32bit random numbers. Use the result as the seed for
  2654. the next call, and for startseed, use any large value, like $A6F87EC1
  2655.  
  2656.     absvalue:=Abs(value)
  2657.  
  2658. computes the absolute value.
  2659.  
  2660.     s:=Sign(v)
  2661.  
  2662. computes the sign of v, i.e. returns -1,0,1
  2663.  
  2664.     a,b:=Mod(c,d)
  2665.  
  2666. Divides 32bit c by 16bit d and returns 16bit modulo a and optionally
  2667. a 16bit result of the division b.
  2668.  
  2669.     x:=Shl(y,num)         x:=Shr(y,num)
  2670.  
  2671. shifts y num bits to left or right (set new bits to 0).
  2672.  
  2673.     a:=Long(adr)          a:=Int(adr)          a:=Char(adr)
  2674.  
  2675. peeks into memory at some address, and returns the value found. This
  2676. works with 32, 16 and 8 bit values respectively. Note that the compiler does
  2677. not check if 'adr' is valid. These functions are available in E for
  2678. those cases where reading and writing in memory with PTR TO <type>
  2679. would only make a program more complex or less efficient. You are _not_
  2680. encouraged to use these functions.
  2681.  
  2682.     PutLong(adr,a)       PutInt(adr,a)        PutChar(adr,a)
  2683.  
  2684. Pokes value 'a' into memory. See: Long()
  2685.  
  2686.     y:=Bounds(x,a,b)
  2687.  
  2688. makes sure x lies between bounds a and b, and adjust acordingly if necessary.
  2689. It equals:    y:=IF x<a THEN a ELSE IF x>b THEN b ELSE x
  2690.  
  2691.  
  2692. 9H. string and list linking functions
  2693. -------------------------------------
  2694. E provides for a set of functions that allows the creation of
  2695. linked list with the STRING and LIST datatype, or strings and lists
  2696. that were created with String() and List() respectively. As you may
  2697. know by now, strings and lists, complex datatypes, are pointers
  2698. to their respective data, and have extra fields to a negative offset
  2699. of that pointer specifying their current length and maxlength. the
  2700. offsets of these fields are PRIVATE. as an addition to those two,
  2701. any complex datatype has a 'next' field, which is set to NIL by
  2702. default, which may be used to build linked list of strings, for example.
  2703. in the following, I will use 'complex' to denote a ptr to a STRING
  2704. or LIST, and 'tail' to denote another such pointer, or one that already
  2705. has other strings linked to it. 'tail' may also be a NIL pointer,
  2706. denoting the end of a linked list.
  2707. [note: these String-list functions have nothing to do with E-lists or
  2708.  Lisp-Cell lists]
  2709. The following functions may be used:
  2710.  
  2711.     complex:=Link(complex,tail)
  2712.  
  2713. puts the value tail into the 'next' field of complex. returns again complex.
  2714. example:
  2715.  
  2716. DEF s[10]:STRING, t[10]:STRING
  2717. Link(s,t)
  2718.  
  2719. creates a linked list like:    s --> t --> NIL
  2720.  
  2721.     tail:=Next(complex)
  2722.  
  2723. reads the 'next' field of var complex. this may of course be NIL, or
  2724. a complete linked list. Calling Next(NIL) will result in NIL, so it's
  2725. safe to call Next when you're not sure if you're at the end of a linked list.
  2726.  
  2727.     tail:=Forward(complex,num)
  2728.  
  2729. same as Next(), only goes forward num links, instead of one, thus:
  2730.  
  2731. Next(c) = Forward(c,1)
  2732.  
  2733. You may safely call Forward() with a num that is way too large;
  2734. Forward will stop if it encounters NIL while searching links, and
  2735. will return NIL.
  2736.  
  2737.     DisposeLink(complex)
  2738.  
  2739. same as Dispose(), with two differences: it's only for strings and
  2740. lists allocated with String() or List(), and will automatically
  2741. de-allocate the tail of complex too. Note that large linked lists
  2742. containing strings allocated with String() as well as some allocated
  2743. locally or globally with STRING may also be de-allocated this way.
  2744.  
  2745. For a good example of how linked lists of strings may be put to
  2746. good use in real-life programs, see Src/Utils/D.e
  2747.  
  2748.  
  2749. 9I. lisp-cells and cell functions
  2750. ---------------------------------
  2751. yep. that's right. you thought LISP was fun, then try E now.
  2752. [or: the story about why E is a better LISP than LISP itself :-)]
  2753.  
  2754. Starting from v3, E has the cell datatype, almost identicall to cells
  2755. in the LISP language. more technically, E has:
  2756.  
  2757. `Conservative Mark and Sweep Garbage-Collected Lisp-Cells'
  2758.  
  2759. basically this amounts to being able to allocate LISP-cells,
  2760. which are pairs of two values:
  2761.  
  2762.     x:=<a,b>
  2763.  
  2764. which is much like NEW [a,b]:LONG, only now E will automatically
  2765. deallocate the 8 bytes in question itself when it finds out it needs
  2766. memory and no pointers are pointing to the cell. In practise this
  2767. means that you can freely have functions create cells as tempories,
  2768. without worrying about freeing them. And any LISP-programmer will
  2769. be able to explain to you that with cells you can build any
  2770. data-structure (most notably trees and lists). [note: this text
  2771. does not thorougly explain how to make full use of cells, since
  2772. dozens of LISP books have been written about this]
  2773.  
  2774. Selecting the values can easily be done using Car(x) and Cdr(x),
  2775. two LISP-functions which select head and tail (first and second)
  2776. element of the cell. if x is a PTR TO LONG, even x[0] and x[1]
  2777. are allowed.
  2778.  
  2779. One can also write lists of cells:
  2780.  
  2781.     <a,b,c>
  2782.  
  2783. (note the commas) as short for
  2784.  
  2785.     <a:<b:<c:NIL>>>
  2786.  
  2787. An alternative for selection with Car/Cdr is E's unification:
  2788.  
  2789.     x <=> <a,b:c>
  2790.     a+b+c
  2791.  
  2792. instead of:
  2793.  
  2794.     Car(x)+Car(Cdr(x))+Cdr(Cdr(x))
  2795.  
  2796. lisp-cell unification resembles E-list unification (see 4L). for
  2797. example:
  2798.  
  2799.     x <=> <1,2|a>
  2800.  
  2801. equals:
  2802.  
  2803.     IF Car(x)=1
  2804.           IF Car(Cdr(x))=2
  2805.             a:=Cdr(Cdr(x))
  2806.             ...
  2807.  
  2808.  
  2809. A lisp-nil value is available "<>", which equals NIL and 0.
  2810.  
  2811. some functions are available (note that Cons() is _only_ available
  2812. through <...>)
  2813.  
  2814.     h:=Car(c)    t:=Cdr(c)
  2815.  
  2816. fix the head and the tail value of a cell c
  2817.  
  2818.     bool:=Cell(c)
  2819.  
  2820. gives a bool for wether or not c points at a cell, so Cell(<1>)=TRUE,
  2821. and Cell(3.14)=FALSE. This is not a fast function.
  2822.  
  2823.     n:=FreeCells()
  2824.  
  2825. tell you about the amount of free cells available. very slow function.
  2826. there should be no need to call this function other than curiosity.
  2827.  
  2828.     SetChunkSize(k)
  2829.  
  2830. Sets the chunksize to allocate for cells to k kilobyte. default is 128k.
  2831. This function can only be called once, and only before the first cons
  2832. (<..>) allocation takes place. Thereafter it has no effect.
  2833.  
  2834. In general, get a good book about lisp to understand more about
  2835. programming with cells.
  2836.  
  2837. One can write any LISP-functions in E, with exactly the same functionality:
  2838.  
  2839. PROC append(x,y) IS IF x THEN <Car(x)|append(Cdr(x),y)> ELSE y
  2840. PROC nrev(x) IS IF x THEN append(nrev(Cdr(x)),<Car(x)>) ELSE NIL
  2841. PROC sum(x) IS IF x THEN Car(x)+sum(Cdr(x)) ELSE 0
  2842.  
  2843. using a destructive implementation for functions like these is
  2844. also allowed.
  2845.  
  2846. techy stuff:
  2847. E's garbage collector implements a conservative mark and sweep algorithm
  2848. that was tested to be 5 to 25 times faster than several logical and
  2849. functional language implementations on the Amiga. Conservative
  2850. means that in case of doubt, the GC will not deallocate a cell. this
  2851. is necessary since in a typeless language such as E, the GC can
  2852. easily bump in to a value that is not a valid pointer etc.
  2853.  
  2854. The GC allocates big chunks (default 128k), in which it allocates
  2855. cells. if out of cells, it will collect garbage by scanning the
  2856. stack and registers for pointers into the cellspace, and recursively
  2857. marks them. after that, all unmarked cells are reused, and if the
  2858. gain after a collection was only small, a new chunk is allocated.
  2859.  
  2860. interaction with other E values:
  2861. - storing other values in cells is no problem whatsoever. objects,
  2862.   strings, floats, anything can be put into a cell without confusing
  2863.   the GC too much.
  2864. - storing cells in other values, for example a ptr to a cell in a
  2865.   dynamic object, is problematic, since the GC won't be able to find
  2866.   it there. a sollution for this will be provided. However I think this
  2867.   case will seldomly occur.
  2868.   ptrs to cells can safely be stored in global and local variables,
  2869.   even registers, and any stack datastructures.
  2870.   [and most importantly, in other cells!]
  2871.  
  2872. caveats:
  2873. - The GC currently can't collect cells that have a Car-list >1000
  2874.   long or so, i.e. <<<NIL:a>:b>:c>, but then 1000 instead of 3
  2875.   entries. this will hardly ever occur since lists like this
  2876.   are usually formed as Cdr-lists, which the GC can handle into
  2877.   infinity.
  2878. - inline assembly code should never push stuff on the stack that
  2879.   is not LONG alligned. this was already necessary in v2.1b,
  2880.   but now is even more essential.
  2881.  
  2882. There's a tradeof in chunk-size between time and space.
  2883. Allocating small chunks obviously is nice since you won't waste
  2884. any memory, however, when collecting garbage, the effort for
  2885. each pointer to trace is almost proportional to the number of
  2886. spaces. therefore:
  2887. - if speed is most important tune the chunkspacesize such that
  2888.   that only one space is needed. if the top cell-memory usage at a
  2889.   certain time is 50k, a chunkspace of 100k or 150k will give
  2890.   optimal performance.
  2891. - if memory usage is more important, in the example above a
  2892.   chunksize of 20k or 30k will be quite optimal for memory.
  2893. I general, time a heavy usage of your cell-algorithm with
  2894. different sizes to see what trade-off suits you best.
  2895.  
  2896.  
  2897. +---------------------------------------------------------------+
  2898. |               10. LIBRARY FUNCTIONS AND MODULES        |
  2899. +---------------------------------------------------------------+
  2900.  
  2901. 10A. built-in library calls
  2902. --------------------------
  2903. As you may have noticed from previous sections, the piece of code
  2904. automatically linked to the start of your code, called the "initialisation code",
  2905. always opens the three libraries intuition, dos, graphics and (and sometimes
  2906. mathieeesingbas), and because of this, the compiler has all the calls to those
  2907. four libraries (including exec) integrated in the compiler (there are a few hundred
  2908. of them). These are up to AmigaDos v3.00 (v39). To call Open() from the dos library,
  2909. simply say:
  2910.  
  2911. handle:=Open('myfile',OLDFILE)
  2912.  
  2913. or AddDisplayInfo() from the graphics library:
  2914.  
  2915. AddDisplayInfo(mydispinfo)
  2916.  
  2917. it's as simple as that.
  2918.  
  2919.  
  2920. 10B. interfacing to the amiga system with the v39 modules
  2921. ----------------------------------------------------------
  2922. To use any other library than the five in the previous section, you'll
  2923. need to resort to modules. Also, if you wish to use some OBJECT or CONST
  2924. definition from the Amiga includes as is usual in C or assembler,
  2925. you'll need modules. Modules are binary files which may include constant,
  2926. object, library and function (code) definitions. The fact that they're
  2927. binary has the advantage over ascii (as in C and assembly), that they
  2928. need not be compiled over and over again, each time your program is
  2929. compiled. The disadvantage is that they cannot be simply be viewed; they
  2930. need a utility like ShowModule (see 17A) to make their contents
  2931. visible. The modules that contain the library definitions (i.e the calls)
  2932. are in the root of emodules: (the modules dir in the distribution), the
  2933. constant/object definitions are in the subdirectories, structured just
  2934. like the originals from Commodore.
  2935.  
  2936. MODULE
  2937.  
  2938. syntax:        MODULE <modulenames>,...
  2939.  
  2940. Loads a module. A module is a binary file containing information on libraries,
  2941. constants, and sometimes functions. Using modules enables you to use
  2942. libraries and functions previously unknown to the compiler.
  2943.  
  2944. Now for an example, below is a short version of the source/examples/asldemo.e
  2945. source that uses modules to put up a filerequester from the 2.0 Asl.library.
  2946.  
  2947.  
  2948. MODULE 'Asl', 'libraries/Asl'
  2949.  
  2950. PROC main()
  2951.   DEF req:PTR TO filerequester
  2952.   IF aslbase:=OpenLibrary('asl.library',37)
  2953.     IF req:=AllocFileRequest()
  2954.       IF RequestFile(req) THEN WriteF('File: "\s" in "\s"\n',req.file,req.drawer)
  2955.       FreeFileRequest(req)
  2956.     ENDIF
  2957.     CloseLibrary(aslbase)
  2958.   ENDIF
  2959. ENDPROC
  2960.  
  2961.  
  2962. From the modules 'asl', the compiler takes asl-function definitions like
  2963. RequestFile(), and the global variable 'aslbase', which only needs to
  2964. be initialised by the programmer. From 'libraries/Asl', it takes
  2965. the definition of the filerequester object, which we use to read the
  2966. file the user picked. Well, that wasn't all that hard: did you think
  2967. it was that easy to program a filerequester in E?
  2968.  
  2969. 10C. compiling own modules
  2970. --------------------------
  2971. with v3, you can gather all PROCs, CONSTs, OBJECTs and to
  2972. some extend also global variables that you feel somehow belong
  2973. together in one source, write "OPT MODULE" to signal EC that
  2974. this is supposed to be a module, and then compile all to a
  2975. .m file to be used in the main program, just like you used to
  2976. do with the old modules.
  2977.  
  2978. by default, all elements in a module are PRIVATE, i.e. not accessable
  2979. to the code that imports the .m file. to show which elememts
  2980. you wish to be visible in the module, simply write EXPORT
  2981. before it:
  2982.  
  2983. EXPORT ENUM TESTING,ONE,TWO,THREE,FOUR
  2984.  
  2985. EXPORT DEF important_glob_var, bla:PTR TO x
  2986.  
  2987. EXPORT OBJECT x
  2988.   next, index, term
  2989. ENDOBJECT
  2990.  
  2991. EXPORT PROC burp()
  2992.   /* whatever */
  2993. ENDPROC
  2994.  
  2995. "EXPORT" is usefull in making a distinction between private and
  2996. public, especially when all functions of an OBJECT can be accessed
  2997. via PROCs, you may wish to keep to OBJECT private as an effective
  2998. method of data hiding. more on this topic, (see 14C)
  2999.  
  3000. If in a module _all_ elememts need to be exported (for example
  3001. one with only constants), a 'OPT EXPORT' will export all, without
  3002. the need for individual EXPORT keywords.
  3003.  
  3004. global variables require extra attention:
  3005. - try to avoid lots of global variables. having lot of globals
  3006.   in modules makes projects messy and error-prone
  3007. - globs in a module cannot have initialisations directly
  3008.   in the DEF statement (reason for this will become clear
  3009.   below). for example:
  3010.   DEF a             not     DEF a=1
  3011.   DEF a:PTR TO x    not     DEF a[10]:ARRAY OF x
  3012. - globals in a module which are not exported function as
  3013.   local for the module, i.e. they'll never clash with globals
  3014.   in other modules. those who _are_ exported though, are
  3015.   combined with the others, i.e. if in both the main program
  3016.   and in a module a variable with the same name are used,
  3017.   this will be one and the same variable. that's why
  3018.   one can write DEF a[10]:ARRAY OF x in the main program,
  3019.   and EXPORT DEF a:PTR TO x in the module, to share the
  3020.   array. Also, if both use for example 'gadtools.m',
  3021.   only one of the two needs to initialise 'gadtoolsbase'
  3022.   for both to be able to make calls to the library.
  3023.   If you do not want librarybases to be shared (i.e. you
  3024.   want to have a local, private library base), simply
  3025.   redeclare it in a DEF in the module that is not EXPORTed.
  3026.   If you export a variable in a general purpose
  3027.   module, make sure to give it a pretty unique name.
  3028. - using globals in modules which provide general purpose
  3029.   datatypes needs special attention, as the module may be
  3030.   in use from more than one other module, in which case
  3031.   it may be unclear who is responsable for resources.
  3032.   take good care of this.
  3033.  
  3034. Using modules in modules
  3035.  
  3036. This requires little extra attention. If the module (B) you include
  3037. in your own module (A) is one that only declares CONSTs, LIBRARYs and
  3038. OBJECTs (without code) nothing special happens, however if B includes
  3039. PROCs, then it's obvious this code needs to be linked later to the
  3040. main program when A is linked. Therefore if a main program uses A,
  3041. B will need to be present for compilation. The fact that A needs
  3042. B is stored in A, and can be viewed with ShowModule. This chain
  3043. of uses may grow out to a tree of dependencies, which has the result
  3044. that if you use just one module in your program, a lot of others
  3045. are automatically linked to it. Thus, E's module system automatically
  3046. keeps track of dependancies that other languages need makefiles for.
  3047. EC also allows for circular inclusions, and loads/links modules at most
  3048. once (i.e. doesn't link unused modules).
  3049.  
  3050.  
  3051. Try out the new ShowModule (see 17A) to see what EC puts in modules.
  3052.  
  3053.  
  3054. Including modules from other directories.
  3055.  
  3056. By default, a module name is prefixed by 'emodules:' to obtain
  3057. the actual file. Now you can prefix the name with a '*' to
  3058. denote the directory the source is in, so:
  3059.  
  3060. MODULE 'bla', '*bla'
  3061.  
  3062. if this statement would be in source 'WORK:E/burp.e', these two
  3063. modules would be 'emodules:bla.m' and 'WORK:E/bla.m'.
  3064.  
  3065. This is naturally the way to include components of your app into
  3066. other parts. If you write modules that you use in many of your programs
  3067. it would be handy to store them in the emodules hierarchy, and the
  3068. place for this is the 'emodules:other/' dir.
  3069.  
  3070.  
  3071.  
  3072. 10D. the modulecache
  3073. --------------------
  3074. (see 17D, ShowCache/FlushCache about this).
  3075.  
  3076.  
  3077. +---------------------------------------------------------------+
  3078. |                    11. QUOTED EXPRESSIONS            |
  3079. +---------------------------------------------------------------+
  3080.  
  3081. 11A. quoting and scope
  3082. ----------------------
  3083. Quoted expressions start with a backquote. The value of a quoted
  3084. expression is not the result from the computation of the expression,
  3085. but the address of the code. This result may then be passed on as
  3086. a normal variable, or as an argument to certain functions.
  3087. example:
  3088.  
  3089. myfunc:=`x*x*x
  3090.  
  3091. myfunc is now a pointer to a `function' that computes x^3 when evaluated.
  3092. These pointers to functions are very different from normal PROCs, and
  3093. you should never mix the two up. The biggest differences are that a
  3094. quoted expression is just a simple expression, and thus cannot have its
  3095. own local variables. In our example, "x" is just a local or global variable.
  3096. That's where we have to be cautious:
  3097. if we evaluate myfunc somewhat later in the same PROC, x may be local,
  3098. but if myfunc is given as parameter to another PROC, and then evaluated,
  3099. x needs of course to be global. There's no scope checking on this.
  3100.  
  3101. 11B. Eval()
  3102. -----------
  3103.     Eval(func)
  3104.  
  3105. simply evaluates a quoted expression (exp = Eval(`exp)).
  3106.  
  3107. NOTE: because E is a somewhat typeless language, accidentally writing
  3108. "Eval(x*x)"  instead of  "Eval(`x*x)"  will go unnoticed by the
  3109. compiler, and will give you big runtime problems: the value of x*x
  3110. will be used as a pointer to code.
  3111.  
  3112. To understand why 'quoted expressions' is a powerful feature think of the
  3113. following cases: if you were to perform a set of actions on a set of different
  3114. variables, you'd normally write a function, and call that function with
  3115. different arguments. But what happens when the element that you want to give
  3116. as argument is a piece of code? in traditional languages this would not be
  3117. possible, so you would have to 'copy' the blocks of code representing your
  3118. function, and put the expression in it. Not in E. say you wanted to write
  3119. a program that times the execution time of different expressions. In E you
  3120. would simply write:
  3121.  
  3122. PROC timing(func,title)
  3123.   /* do all sorts of things to initialise time */
  3124.   Eval(func)
  3125.   /* and the rest */
  3126.   WriteF('time measured for \s was \d\n',title,t)
  3127. ENDPROC
  3128.  
  3129. and then call it with:
  3130.  
  3131. timing(`x*x*x,'multiplication')
  3132. timing(`sizycalc(),'large calculation')
  3133.  
  3134.  
  3135. in any other imperative language, you would have to write out
  3136. copies of timing() for every call to it, or you would have to
  3137. put each expression in a separate function. This is just a simple
  3138. example: think about what you could do with data structures (LISTs)
  3139. filled with unevaluated code:
  3140.  
  3141. drawfuncs:=[`Plot(x,y,c),`Line(x,y,x+10,y+10,c),`Box(x,y,x+20,y+20,c)]
  3142.  
  3143. Note that this idea of functions as normal variables/values is not new
  3144. in E, quoted expressions are literally from LISP, which also has the
  3145. somewhat more powerful so-called Lambda function, which can also be
  3146. given as argument to functions; E's quoted expressions can also be
  3147. seen as parameterless (or global parameter only) lambda's.
  3148.  
  3149.  
  3150. 11C. built-in functions
  3151. -----------------------
  3152.  
  3153.     MapList(varadr,list,listvar,func)
  3154.  
  3155. performs some function on all elements of list and returns all
  3156. results in listvar. func must be a quoted expression (see 11A),
  3157. and var (which ranges over the list) must be given by reference. Example:
  3158.  
  3159. MapList({x},[1,2,3,4,5],r,`x*x)       results r in:     [1,4,9,16,25]
  3160.  
  3161. returns listvar.
  3162.  
  3163.     ForAll(varadr,list,func)
  3164.  
  3165. Returns TRUE if for all elements in the list the function (quoted
  3166. expression) evaluates to TRUE, else FALSE. May also be used to perform
  3167. a certain function for all elements of a list:
  3168.  
  3169. ForAll({x},['one','two','three'],`WriteF('example: \s\n',x))
  3170.  
  3171.     Exists(varadr,list,func)
  3172.  
  3173. As ForAll(), only this one returns TRUE if for any element the function
  3174. evaluates to TRUE (<>0). note that ForAll() always evaluates all elements,
  3175. but Exists() possibly does not.
  3176.  
  3177.     SelectList(v,list,listvar,quotedexp)
  3178.  
  3179. Much like MapList(), only now doesn't store the result from quotedexp,
  3180. it uses it as a boolean value, and only those value for which it is
  3181. true are stored in listvar (which should be capable of holding
  3182. the same amount of elements as list. example:
  3183.  
  3184. SelectList({x},[1,2,0,3,NIl],r,`x<>0)
  3185.  
  3186. results in r being [1,2,3].
  3187. returns length of listvar.
  3188.  
  3189. Example of how to use these functions in a practical fashion:
  3190. we allocate different sizes of memory in one statement, check them
  3191. all together at once, and free them all, but still only those that
  3192. succeeded. (example is v37+)
  3193.  
  3194.  
  3195. PROC main()
  3196.   DEF mem[4]:LIST,x
  3197.   MapList({x},[200,80,10,2500],mem,`AllocVec(x,0))              -> alloc some
  3198.   WriteF(IF ForAll({x},mem,`x) THEN 'Yes!\n' ELSE 'No!\n')        -> suxxes ?
  3199.   ForAll({x},mem,`IF x THEN FreeVec(x) ELSE NIL)     -> free only those <>NIL
  3200. ENDPROC
  3201.  
  3202.  
  3203. Note the absence of iteration in this code. Just try to rewrite this
  3204. example in any other language to see why this is special.
  3205.  
  3206.  
  3207. +---------------------------------------------------------------+
  3208. |                  12. FLOATING POINT SUPPORT            |
  3209. +---------------------------------------------------------------+
  3210.  
  3211.  
  3212. REALs (or FLOATs, whatever) are very different in E than in other
  3213. languages. This mainly has to do with the fact that E doesn't
  3214. really dicriminate between types of values. One is adviced to
  3215. understand this chapter _well_ before attempting to use floats.
  3216.  
  3217.  
  3218. 12A. float values
  3219. -----------------
  3220. In E, a float is just another 32bit value. The E compiler treats
  3221. them just like integers or pointers, with the difference that
  3222. their bit representation means something different. The E float
  3223. format is the IEEEsingle standard.
  3224.  
  3225. A float value looks like an integer value with the exception that
  3226. somewhere a "." is present. for example, the following are valid 
  3227. floats:
  3228.  
  3229.     3.14159    .1    1.    -12345.6
  3230.  
  3231. these aren't:
  3232.  
  3233.     .    1234
  3234.  
  3235. (i.e. atleast one "." and one "0-9" char must be present).
  3236.  
  3237. You can use these values at almost all places where LONG values
  3238. are legal, i.e. if you have have a function or datastructure that
  3239. handles arbitrary LONG values, it will also handle floats.
  3240.  
  3241.     DEF f=3.14
  3242.     myobj.x:=.1
  3243.     fun(f,2.73)
  3244.  
  3245.  
  3246.  
  3247. 12B. computing with floats
  3248. --------------------------
  3249. Because to E a float will seem like just another LONG, it will happily
  3250. apply integer math to it when used in an expression, which is mostly
  3251. not what you want. Also, one would like to be able to convert to
  3252. integer and vice-versa. The float operator "!" handles all this.
  3253.  
  3254. assume in the following examples that a,b,c contain integer values,
  3255. and x,y,z float values.
  3256.  
  3257. By default, an expression in E is considered an integer expression.
  3258. what the "!" does when it occurs in an expression is the following:
  3259. - changes the expression from int to float. any operators following
  3260.   (+ * - / = <> > < >= <=) will be float operations. "!" may occur
  3261.   any number of times in an expression, changing from and to float
  3262.   again and again.
  3263. - the expression that did occur before the "!", if any, is converted
  3264.   to the appropriate type.
  3265.  
  3266. examples:
  3267.  
  3268.     x:=a!
  3269.  
  3270. converts "a" to float, and stores the result in x. "a" is an integer exp,
  3271. which is then toggled to float, which implies a convertion.
  3272.  
  3273.     a:=!x!
  3274.  
  3275. converts "x" to integer and stores the result in a.
  3276.  
  3277.     x:=y
  3278.  
  3279.     x:=Ftan(y)
  3280.  
  3281. no "!" is needed here since no operator-math or conversions are necessary.
  3282.  
  3283.     x:=!y*z
  3284.  
  3285. the "*" acts on y and z as floats, since "!" denotes the whole as
  3286. a float-exp. the float result is stored in x
  3287.  
  3288.     a:=b!*x+y!
  3289.  
  3290. a more complex example: the int "b" is converted to float, then x
  3291. and y are float-multiplied and -added to it. The result is converted
  3292. to int and stored in the int "a"
  3293.  
  3294.     x:=!y*z-z*y+(a!)+z/z
  3295.  
  3296.     z:=!x*Fsin(!x*y)
  3297.  
  3298. all (+ * - /) are computed as float, and the int "a" is converted
  3299. to float somewhere in the middle. since "(" ")" denotes a new expression,
  3300. it has it's own status of "!". Same idea for the function below.
  3301.  
  3302.     IF !x<0.1 THEN WriteF('Float value too small!\n')
  3303.  
  3304. as you can see, "!" also works on the six comparison operators.
  3305.  
  3306.  
  3307.  
  3308. 12C. builtin float functions
  3309. ----------------------------
  3310.  
  3311. Some trans-math functions are present, more will probably follow.
  3312.  
  3313.     x:=Fsin(y)    x:=Fcos(y)    x:=Ftan(y)
  3314.  
  3315. usual sin() etc. functions. they work with radians.
  3316.  
  3317.     x:=Fabs(y)
  3318.  
  3319. compute absolute value of y
  3320.  
  3321.     x:=Ffloor(y)    x:=Fceil(y)
  3322.  
  3323. compute lowest and highest whole-number float value near y
  3324.  
  3325.     x:=Fexp(y)    x:=Flog(y)    Flog10(y)    x:=Fpow(y,z)    Fsqrt(y)
  3326.  
  3327. compute y^e (something like 2.73), ln(y), log base 10, y^z and
  3328. square root of y, respectively.
  3329.  
  3330.     x,n:=RealVal(s)
  3331.  
  3332. parses string "s" to produce float value x. will skip leading spaces and tabs.
  3333. n is the number of characters parsed from the start of the string, or 0
  3334. if it couldn't be parsed as a float value. "x" will then be 0.0.
  3335. accepts negative numbers.
  3336. example:
  3337.  
  3338. RealVal(' 3.14 ')    results in    3.14, 5
  3339. RealVal('blabla')    results in    0.0, 0
  3340.  
  3341.     s:=RealF(s,x,n)
  3342.  
  3343. Format a float value x to the estring s, with n positions after the ".".
  3344. max for "n" is 8, even less if you have lots of digits leading the ".".
  3345. an "n" of 0 will denote no fraction. The string is returned as result,
  3346. so it can be reused in a WriteF() for example:
  3347.  
  3348. WriteF('float = \s\n',RealF(s,3.14159),4)    results in    'float = 3.1416\n'
  3349.  
  3350. RealF() tries hard to make sensible roundings for a certain "n", as
  3351. the example shows. negative numbers are also handled properly.
  3352.  
  3353. RealF(s,-3.14159,0)    results in    '-3'
  3354.  
  3355.  
  3356.  
  3357. 12D. float implementation issues
  3358. --------------------------------
  3359. As said before, the E float format is IEEE (single), this means that
  3360. older float code using the FFP format with the SpXxx functions will
  3361. have to be rewritten (as stated in the v2.1b docs). The mathffp
  3362. library is no longer directly supported by EC v3.0, and you'll
  3363. have to open this library like all others if you want to use it.
  3364.  
  3365. single IEEE's were chosen because:
  3366. - double IEEE's don't fit in a LONG
  3367. - the FFP format routines do not make use of a 68881 if present,
  3368.   the IEEE ones do. Furthermore the FFP format is incompatible
  3369.   with the 68881, which also uses IEEE format.
  3370. - IEEE is the worldwide float-format standard, which encourages
  3371.   data-file compatability among software/platforms.
  3372.  
  3373. E's float routines use the mathieeesingbas.library and the
  3374. mathieeesingtrans.library, which are not by default supplied
  3375. with the ancient v1.3 of the OS. This means that if you want
  3376. to write under / support 1.3 AND you want to use the _builtin_
  3377. floats, you have to make sure these libraries are present (they
  3378. seem to be available, maybe through commodore?).
  3379.  
  3380. Both EC and the programs it generates do not open these libraries
  3381. as long as no float-features are used.
  3382.  
  3383. If all else fails, one can always use other floatlibraries to use
  3384. floats with 1.3. I might recommend the tools/longreal.m module
  3385. which uses doubles.
  3386.  
  3387. In the future, EC will probably allow mathieee library calls to
  3388. be replaced with inline 68881 code transparently.
  3389.  
  3390.  
  3391. +---------------------------------------------------------------+
  3392. |                      13. EXCEPTION HANDLING            |
  3393. +---------------------------------------------------------------+
  3394.  
  3395. 13A. defining exception handlers (HANDLE/EXCEPT)
  3396. ------------------------------------------------
  3397. The exception mechanism in E is basically the same as in ADA; it
  3398. provides for flexible reaction on errors in your program and
  3399. complex resource management. NOTE: the term 'exception' in E has
  3400. very little to do with exceptions caused directly by 680x0 processors.
  3401.  
  3402. An exception handler is a piece of program code that will be invoked
  3403. when runtime errors occur, such as windows that fail to open or
  3404. memory that is not available. You, or the runtime system itself,
  3405. may signal that something is wrong (this is called "raising an
  3406. exception"), and then the runtime-system will try and find the
  3407. appropriate exception handler. I say "appropriate" because a program
  3408. can have more than one exception handler, on all levels of a program.
  3409. A normal function definition may (as we all know) look like this:
  3410.  
  3411. PROC bla()
  3412.   /* ... */
  3413. ENDPROC
  3414.  
  3415. a function with an exception handler looks like this:
  3416.  
  3417. PROC bla() HANDLE
  3418.   /* ... */
  3419. EXCEPT
  3420.   /* ... */
  3421. ENDPROC
  3422.  
  3423. The block between PROC and EXCEPT is executed as normal, and if no
  3424. exception occur, the block between EXCEPT and ENDPROC is skipped, and
  3425. the procedure is left at ENDPROC. If an exception is raised, either
  3426. in the PROC part, or in any function that is called in this block,
  3427. an exception handler is invoked.
  3428.  
  3429. 13B. using the Raise() function
  3430. -------------------------------
  3431. There are many ways to actually "raise" an exception, the simplest
  3432. is through the function Raise():
  3433.  
  3434.     Raise(exceptionID=0)
  3435.  
  3436. the exception ID is simply a constant that defines the type of
  3437. exception, and is used by handlers to determine what went wrong.
  3438. Example:
  3439.  
  3440. ENUM NOMEM,NOFILE  /* and others */
  3441.  
  3442. PROC bla() HANDLE
  3443.   DEF mem
  3444.   IF (mem:=New(10))=NIL THEN Raise(NOMEM)
  3445.   myfunc()
  3446. EXCEPT
  3447.   SELECT exception
  3448.     CASE NOMEM
  3449.       WriteF('No memory!\n')
  3450.     /* ... and others */
  3451.   ENDSELECT
  3452. ENDPROC
  3453.  
  3454. PROC myfunc()
  3455.   DEF mem
  3456.   IF (mem:=New(10))=NIL THEN Raise(NOMEM)
  3457. ENDPROC
  3458.  
  3459. The "exception" variable in the handler always contains the value of
  3460. the argument to the Raise() call that invoked it.
  3461. In both New() cases, the Raise() function invokes the handler of
  3462. function bla(), and then exits it correctly to the caller of bla().
  3463. If myfunc() had its own exception-handler, that one would be invoked
  3464. for the New() call in myfunc(). The scope of a handler is from the start
  3465. of the PROC in which it is defined until the EXCEPT keyword, including
  3466. all calls made from there.
  3467.  
  3468. This has three consequences:
  3469. A. handlers are organised in a recursive fashion, and which handler is
  3470.    actually invoked is dependant on which function calls which at runtime;
  3471. B. if an exception is raised within a handler, the handler of a lower
  3472.    level is invoked. This characteristic of handlers may be used
  3473.    to implement complex recursive resource allocation schemes with
  3474.    great ease, as we'll see shortly.
  3475. C. If an exception is raised on a level where no lower-level handler
  3476.    is available (or in a program that hasn't got any handlers at all),
  3477.    the program is terminated. (i.e: Raise(x) has the same effect as
  3478.    CleanUp(0))
  3479.  
  3480. other functions:
  3481.  
  3482.     Throw(exceptionID,value)
  3483.  
  3484. same as Raise(), only now it takes an arbitrary value with it. in
  3485. a handler one can then scrutinize this value with the variable
  3486. 'exceptioninfo'
  3487.  
  3488.     ReThrow()
  3489.  
  3490. has no args. simply does a Throw() on the current exception value,
  3491. IFF it is <>0.
  3492.  
  3493.  
  3494. 13C. defining exceptions for built-in functions (RAISE/IF)
  3495. ---------------------------------------------------------
  3496. With exceptions like before, we have made a major gain over the
  3497. old way of defining our own "error()" function, but still it is
  3498. a lot of typing to have to check for NIL with every call to New().
  3499.  
  3500. The E exception handling system allows for definition of exceptions
  3501. for all E functions (like New(), OpenW() etc.), and for all Library
  3502. functions (OpenLibrary(), AllocMem() etc.), even for those
  3503. included by modules. Syntax:
  3504.  
  3505. RAISE <exceptionId> IF <func> <comp> <value> , ...
  3506.  
  3507. the part after RAISE may be repeated with a ",".
  3508. Example:
  3509.  
  3510. RAISE NOMEM IF New()=NIL,
  3511.       NOLIBRARY IF OpenLibrary()=NIL
  3512.  
  3513. the first line says something like: "whenever a call to New() results
  3514. in NIL, automatically raise the NOMEM exception".
  3515. <comp> may be any of = <> > < >= <=
  3516. After this definition, we may write all through our programs:
  3517.  
  3518. mem:=New(size)
  3519.  
  3520. without having to write:
  3521.  
  3522. IF mem=NIL THEN Raise(NOMEM)
  3523.  
  3524. Note that the only difference is that "mem" never gets any value
  3525. if the runtime system invokes the handler: code is generated for
  3526. every call to New() to check directly after New() returns and call
  3527. Raise() when necessary.
  3528.  
  3529. We'll now be implementing a small example that would be complex to solve
  3530. without exception handling: we call a function recursively, and in each
  3531. we allocate a resource (in this case memory), which we allocate before,
  3532. and release after the recursive call. What happens when somewhere high
  3533. in the recursion a severe error occurs, and we have to leave the program?
  3534. right: we would (in a conventional language) be unable to free all the
  3535. resources lower in the recursion while leaving the program, because all
  3536. pointers to those memory areas are stored in unreachable local variables.
  3537. In E, we can simply raise an exception, and from the end of the handler
  3538. again raise an exception, thus recursively calling all handlers and
  3539. releasing all resources. Example:
  3540.  
  3541.  
  3542. CONST SIZE=100000
  3543. ENUM NOMEM  /* ,... */
  3544.  
  3545. RAISE NOMEM IF AllocMem()=NIL
  3546.  
  3547. PROC main()
  3548.   alloc()
  3549. ENDPROC
  3550.  
  3551. PROC alloc() HANDLE
  3552.   DEF mem
  3553.   mem:=AllocMem(SIZE,0)        /* see how many blocks we can get */
  3554.   alloc()            /* do recursion */
  3555. EXCEPT DO
  3556.   IF mem THEN FreeMem(mem,SIZE)
  3557.   ReThrow()            /* recursively call all handlers */
  3558. ENDPROC
  3559.  
  3560.  
  3561. This is of course a simulation of a natural programming problem that
  3562. is usually far more complex, and thus the need for exception handling
  3563. becomes far more obvious. For a real-life example program whose error
  3564. handling would have become very difficult without exception
  3565. handlers, see the 'D.e' utility source.
  3566.  
  3567. The "DO" after an EXCEPT means that instead of jumping to ENDPROC,
  3568. the main code will simply continue execution in the handler as soon
  3569. as it gets there. it also sets exception to 0.
  3570. This is handy if you free resources local to a PROC in the handler.
  3571.  
  3572.  
  3573.  
  3574. 13D. use of exception-ID's
  3575. --------------------------
  3576. In real life an exception-ID is ofcourse a normal 32-bit value,
  3577. and you may pass just about anything to an exception handler: for
  3578. example, some use it to pass error-description strings
  3579.  
  3580. Raise('Could not open "gadtools.library"!')
  3581.  
  3582. However, if you want to use exceptions in expandabele fashion and you
  3583. want to be able to use future modules that raise exceptions not defined
  3584. by your program, follow the following guidelines:
  3585.  
  3586. - Use and define ID 0 as "no error" (i.e. normal termination)
  3587.  
  3588. - For exceptions specific to your program, use the ID's 1-10000.
  3589.   Define these in the usual fashion with ENUM:
  3590.  
  3591.   ENUM OK,NOMEM,NOFILE,...
  3592.  
  3593.   (OK will be 0, and others will be 1+)
  3594.  
  3595. - ID's 12336 to 2054847098 (these are all identifiers
  3596.   consisting of upper/lowercase letters and digits of lenght 2,3 or 4
  3597.   enclosed in "") are reserved as common exceptions. A common exception
  3598.   is an exception that need not need be defined in your program, and that
  3599.   may be used by implementors of modules (with functions in them) to
  3600.   raise exceptions: for example, if you design a set of procedures that
  3601.   perform a certain task, you may want to raise exceptions. As you would
  3602.   want to use those functions in various programs, it would be
  3603.   unpractical to have to coordinate the ID's with the main program,
  3604.   furthermore, if you use more than one set of functions (in a module,
  3605.   in the future) and every module would have a different ID for
  3606.   'no memory!', things could get out of hand.
  3607.   This is where common exceptions come in: the common out-of-memory
  3608.   ID is "MEM" (including the quotes): any implementor can now simply
  3609.  
  3610.   Raise("MEM")
  3611.  
  3612.   from all different procedures, and the programmer that uses the module
  3613.   only needs to suply an exception handler that understands "MEM"
  3614.  
  3615.   future modules that contain sets of functions will specify what
  3616.   exception a certain procedure may raise, and if these overlap
  3617.   with the ID's of other procedures, the task of the programmer
  3618.   that has to deal with the exceptions will be greatly simplyfied.
  3619.  
  3620.   examples:
  3621.  
  3622.   (system)
  3623.  
  3624.   "MEM"        out of memory
  3625.   "FLOW"    (nearly) stack overflow
  3626.   "^C"        Control-C break
  3627.   "ARGS"    bad args
  3628.  
  3629.   (exec/libraries)
  3630.  
  3631.   "SIG"        could not allocate signal
  3632.   "PORT"    could not create messageport
  3633.   "LIB"        library not available
  3634.   "ASL"        no asl.library
  3635.   "UTIL"    no utility.library
  3636.   "LOC"        no locale.library
  3637.   "REQ"        no req.library
  3638.   "RT"        no reqtools.library
  3639.   "GT"        no gadtools.library (similar for others)
  3640.  
  3641.   (intuition/gadtools/asl/gfx)
  3642.  
  3643.   "WIN"        failed to open window
  3644.   "SCR"        failed to open screen
  3645.   "REQ"        could not open requester
  3646.   "FREQ"    could not open filerequester
  3647.   "GAD"        could not create gadget
  3648.   "MENU"    could not create menu(s)
  3649.   "FONT"    problem getting font
  3650.  
  3651.   (dos)
  3652.  
  3653.   "OPEN"    could not open a file / file does not exist
  3654.   "OUT"        problems while writing
  3655.   "IN"        problems while reading
  3656.   "EOF"        unexpected end of file
  3657.   "FORM"    input format error
  3658.   "SEG"        loadseg problems
  3659.  
  3660.   The general tendancy is:
  3661.   * all uppercase for general system exceptions,
  3662.   * mixed case for exceptions used by >1 app, but not general enough.
  3663.   * all lowercase for exceptions raised within your own
  3664.     multi-module application
  3665.  
  3666. - all others (including all negative ID's) remain reserved.
  3667.  
  3668.  
  3669. +---------------------------------------------------------------+
  3670. |                      14. OO PROGRAMMING            |
  3671. +---------------------------------------------------------------+
  3672.  
  3673. 14A. OO features in E
  3674. ---------------------
  3675. The features descibed here in this chapter are grouped as such
  3676. since they constitute what is generally seen as the three essential
  3677. main components that make a language 'Object Oriented' (i.e.
  3678. inheritance - data hiding - polymorhism). However in E they are
  3679. by know means a 'seperate chapter' since each can be used in any
  3680. way with other E features.
  3681.  
  3682.  
  3683. 14B. object inheritance
  3684. -----------------------
  3685. it's always annoying not being able to express dependencies between
  3686. OBJECTs, or reuse code that works on a particular OBJECT with a bigger
  3687. OBJECT that encapsulates the first. Object Inheritance allows you
  3688. to do just that in E. when you have an object a:
  3689.  
  3690. OBJECT a
  3691.   next, index, term
  3692. ENDOBJECT
  3693.  
  3694. you can make a new object b that has the same properties
  3695. as a (and is compatible with code for a):
  3696.  
  3697. OBJECT b OF a
  3698.   bla, x, burp
  3699. ENDOBJECT
  3700.  
  3701. is equivalent to:
  3702.  
  3703. OBJECT b
  3704.   next, index, term         /* from a */
  3705.   bla, x, burp
  3706. ENDOBJECT
  3707.  
  3708. with DEF p:b, you can directly not only access p.bla as usual,
  3709. but also p.next.
  3710.  
  3711. as an example, if one would have a module with an OBJECT to
  3712. implement a certain datatype (for example a doubly-linked-list),
  3713. and PROCs to support it, one could simply inherit from it, adding
  3714. own data to the object, and use the _existing_ functions to
  3715. manipulate the list. However, it's only in combination with
  3716. methods (descibed below), inheritance can show it's real power.
  3717.  
  3718.  
  3719. 14C. data hiding (EXPORT/PRIVATE/PUBLIC)
  3720. ----------------------------------------
  3721. E has a very handy data-hiding mechanism. Other languages, like C++,
  3722. use data-hiding on classes, which raises the need for kludges (like
  3723. 'friends'), and makes datahiding insecure (Eiffel). E's datahiding
  3724. works on the module-level, which can model class-level datahiding,
  3725. but enables more intelligent schemes also.
  3726.  
  3727. PRIVATE and PUBLIC let you declare a section of an object as visible
  3728. to the outer world or not; the outer world here is all code outside
  3729. the module. for the code within a module, everything is always visible.
  3730. example:
  3731.  
  3732.  
  3733. OBJECT mydata PRIVATE                   -> whole object is private
  3734.   bla:PTR TO mydata, burp, grrr:INT
  3735. ENDOBJECT
  3736.  
  3737. OBJECT aaargh
  3738.   blerk:PTR TO aaargh                   -> public
  3739. PRIVATE
  3740.   x:INT, y:INT, z:INT                   -> private
  3741. PUBLIC
  3742.   hmpf[10]:ARRAY OF mydata              -> public again
  3743. ENDOBJECT
  3744.  
  3745.  
  3746. an object is by default public, an occuring PRIVATE or PUBLIC
  3747. acts as a toggle-switch to the objects current visibility. In the
  3748. first object, all is private. The second object has only (x,y,z)
  3749. as private. PRIVATE and PUBLIC keywords may occur:
  3750. - in the object header line
  3751. - as a line on itself in the object-def
  3752. - preceding decls in an object-def
  3753. (i.e virtually anywhere)
  3754.  
  3755. Why datahiding?
  3756. If you want to know why datahiding is a good technique, you'd
  3757. probably want to read a good book on OO. But in short: it is
  3758. generally assumed that lots of problems in maintaining and
  3759. enhancing large pieces of software is the fact that it's hard to change
  3760. things because lots of code start to depend on certain structures
  3761. in your program. if you datahide an object, only the code within a
  3762. module will rely on the format of objects, and you can easily change
  3763. both representation of an object (for example changing a stack
  3764. implementation from ARRAY to a linked list) and the code that
  3765. works with it. If a lot of code of a large app depend on the fact
  3766. that the stack is an ARRAY, you won't be able to simply change
  3767. it, which will lead to kludges. In general, try to datahide as
  3768. much as possible without becoming too restrictive on the use
  3769. of your object. Using methods (below) will often enable you to
  3770. keep the whole object private.
  3771.  
  3772.  
  3773. 14D. methods and virtual methods
  3774. --------------------------------
  3775. A method is much like a PROC, only now it's part of an OBJECT. It
  3776. also allows you to exploit Polymorhism on objects, as we'll see
  3777. below. definition of a method:
  3778.  
  3779.  
  3780. OBJECT blerk PRIVATE
  3781.   x:PTR TO blerk, y:INT, z
  3782. ENDOBJECT
  3783.  
  3784. PROC getx() OF blerk IS self.x
  3785.  
  3786.  
  3787. the 'OF blerk' part tells the compiler it belongs to the object
  3788. 'blerk'. Note that apart from the 'OF' the syntax is completely
  3789. like a 'PROC', however, it can't be invoked as one, and also
  3790. functions quite differently.
  3791.  
  3792. 'self' is a local variable that is available in every method, and
  3793. is a pointer to the object that the method belongs to (in this
  3794. case 'self:PTR TO blerk'. This function just returns the value
  3795. of the x field of blerk, which actually makes sense, given that
  3796. this allows you to later change whatever x represents.
  3797.  
  3798. we may call methods similar to object selections ".":
  3799.  
  3800.  
  3801. DEF a:PTR TO blerk
  3802. NEW a
  3803. ...
  3804. a.getx()           -> invoke method getx() on object a
  3805.  
  3806.  
  3807. in this example, upon invocation `a' becomes the value of `self'
  3808. during the execution of getx().
  3809.  
  3810. sofar the use of methods has been nice, but hasn't show us it's
  3811. real power, which only comes when used with inheritance.
  3812.  
  3813. If I inherit an object that has methods, I automatically get
  3814. those in the new object:
  3815.  
  3816.  
  3817. OBJECT burp OF blerk PRIVATE        -> same as blerk, + extra field
  3818.   prut:INT
  3819. ENDOBJECT
  3820.  
  3821. DEF b:PTR TO burp
  3822. NEW b
  3823. ...
  3824. b.getx()                            -> same method
  3825.  
  3826.  
  3827. The interesting thing is now, that instead of inheriting a method,
  3828. you may also redefine it:
  3829.  
  3830.  
  3831. PROC getx() OF burp IS self.x+1
  3832.  
  3833.  
  3834. (it goes without saying that we may also add new methods)
  3835. so where appropriate, we can choose to modify slightly the
  3836. behaviour of methods we get from other objects, while the
  3837. interface to it (i.e. 'getx()') stays the same. Not only
  3838. does this allow us to reuse code selectively, we can also make use
  3839. of polymorhism:
  3840.  
  3841.  
  3842. PROC dosomething(o:PTR TO blerk)
  3843.   ...
  3844.   o.getx()
  3845.   ...
  3846. ENDPROC
  3847.  
  3848. dosomething(a)
  3849. dosomething(b)
  3850.  
  3851.  
  3852. we may call that PROC with both a and b, since both are compatible
  3853. with a blerk object. But which of the two method implementations of
  3854. getx() is invoked at o.getx()? Answer: both are. Method calls in E
  3855. are what virtual method calls are in other languages: they dynamically
  3856. act on the real type of an object (o) and call the appropriate method.
  3857.  
  3858. A more clear example:
  3859.  
  3860.  
  3861. -> classical OO polymorphic example
  3862.  
  3863. OBJECT loc
  3864.   PRIVATE xpos:INT, ypos:INT
  3865. ENDOBJECT
  3866.  
  3867. OBJECT point OF loc
  3868.   PRIVATE colour:INT
  3869. ENDOBJECT
  3870.  
  3871. OBJECT circle OF point
  3872.   PRIVATE radius:INT
  3873. ENDOBJECT
  3874.  
  3875. PROC show() OF loc IS WriteF('I''m a Location!\n')
  3876. PROC show() OF point IS WriteF('I''m a Point!\n')
  3877. PROC show() OF circle IS WriteF('I''m a Circle!\n')
  3878.  
  3879. PROC main()
  3880.   DEF x:PTR TO loc,l:PTR TO loc,p:PTR TO point,c:PTR TO circle
  3881.   ForAll({x},[NEW l,NEW p,NEW c],`x.show())
  3882. ENDPROC
  3883.  
  3884.  
  3885. In the above, x is a PTR TO loc, so many would expect x.show() to
  3886. write 'I'm a Location' three times, but instead it writes the
  3887. right string for each object.
  3888.  
  3889. If one would write this example in a non-OO language, one would need
  3890. a SELECT for every operation like show(), testing some value
  3891. present in the object to see what it is. If I would add a new shape
  3892. to this, say:
  3893.  
  3894. OBJECT ellipse OF circle
  3895.  
  3896. I would need to change all SELECTs throughout my app to account for
  3897. it. With object-polymorhism, I can just write a show() method, and
  3898. ALL code throughout my app that calls x.show() will act correctly
  3899. when x is a PTR TO ellipse, even without recompilation!
  3900.  
  3901.  
  3902. It's difficult to show why this is powerful in a few examples, and
  3903. best to discover this is using it in real life apps. and: like I said,
  3904. read a book on it.
  3905.  
  3906.  
  3907. How does polymorphism work?
  3908. In the above examples, it's clear the compiler can't know
  3909. what method it's going to call. that's why E uses a 'class
  3910. object', and every object created gets a ptr to this object.
  3911. In the class object, all information is stored that is common
  3912. for all objects of that type, such as pointers to methods.
  3913. when the E compiler sees a call like x.show(), instead of
  3914. looking directly at the show() that belongs to the type of
  3915. x (i.e. loc), it will generate code to retrieve the pointer
  3916. to the show() method from loc's class object. since the
  3917. class object for point looks the same as loc (only maybe
  3918. slightly larger), that code will automatically call point's
  3919. show(), when x is really a point object. This is sometimes
  3920. called runtime binding.
  3921.  
  3922. Objects that have methods therefore always are 4 bytes larger
  3923. than you expect them to be, since they contain a class object
  3924. pointer. This pointer is automatically installed by NEW, which
  3925. is the reason _currently_ NEW is the only way to create such
  3926. an object.
  3927.  
  3928. If a method is declared with the sole purpose of enabling
  3929. subclasses to redefine it (this type of class is known as
  3930. a virtual baseclass in some languages), one may use EMPTY:
  3931.  
  3932. PROC bla() OF obj IS EMPTY
  3933.  
  3934. One may effectively add methods to system OBJECTs:
  3935.  
  3936. OBJECT mygadget OF gadget    -> from intuition!
  3937.   -> extra fields here
  3938. ENDOBJECT
  3939.  
  3940. PROC creategadget() OF mygadget IS ...
  3941.  
  3942.  
  3943.  
  3944. +---------------------------------------------------------------+
  3945. |                      15. INLINE ASSEMBLY            |
  3946. +---------------------------------------------------------------+
  3947.  
  3948. 15A. identifier sharing
  3949. -----------------------
  3950. As you've probably guessed from the example in chapter 5D, assembly
  3951. instructions may be freely mixed with E code. The big secret is, that
  3952. a complete assembler has been built in to the compiler.
  3953. Apart from normal assembly addressing modes, you may use the following
  3954. identifiers from E:
  3955.  
  3956. mylabel:
  3957. LEA mylabel(PC),A1        /* labels */
  3958.  
  3959. DEF a                /* variables */
  3960. MOVE.L (A0)+,a            /* note that <var> is <offset>(A4) (or A5) */
  3961.  
  3962. MOVE.L dosbase,A6        /* library call identifiers */
  3963. JSR    Output(A6)
  3964.  
  3965. MOVEQ  #TRUE,D0            /* constants */
  3966.  
  3967.  
  3968. EC's assembler supports following constructs,
  3969.  
  3970. where
  3971. n    = registernum
  3972. x    = index
  3973. lab    = label, from: "label:" or "PROC label()"
  3974. abs    = absolute addressing
  3975. s    = size. L, W or B where appropriate.
  3976.  
  3977. - addressing modi supported by EC:
  3978.  
  3979.   Dn, An, (An), (An)+, -(An), x(An), x(An,Dn.s),
  3980.   lab(PC), lab(PC,Dn.s), abs, abs.W
  3981.  
  3982.   (note: write abs.W in hexadecimal, to not confuse it with a float
  3983.    value, i.e. write   MOVE.L $4.W,A6   )
  3984.  
  3985. - supported partially:
  3986.  
  3987.   #<constexp>
  3988.  
  3989. - not supported:
  3990.  
  3991.   lab (same as abs), #lab
  3992.   use LEA lab(PC),An instead.
  3993.  
  3994. - extra modi:
  3995.  
  3996.   var.s (transfers contents of var. optionally size is ".W" or ".B",
  3997.          default is ".L")
  3998.  
  3999.   LibraryFunction(A6)
  4000.  
  4001.   example:
  4002.  
  4003.   ...
  4004.   MOVE.W myvar.W,D0     -> move lowword of 'myvar'
  4005.   ...
  4006.   MOVE.L dosbase,A6
  4007.   JSR    Write(A6)
  4008.  
  4009.  
  4010. 15B. the inline assembler compared to a macro assembler
  4011. -------------------------------------------------------
  4012. The inline assembler differs somewhat from your average macro-assembler,
  4013. and this is caused mainly by the fact that it is an extension to E,
  4014. and thus it obeys E-syntax. Main differences:
  4015.  
  4016. - comments are with /* */ and not with ";", they have a different meaning.
  4017. - keywords and registers are in uppercase, everything is case sensitive
  4018. - no macros and other luxury assembler stuff (well, there's the complete
  4019.   E language to make up for that ...)
  4020. - You should be aware that registers A4/A5 may not be trashed by inline
  4021.   assembly code, as these are used by E code. Also, if your code
  4022.   can be called by code that is register-allocated, you should preserve
  4023.   D3-D7. a
  4024.  
  4025.     MOVEM.L D3-D7,-(A7); /* inline asm */; MOVEM.L (A7)+,D3-D7
  4026.  
  4027.   should help if problems occur.
  4028. - no support for LARGE model/reloc-hunks in assembly _YET_.
  4029.   This means practically that you have to use (PC)-relative addressing
  4030.   for now (which is faster anyway).
  4031.  
  4032.  
  4033. 15C. ways using binary data (INCBIN/CHAR..)
  4034. -------------------------------------------
  4035.  
  4036. INCBIN
  4037.  
  4038. syntax:        INCBIN <filename>
  4039.  
  4040. includes a binary file at the exact spot of the statement, should
  4041. therefore be separate from the code. Example:
  4042.  
  4043. mytab: INCBIN 'df1:data/blabla.bin'
  4044.  
  4045. LONG, INT, CHAR
  4046.  
  4047. syntax:        LONG <values>,...
  4048.         INT <values>,...
  4049.         CHAR <values>,...
  4050.  
  4051. Allows you to place binary data directly in your program. Functions much
  4052. like DC.x in assembly. Note that the CHAR statement also takes strings,
  4053. and will always be aligned to an even word-boundary. Example:
  4054.  
  4055. mydata: LONG 1,2; CHAR 3,4,'hi folks!',0,1
  4056.  
  4057.  
  4058. 15D. OPT ASM
  4059. ------------
  4060. OPT ASM is discussed also in chapter 16A. It allows you to operate
  4061. 'EC' as an assembler. There's no good reason to use EC over some
  4062. macro-assembler, except that it is significantly faster than for example
  4063. A68k, equals DevPac and loses from AsmOne (sob 8-{). You will also have
  4064. a hard time trying to squeeze your disks of old seka-sources through EC,
  4065. because of the differences as described in chapter 15B. If you want to write
  4066. assembly programs with EC, and want to keep your sources compatible with
  4067. other assemblers, simply precede all E-specific elements with a ";",
  4068. EC will use them, and any other assembler will see them as a comment.
  4069. Example:
  4070.  
  4071. ; OPT ASM
  4072.  
  4073. start:    MOVEQ    #1,D0        ;-> do something silly
  4074.     RTS            ;-> and exit
  4075.  
  4076. this will be assembled by any assembler, including EC
  4077.  
  4078.  
  4079. 15E. Inline asm and register variables
  4080. ---------------------------------------
  4081. register variables are a great companion to inline assembly, as
  4082. they function just as registers, but at the same time have clear
  4083. identifiers instead of Dx, and also are automatically saved and
  4084. restored by E code. example:
  4085.  
  4086. PROC bla()
  4087.   DEF count:REG
  4088.   MOVEQ #10,count
  4089. loop: WriteF('count=\d\n',count)
  4090.   DBRA count,loop
  4091. ENDPROC
  4092.  
  4093. all instruction that can work with a Dx EA, work with register
  4094. variables. examples:
  4095.  
  4096. MOVEQ #1,a
  4097. MOVEM.L D0/D1/a/b/A0,-(A7)
  4098. LSL.L a,b
  4099.  
  4100. etc.
  4101.  
  4102. as may be known, EC uses D3-D7 for these register variables. If you wish
  4103. to write code that freely mixes assembly with E, it's advisable to
  4104. keep longer-term values in register variables, and temporaries in
  4105. D0-D2/A0-A3/A6
  4106.  
  4107. +---------------------------------------------------------------+
  4108. |            16. TECHNICAL AND IMPLEMENTATION ISSUES        |
  4109. +---------------------------------------------------------------+
  4110.  
  4111. 16A. the OPT keyword
  4112. --------------------
  4113.  
  4114. OPT, LARGE, STACK, ASM, NOWARN, DIR, OSVERSION, MODULE, EXPORT, RTD, REG
  4115.  
  4116. syntax:        OPT <options>,...
  4117.  
  4118. allows you to change some compiler settings:
  4119.  
  4120. LARGE        Sets code and data model to large. Default is small;
  4121.         the compiler generates mostly pc-relative code, with a
  4122.         max-size of 32k. With LARGE, there are no such limits,
  4123.         and reloc-hunks are generated (see 0D, LARGE).
  4124. STACK=x        Set stacksize to x bytes yourself. Only if you know what
  4125.         you are doing. Normally the compiler makes a very good
  4126.         guess itself at the required stack space (see 16C).
  4127. ASM        Set the compiler to assembly mode. From there on, only
  4128.         assembly instructions are allowed, and no initialisation
  4129.         code is generated. (see 15D, inline assembly)
  4130. NOWARN        Shut down warnings. The compiler will warn you if it
  4131.         *thinks* your program is incorrect, but still syntactically
  4132.         ok. (see 0D, -n)
  4133. DIR=moduledir    Sets the directory where the compiler searches for modules.
  4134.         default='emodules:'
  4135. OSVERSION=vers    Default=33 (v1.2). Sets the minimum version of the kickstart
  4136.         (like 37 for v2.04) your program runs on. That way, your
  4137.         program simply fails while the dos.library is being opened
  4138.         in the initialisation code when running on an older machine.
  4139.         However, checking the version yourself and giving an
  4140.         appropriate error-message is more helpful for the user.
  4141. MODULE        denotes this source to be a module. (see 10C)
  4142. EXPORT        automatically export all declarations in a module
  4143. RTD        generates RTD's instead of RTS in the main source.
  4144.         020+ only. [experimental opti]
  4145. 020,881,040    generate code for these CPU's. not really usable yet.
  4146. REG=n        use n register for register-allocation.
  4147.  
  4148. example:
  4149.  
  4150. OPT STACK=20000,NOWARN,DIR='df1:modules',OSVERSION=39,REG=3
  4151.  
  4152.  
  4153. 16B. small/large model
  4154. ----------------------
  4155. Amiga E lets you choose between SMALL and LARGE code/data model.
  4156. Note that most of the programs you'll write (especially if you just
  4157. started with E) will fit into 32k when compiled: you won't have to
  4158. bother setting some code-generation model. You'll recognise the
  4159. need for LARGE model as soon as EC starts complaining that it can't
  4160. squeeze your code into 32k anymore. To compile a source with LARGE model:
  4161.  
  4162. 1> ec -l sizy.e
  4163.  
  4164. or better yet, put the statement
  4165.  
  4166. OPT LARGE
  4167.  
  4168. at the top of your code.
  4169.  
  4170.  
  4171. 16C. stack organisation
  4172. -----------------------
  4173. To store all local and global variables, the run-time system of an
  4174. executable generated by Amiga E allocates a chunk of memory,
  4175. from which it takes some fixed part to store all global variables.
  4176. The rest will be dynamically used as functions get called.
  4177. as a function is called in E, space on the stack is reserved
  4178. to store all local data, which is released upon exit of the function.
  4179. That is why having large arrays of local data can be dangerous when
  4180. used recursively: all data of previous calls to the same function
  4181. still resides on the stack and eats up large parts of the free stack
  4182. space. However, if PROC's are called in a linear fashion, there's
  4183. no way the stack will overflow.
  4184. Example:
  4185.  
  4186. global data:        10k (arrays e.d)
  4187. local data PROC #1:     1k
  4188. local data PROC #1:     3k
  4189.  
  4190. the runtime system always reserves an extra 10k over this for normal
  4191. recursion (for example with small local-arrays) and additional buffers/
  4192. system spaces, thus will allocate a total of 24k stack space
  4193.  
  4194.  
  4195. 16D. hardcoded limits
  4196. ---------------------
  4197.  
  4198. Note these signs: (+-)    just about, depends on situation,
  4199.                   (n.l.)  no clear limit, but this seems reasonable.
  4200.  
  4201. --------------------------------------------------------------------------
  4202. OBJECT/ITEM                    SIZE/AMOUNT/MAX
  4203. --------------------------------------------------------------------------
  4204.  
  4205. value datatype CHAR                0 .. 255
  4206. value datatype INT                -32 k .. +32 k
  4207. value datatype LONG/PTR                -2 gig .. +2 gig
  4208.  
  4209. identifierlength                100 bytes (n.l.)
  4210. length of one source line            2000 lexical tokens (+-)
  4211. source length                    2 gig (theoretically)
  4212. constant lists                    few hundred elements (+-)
  4213. constant strings                1000 chars (n.l.)
  4214. max. nesting depth of loops (IF, FOR etc.)    500 deep
  4215. max. nesting depth of comments            infinite
  4216.  
  4217. #of local variables per procedure        8000
  4218. #of global variables                7500
  4219. #of arguments to own functions            8000 (together with locals)
  4220. #of arguments to E-varargs functions (WriteF())    64 (v2.1) / 1024 (v2.5)
  4221.  
  4222. one object (allocated local/global or dyn.)    8 k
  4223. one array, list or string (local or global)    32 k
  4224. one string (dynamically)            32 k
  4225. one list (dynamically)                128 k
  4226. one array (dynamically)                2 gig
  4227. objects with NEW                64k elem.
  4228. CHAR/INT/LONG with NEW                2 gig.
  4229.  
  4230. local data per procedure            250 meg
  4231. global data                    250 meg
  4232.  
  4233. code size of one procedure            32 k
  4234. code size of executable                32 k SMALL, 2 gig LARGE model
  4235. current practical limit (may extend in future)    2-5 meg (v2.1) / 10 meg (v2.5)
  4236.  
  4237. buffersize of generated code and identifiers    relative to source
  4238. buffersize of labels/branches and intermediate    independently (re)allocated
  4239.  
  4240.  
  4241.  
  4242. 16E. error messages, warnings and the unreferenced check
  4243. --------------------------------------------------------
  4244. Sometimes, when compiling your source with EC, you get a message
  4245. of the sort UNREFERENCED: <ident>, <ident>, ...
  4246. This is the case when you have declared variables, functions or labels,
  4247. but did not use them. This is an extra service rendered to you by the
  4248. compiler to help you find out about those hard to find errors.
  4249.  
  4250. There are several warnings that the compiler issues to notify you that
  4251. something might be wrong, but is not really an error.
  4252.  
  4253.  
  4254. - "A4/A5 used in inline assembly"
  4255.   This is the warning you'll get if you use registers A4 or A5 in your
  4256.   assembly code. The reason for this is that those registers are used
  4257.   internally by E to address the global and local variables respectively.
  4258.   Of course there might be a good reason to use these, like doing
  4259.   a MOVEM.L A4/A5,-(A7) before a large part of inline assembly code
  4260.  
  4261. - "keep an eye on your stacksize"
  4262. - "stack is definitely too small"
  4263.   Both these may be issued when you use OPT STACK=<size>. The compiler
  4264.   will simply match your <size> against its own estimate (see 16C),
  4265.   and issue the former warning if it thinks it's ok but a bit on the small
  4266.   side, and the latter if it's probably too small.
  4267.  
  4268. - 'suspicious use of "=" in void expressions (s). (line %d)'
  4269.   This warning is issued if you write expressions like 'a=1' as a
  4270.   statement. One reason for this is the fact that a comparison doesn't
  4271.   make much sense as a statement, but the main reason is that it could be
  4272.   an often occurring typo for 'a:=1'. Forgetting those ":" may be hard to
  4273.   find, and it may have disastrous consequences.
  4274.  
  4275. - 'module changed OPT settings'
  4276.   If you use a module that has OPT OSVERSION=37, this changes the
  4277.   OPT for the main program too. this warning serves to make you aware
  4278.   of this. put such an OPT in the main program too to get rid of it.
  4279.  
  4280. - 'variable used as function'
  4281.   in v3, arbitrary variables may be used as function. this function
  4282.   is there to warn you so you don't accidentally do this.
  4283.  
  4284. - 'code outside PROCs'
  4285.   You wrote E code in between PROCs, which is only rarely useful.
  4286.  
  4287. Errors.
  4288. The compiler will print the source-code-line that caused the error
  4289. below it, with a cursor at the exact spot. The cursor denotes the spot
  4290. the compiler was when it _discovered_ the error, it is thus likely
  4291. that the symbol that caused the error is the one just _before_ the
  4292. cursor.
  4293.  
  4294. - 'syntax error'
  4295.   Most common error. This error is issued either when no other
  4296.   error is appropriate or your way of ordering code in your sources
  4297.   is too abnormal.
  4298.  
  4299. - 'unknown keyword/const'
  4300.   You have used an identifier in uppercase (like "IF" or "TRUE"), and
  4301.   the compiler could not find a definition for it. Causes:
  4302.   * mispelled keyword
  4303.   * you used a constant, but forgot to define it in a CONST statement
  4304.   * you forgot to specify the module where your constant is defined
  4305.  
  4306. - '":=" expected'
  4307.   You have written a FOR statement or an assignment, and put something
  4308.   other than ":=" in its place.
  4309.  
  4310. - 'unexpected characters in line'
  4311.   You used characters that have no syntactic meaning in E outside of
  4312.   a string. examples: "@!&\~"
  4313.  
  4314. - 'label expected'
  4315.   At some places, for example after the PROC or JUMP keyword,
  4316.   a label identifier is required. You wrote something else.
  4317.  
  4318. - '"," expected'
  4319.   In specifying a list of items (for example a parameter list)
  4320.   you wrote something else instead of a comma.
  4321.  
  4322. - 'variable expected'
  4323.   This construction requires a variable, example:
  4324.   FOR <var>:= ... etc.
  4325.  
  4326. - 'value does not fit in 32 bit'
  4327.   In specifying a constant value (see 2A-2E) you wrote too
  4328.   large a number, examples:  $FFFFFFFFF, "abcdef".
  4329.   Also occurs when you define a SET of more than 32 elements.
  4330.  
  4331. - 'missing apostrophe/quote'
  4332.   You forgot the ' at the other end of a string.
  4333.  
  4334. - 'incoherent program structure'
  4335.   * you started a new PROC before ending the last one
  4336.   * you don't nest your loops properly, for example:
  4337.     FOR
  4338.       IF
  4339.       ENDFOR
  4340.     ENDIF
  4341.  
  4342. - 'illegal command-line option'
  4343.   In specifying 'EC -opt source' you wrote something for '-opt'
  4344.   that is not a legal option to EC.
  4345.  
  4346. - 'division and multiplication 16bit only'
  4347.   The compiler detected that you were about to use 32bits
  4348.   for * or /. This would not have the desired result at runtime.
  4349.   (see 9G, Mul() and Div()).
  4350.  
  4351. - 'superfluous items in expression/statement'
  4352.   After the compiler already compiled your statement, it still found
  4353.   lexical tokens instead of an end of line. You probably forgot
  4354.   the <lf> or ";" to separate two statements.
  4355.  
  4356. - 'procedure "main" not available'
  4357.   Your program does not include a main procedure !
  4358.  
  4359. - 'double declaration of label'
  4360.   You declared a label twice, for example:
  4361.   label:
  4362.   PROC label()
  4363.  
  4364. - 'unsafe use of "*" or "/"'
  4365.   This again has to do with 16bit instead of 32bit * and /.
  4366.   See 'division and multiplication 16bit only'.
  4367.  
  4368. - "reading sourcefile didn't succeed"
  4369.   Check your source spec. that you gave with 'ec mysource'
  4370.   make sure the file ends in '.e'
  4371.  
  4372. - "writing executable didn't succeed"
  4373.   Trying to write the generated code as an executable caused a dos
  4374.   error. For example, the executable that did already exist could
  4375.   not be overwritten.
  4376.  
  4377. - 'no args'
  4378.   "USAGE: ec [-opts] <sourcecodefilename> (`.e' is added)"
  4379.   You get this by just typing 'ec' without any arguments.
  4380.  
  4381. - 'unknown/illegal addressing mode'
  4382.   This error is reported only by the inline assembler. Possible causes are:
  4383.   * you used some addressing mode that does not exist on the 68000
  4384.   * the addressing mode exists, but not for this instruction.
  4385.     not all assembly instructions support all combinations of
  4386.     effective addresses for source and destination.
  4387.  
  4388. - 'unmatched parentheses'
  4389.   Your statement has more "(" than ")" or the other way around
  4390.  
  4391. - 'double declaration'
  4392.   One identifier is used in two or more declarations.
  4393.  
  4394. - 'unknown identifier'
  4395.   An identifier is not used in any declaration; it is unknown.
  4396.   You probably forgot to put it in a DEF statement.
  4397.  
  4398. - 'incorrect #of args or use of ()'
  4399.   * You forgot to put "(" or ")" at the right spot
  4400.   * you supplied the incorrect #of arguments to some function
  4401.  
  4402. - 'unknown e/library function'
  4403.   You wrote an identifier with the first character in uppercase, and
  4404.   the second in lowercase, but the compiler could not find a definition.
  4405.   Possible causes:
  4406.   * Misspelled name of function
  4407.   * You forgot to include the module that defines this library call.
  4408.  
  4409. - 'illegal function call'
  4410.   Rarely occurs. You get this one if you try to construct weird
  4411.   function calls like nested WriteF()'s. Example:
  4412.   WriteF(WriteF('hi!'))
  4413.  
  4414. - 'unknown format code following "\"'
  4415.   You specified a format code in a string which is illegal.
  4416.   (see 2F for a listing of format codes)
  4417.  
  4418. - '/* not properly nested comment structure */'
  4419.   The #of '/*' is unequal to the #of '*/', or is placed in a funny order.
  4420.  
  4421. - 'could not load binary'
  4422.   <filespec> in INCBIN <filespec> could not be read.
  4423.  
  4424. - '"}" expected'
  4425.   You started an expression with "{<var>" , but forgot the "}"
  4426.  
  4427. - 'immediate value expected'
  4428.   Some constructions require an immediate value instead of an expression.
  4429.   Example:
  4430.   DEF s[x*y]:STRING   /* wrong: only something like s[100]:STRING is legal */
  4431.  
  4432. - 'incorrect size of value'
  4433.   You specified an unacceptably large (or small) value for some construction.
  4434.   Examples:
  4435.   DEF s[-1]:STRING, t[1000000]:STRING    /* needs to be 0..32000  */
  4436.   MOVEQ #1000,D2                         /* needs to be -128..127 */
  4437.  
  4438. - 'no e code allowed in assembly modus'
  4439.   You wish to operate the compiler as an assembler by writing 'OPT ASM',
  4440.   but, by accident, wrote some E code.
  4441.  
  4442. - 'illegal/inappropriate type'
  4443.   At someplace where a <type> spec. was needed, you wrote something
  4444.   inappropriate. Examples:
  4445.   DEF a:PTR TO ARRAY       /* no such type */
  4446.   [1,2,3]:STRING
  4447.  
  4448. - '"]" expected'
  4449.   You started with "[", but never ended with "]"
  4450.  
  4451. - 'statement out of local/global scope'
  4452.   A breakpoint of scope is the first PROC statement. before that,
  4453.   only global definitions (DEF,CONST,MODULE etc.) are allowed, and no code.
  4454.   In the second part, only code and function definitions are legal, no
  4455.   global definitions.
  4456.  
  4457. - 'could not read module correctly'
  4458.   A dos error occurred while trying to read a module from a MODULE
  4459.   statement. Causes:
  4460.   * emodules: was not assigned properly
  4461.   * module name was misspelled, or did not exist in the first place
  4462.   * you wrote MODULE 'bla.m' instead of MODULE 'bla'
  4463.  
  4464. - 'workspace full!'
  4465.   Rarely occurs. If it does, you'll need the '-m' (ADDBUF) option to
  4466.   manually force EC to make a bigger estimate on the needed amount of
  4467.   memory. Try compiling with -m2, then -m3 until the error disappears.
  4468.   You'll probably be writing huge applications with giant amounts
  4469.   of data just to even possibly get this error.
  4470.  
  4471. - 'not enough memory while (re-)allocating'
  4472.   Just like that. Possible solutions:
  4473.   1. You were running other programs in multitasking. Leave them and try again.
  4474.   2. You were low on memory anyway and your memory was fragmented.
  4475.      Try rebooting.
  4476.   3. None of 1-2. Buy a memory expansion (um).
  4477.  
  4478. - 'incorrect object definition'
  4479.   You were being silly while writing the definitions between OBJECT and
  4480.   ENDOBJECT. (see 8F to find out how to do it right).
  4481.  
  4482. - 'illegal use of/reference to object'
  4483.   If you use expressions like ptr.member, member needs to be a legal
  4484.   member of the object ptr is pointing to.
  4485.  
  4486. - 'incomplete if-then-else expression'
  4487.   If you use IF as an operator (see 4E), then an ELSE part
  4488.   needs to be present: an expression with an IF in it always needs to
  4489.   return a value, while a statement with an IF in it can just 'do nothing'
  4490.   if no ELSE part is present.
  4491.  
  4492. - 'unknown object identifier'
  4493.   You used an identifier that was recognised by the compiler as being
  4494.   part of some object, but you forgot to declare it. Causes:
  4495.   * misspelled name
  4496.   * missing module
  4497.   * the identifier in the module is spelled not like you expected
  4498.     from the RKRM's. Check with ShowModule.
  4499.     Note that amiga-system-objects inherit from assembly identifiers,
  4500.     not from C. Second: identifiers obey E-syntax.
  4501.  
  4502. - 'double declaration of object identifier'
  4503.   One identifier used in two object definitions
  4504.  
  4505. - 'reference(s) out of 32k range: switch to LARGE model'
  4506.   Your program is growing larger than 32k. Simply put 'OPT LARGE'
  4507.   in your source and code on. (see 16B).
  4508.  
  4509. - 'reference(s) out of 256 byte range'
  4510.   You probably wrote BRA.S or Bcc.S over too great a distance.
  4511.  
  4512. - 'too sizy expression'
  4513.   You used a list [], possibly recursive [[]], that is too sizy.
  4514.  
  4515. - 'incomplete exception handler definition'
  4516.   You probably used EXCEPT without HANDLE, or the other way round
  4517.   (see 13A on exception handling).
  4518.  
  4519. - 'not allowed in a module'
  4520.   You're doing one of the few things you can't do in a module,
  4521.   such as global variables with initialisations.
  4522.  
  4523. - 'allowed in modules only'
  4524.   you probably use EXPORT in your main source
  4525.  
  4526. - 'this doesn't make sense'
  4527.   general error.
  4528.  
  4529. - 'you need a newer version of EC for this :-)'
  4530.   You probably use a module that was compiled with a newer
  4531.   version of EC than you currently have.
  4532.  
  4533. - 'no matching "["'
  4534.   within a statement, a "]" was found, without a matching "]".
  4535.  
  4536. - 'this instruction needs a better CPU/FPU (see OPT)'
  4537.   You use a construction (probably an asm instruction) that
  4538.   requires an OPT 020 or the like.
  4539.  
  4540. - 'object doesn't understand this method'
  4541.   you invoke a method on a object that wasn't defined
  4542.   for it's type.
  4543.  
  4544. - 'method doesn't have same #of args as method of baseclass'
  4545.   If you redefine a method, you have to make sure the new one
  4546.   has the same #of args as the original.
  4547.  
  4548. - 'toomuch register variables in this function'
  4549.   If you use :REG to assign register variables yourself,
  4550.   you can't use more than 5, currently.
  4551.  
  4552. - 'Linker can't find all symbols'
  4553.   If you use a module A that uses again a module B,
  4554.   B also needs to linked. A relies on certain PROCs to
  4555.   be present in B, and if B was recompiled with those
  4556.   PROCs removed, the linker has trouble putting your
  4557.   exe together.
  4558.  
  4559. - 'could not open "mathieeesingbas.library"'
  4560.   If you use float code, the compiler itself may need
  4561.   floatfunctions to be able to generate code.
  4562.  
  4563. - 'illegal destructor definition'
  4564.   You defined an end() method with arguments (or with a returnvalue)
  4565.  
  4566. - 'implicit initialisation of private members'
  4567.   You write a [...] or NEW [...] expression that has private parts.
  4568.  
  4569. - 'double method declaration'
  4570.   You defined a method on this object twice.
  4571.  
  4572.  
  4573. 16F. compiler buffer organisation and allocation
  4574. ------------------------------------------------
  4575. When you get the error 'workspace full' (very unlikely), or want
  4576. to know what really happens when your program is compiled, it's useful
  4577. to know how EC organises its buffers.
  4578.  
  4579. A compiler, and in this case EC needs buffers to keep track of all sorts
  4580. of things, like identifiers etc., and it needs a buffer to keep the
  4581. generated code in. EC doesn't know how big these buffers need to be.
  4582. for most buffers, like the one for various strcutures, this is no
  4583. problem: if the buffer is full while compiling, EC just allocates a
  4584. new piece of memory and continues. Other buffers, like the one for
  4585. the generated code, need to be a continuous block of memory that doesn't
  4586. move while compiling: EC needs to make a pretty good estimate of
  4587. this buffersize to be able to compile small and large sources alike.
  4588. To do this, EC computes the needed memory relative to the size of
  4589. your source code, and adds a nice amount to it. This way, in 99% of the
  4590. cases, EC will have allocated enough memory to compile just about any
  4591. source, in other cases, you'll get the error and have to specify more
  4592. memory with the '-m' (ADDBUF) option.
  4593.  
  4594. Experiment with different types and sizes of example-sources in combination
  4595. with the '-b' (SHOWBUF) option (see 0D) to see how this works in practice.
  4596.  
  4597.  
  4598. 16G. register allocation
  4599. ------------------------
  4600. E v3 support a register allocation, which is a technique to keep
  4601. variables in registers instead of on the stack. For normal code
  4602. that uses OS-routines you won't notice the difference very much,
  4603. but for tight computation-loops, this optimisation can make a big
  4604. difference. There are two ways to use register allocation:
  4605.  
  4606. - with the option REG.
  4607.   If you write for example EC REG=3 bla.e, (max=5, currently),
  4608.   EC will compute for each PROC the 3 most-used variables in
  4609.   registers. Register allocation is a technique that tries to be
  4610.   intelligent: it will compute for each var a weight, and will
  4611.   use heuristics to increase that weight, for example a var used
  4612.   in a FOR loop gets relatively a higher weight than one outside
  4613.   it, and one in an IF gets an even lower weight. These weights
  4614.   are combined, so a WHILE in a FOR gets quite a high weight.
  4615.  
  4616. - DIY: you can put the keyword REG in front of any type in a
  4617.   declaration, for example:
  4618.  
  4619.     DEF x:REG, s[4]:REG LIST
  4620.  
  4621.   you can do this if you don't trust the register-allocator,
  4622.   or if you want to fine-tune just one PROC. You can even use
  4623.   both together: if in a PROC you have one var with :REG,
  4624.   compiling with REG=5 will allow EC to pick the remaining 4
  4625.   by itself.
  4626.  
  4627. The default is REG=0, so EC works much like the older versions.
  4628.  
  4629. The variables that CAN be allocated are only local variables
  4630. that are not parameters. also, if you take the address of
  4631. a variable with {} it can't be put in a register either (guess
  4632. why...). registers can't be allocated in PROCs that have
  4633. an exception handler, for now.
  4634.  
  4635. There are a few things to note when using registers:
  4636. - this part of EC is currently (E v3.0a) was tested to
  4637.   be pretty reliable, but you still check that behaviour is
  4638.   the same as in non-allocated code.
  4639.   it _should_ work ok, but it's too early to guarantee it :-)
  4640.   In short: be careful for now when applying these techniques.
  4641. - EC uses registers D7..D3 for variables, so if you use
  4642.   inline assembly, you need to check that PROCs that use
  4643.   register-allocation or :REG don't trash these (see 15E).
  4644.   The code generated for a PROC automatically saves the
  4645.   registers it uses (callee save) to protect the code that
  4646.   called it.
  4647. - hint: compiling with REG=5 is not inherently fastest,
  4648.   since variable saving on function/library calls also
  4649.   incurs an overhead. REG=3 may be better for some
  4650.   cases. Also if _all_ code in question deals with
  4651.   library calls instead of pure computation, expect no
  4652.   gain from registers.
  4653.  
  4654. -> register allocation will easily make this program twice as fast
  4655.  
  4656. PROC main()
  4657.   DEF a,b=10,c=20,d
  4658.   FOR a:=1 TO 1000000 DO d:=b+c
  4659. ENDPROC
  4660.  
  4661. -> at most 5% faster when using register allocation
  4662.  
  4663. PROC main()
  4664.   DEF a,s[100]:STRING,t
  4665.   t:='putting "a" in a reg won''t give that much of a speedup, I think.'
  4666.   FOR a:=1 TO 100000 DO StrCopy(s,t)
  4667. ENDPROC
  4668.  
  4669.  
  4670. +---------------------------------------------------------------+
  4671. |                 17. Essential E Utilities            |
  4672. +---------------------------------------------------------------+
  4673.  
  4674. 17A. bin/showmodule
  4675. -------------------
  4676. As you might have noticed, E's equivalent for "includes", modules,
  4677. are binary files, much like those usually suplied with Modula2
  4678. compilers, for example. To display the contents of such a file
  4679. in readable ascii form, you may use showmodule:
  4680.  
  4681. showmodule <modulespec>
  4682.  
  4683. examples:
  4684.  
  4685. 1> showmodule emodules:intuition/intuition
  4686. 1> showmodule >gadtools.txt emodules:gadtools
  4687.  
  4688. note that showmodule by default outputs to stdout,
  4689. and may be interrupted at any point by <ctrlc>.
  4690.  
  4691.  
  4692.  
  4693. 17B. sources/utilities/showhunk.e, bin/showhunk
  4694. -----------------------------------------------
  4695. Displays all types of executable files, and also object ".o"
  4696. files as generated by (other) compilers/assemblers.
  4697. will show you the (very simple) structure of executables generated
  4698. by EC, but also support complex overlay-files. also dumps
  4699. labels (like XREF's and XDEF's).
  4700.  
  4701. most important of all, ShowHunk features a disassembler for
  4702. code-hunks. use the option 'DISASM/S'
  4703.  
  4704. showhunk <exefile>
  4705.  
  4706. like:   1> showhunk helloworld
  4707.         1> showhunk disasm dpaint
  4708.  
  4709.  
  4710. 17C. bin/iconvert, bin/pragma2module
  4711. ------------------------------------
  4712. These two utilities are for advanced E-programmers only. if
  4713. you don't feel like one (yet), skip this part.
  4714.  
  4715. [NOTE: like the showmodule utility, the sources to these utilities
  4716.  have been removed from the distribution, because people misused
  4717.  their knowledge of the .m module format. It is PRIVATE. Contact
  4718.  me first if you want to do something with it.]
  4719.  
  4720. Iconvert will convert structure and constant definitions in
  4721. assembly ".i" files to E modules, and pragma2module will do the
  4722. same for SAS/C pragma library definition files. ofcourse, all
  4723. commodores includes have already been converted this way, but
  4724. say you find a nice PD library that you may want to use with E,
  4725. you will need these utilities.
  4726.  
  4727. most libraries come with various includes defining, most obvious,
  4728. the library calls of the library, as well as the constants
  4729. and structures (OBJECTs in E) that it uses. say that it is
  4730. called "tools.library", then it will probably feature:
  4731.  
  4732. pragmas/tools_pragmas.h
  4733. includes/tools.i
  4734.  
  4735. then do:
  4736.  
  4737. 1> pragma2module tools_pragmas.h
  4738.  
  4739. rename the resulting "tools_pragmas.m" to "tools.m" and put it
  4740. in emodules:, check with ShowModule if all went well.
  4741.  
  4742. Now, in your program you may use tools.library:
  4743.  
  4744. MODULE 'tools'
  4745.  
  4746. PROC main()
  4747.   IF (toolsbase:=Openlibrary('tools.library',37))=NIL THEN error()
  4748.  
  4749.   ToolsFunc()
  4750.  
  4751. ...etc.
  4752.  
  4753. convert tools.i with Iconvert to another tools.m, which you place in
  4754. emodules:libraries, for example. Iconvert needs an assembler like
  4755. the PD A68k to do the hard work of understanding the actual assembly.
  4756.  
  4757. 1> iconvert tools.i
  4758.  
  4759. see with showmodule what became of the ".i" file. use in your
  4760. program with:
  4761.  
  4762. MODULE 'libraries/tools'
  4763.  
  4764. DEF x:toolsobj, y=TOOLS_CONST
  4765.  
  4766. converting with Iconvert may require some assembly expertise, as
  4767. Iconvert relies on the correct format of the ".i" file, just like
  4768. commodores assembly includes. About 10% of the ".i" files need
  4769. to be patched by hand to be "convertable". definitions that
  4770. Iconvert judges correctly are amongst others
  4771.  
  4772. <label> EQU <any_expression>
  4773.  
  4774. STRUCTURE <sname>,0      ; if <>0, then   <struct>_SIZEOF
  4775. ULONG <sname>_<label>
  4776. BPTR <sname>_<label>
  4777.    ; etc.
  4778. LABEL <sname>_SIZEOF     ; or "_SIZE"
  4779.  
  4780. to get an idea what kind of assembly-expression Iconvert can
  4781. handle, take a look at commodores assembly includes and compare
  4782. them to the equivalent modules (for example intuition.i).
  4783.  
  4784.  
  4785. 17D. bin/ShowCache, bin/FlushCache
  4786. ----------------------------------
  4787. The E Module Cache is a piece of memory that is able to hold
  4788. modules (.m) between compiles. The first time you use a certain
  4789. module, EC will load it from disk and put it in the cache. the
  4790. second time and on, EC will find it in cache and doesn't have to
  4791. load anything from disk. If EC compiles a module of which an
  4792. old version is present in cache, it will flush it. One can imagine
  4793. that this a tremendous speedup, even for people with HD's when
  4794. they use a lot of modules and recompile often.
  4795.  
  4796. To see what's currently stored in the cache (and how much memory
  4797. it's waisting :-), type:
  4798.  
  4799. 1> ShowCache
  4800.  
  4801. A second utility, FlushCache, allows you to selectively remove modules
  4802. from the cache. Reasons for this can be:
  4803. - you can't afford the memory it uses
  4804. - you created a new .m, with a tool other than EC, so you need to flush
  4805.   by hand.
  4806. The argument to Flushcache is the substring that needs to occur in
  4807. a module name for it to be flushed. no args means flush all.
  4808.  
  4809. 1> FlushCache                        ; empty whole cache
  4810. 1> FlushCache intuition/             ; flush all intuition-related modules
  4811.  
  4812. You can use the EC option 'IGNORECACHE/S' to compile a source without
  4813. using the cache. Wether the cache is full or empty, EC will load
  4814. all from disk, and store nothing new in cache.
  4815.  
  4816. If two EC's try to access the cache simultanuously in multitasking,
  4817. the second EC acts as if it's IGNORECACHE flag were set.
  4818.  
  4819.  
  4820. 17E. rexx/ecompile.rexx
  4821. -----------------------
  4822. [what's keeping the other rexx-scripts?]
  4823.  
  4824. This is a rexx-script for CygnusEd (tm), and enables you to
  4825. compile E programs from the editor. Just assign this script
  4826. a function key in the editor with "Install Dos/Arexx command ..."
  4827. (check your CED-manual if you're not sure how to do this).
  4828. Now write your programs, and press Fx if you wish to compile.
  4829. Your source will be saved if necessary, the compiler will be
  4830. invoked on a separate console window, and the program is run
  4831. on the same console. When your program is done, you may press
  4832. <return> to return to the editor (CED-screen to back and front is
  4833. automatically done by the script). If an error occurred during
  4834. compilation, the script will let CED jump to the line of
  4835. error after you pressed <return>
  4836.  
  4837. Note: in the script there is a path name as to were the compiler
  4838. can be found. You probably need to change this. Also, the script
  4839. copies EC to ram: for systems with a slower SYS: device, you may
  4840. want to disable this if you have a fast HD.
  4841.  
  4842.  
  4843. 17F. bin/o2m
  4844. ------------
  4845. If you have large pieces of assembly source that you'd like to use it
  4846. would be tedious at best to convert them all by hand to E's inline
  4847. assembly. o2m allows you to simply have your favourite macro-assembler
  4848. assemble it all to a .o file, and o2, then will turn this .o file into
  4849. a .m file for use with E. If you have a file bla.o:
  4850.  
  4851. 1> o2m bla
  4852.  
  4853. will produce bla.m. However, the .o file will have to obey certain rules.
  4854. It should consist of just one code-hunk with external definitions (XDEFs)
  4855. for each symbol you wish to reference from E, and no XREFs. typically,
  4856.  
  4857. your source would look like:
  4858.  
  4859.     XDEF add__ii
  4860.  
  4861. add__ii:
  4862.     move.l    4(a7),d0
  4863.     add.l    8(a7),d0
  4864.     rts
  4865.     
  4866. this example shows a bit of assembly code that gets two arguments (hence
  4867. the two "i" for integer). arguments can be found on the stack, where
  4868. 4(a7) is the last arg, 8(a7) the one before that etc.
  4869.  
  4870. Showhunk shows you this:
  4871.  
  4872.         hunk_unit: 
  4873. HUNK -1 hunk_name:  
  4874.         hunk_code: 12 bytes
  4875.         hunk_ext
  4876.           add__ii = $0
  4877.  
  4878. this type of .o file is the easily transformed to .m by o2m:
  4879.  
  4880. /* this module contains 12 bytes of code! */
  4881.  
  4882. PROC add(a,b)
  4883.  
  4884.  
  4885. there are a couple of things to note:
  4886. - if your asm code uses D3-D7/A4/A5 you should probably save it.
  4887. - if a label doesn't have the "__" with an "i" for each function,
  4888.   it becomes a parameterless function. Don't worry if the label
  4889.   actually references data, you can simply get the address of this
  4890.   'proc' with {}, and use it as a ptr to your data.
  4891.  
  4892. theoretically, o2m could be used to link C code to E programs,
  4893. however in practise this is often not feasable. If your C compiler
  4894. allows you to 'tune' the resulting .o files a bit, this might work.
  4895.  
  4896. some problems are:
  4897. - reference of C functions, for example _printf()
  4898. - reference of globals vars created by C startup code. C code
  4899.   may reference "DOSBase" as an XREF, whereas E's startup code makes 
  4900.   this value available somewhere on the stack
  4901. - call/register conventions.
  4902.  
  4903. I did manage to link a small C function to E that only does some
  4904. computation, and call it succesfully (this was done using MaxonC++,
  4905. whose linker uses the __ii convention for parameters also).
  4906.  
  4907.  
  4908. 17G. bin/EYacc
  4909. --------------
  4910. This is a port of the famous Yacc utility for unix, which now
  4911. produces E code instead of C code. It is only a first version,
  4912. so don't expect too much from it. If you have no clue what Yacc
  4913. does, read a text on it, since I'm not going to explain that in full
  4914. here.
  4915.  
  4916. Basically you can write .y sources as normal, only where actions
  4917. used to be written in C, now you can write E. See the Src/Yacc/bcalc.y
  4918. example.
  4919.  
  4920. 1> eyacc bcalc.y
  4921.  
  4922. produces a file 'yyparse.e'
  4923.  
  4924. 1> ec yyparse
  4925.  
  4926. will get you a module, which contains only the function yyparse().
  4927. The rest of 'how to interface with Yacc' should be analoguous to C.
  4928.  
  4929. [note: I'm halfway a translation of Lex to E-Lex, but not done yet.]
  4930.  
  4931. further info.
  4932. E-Yacc is a modification of Berkeley Yacc 1.8, originally by
  4933. corbett@berkeley.edu. The inclusion of this modified version
  4934. in the E distribution is totally legal, as the author states in
  4935. the original BYacc1.8 README:
  4936.  
  4937. "   Berkeley Yacc is in the public domain.  The data structures and algorithms
  4938. used in Berkeley Yacc are all either taken from documents available to the
  4939. general public or are inventions of the author.  Anyone may freely distribute
  4940. source or binary forms of Berkeley Yacc whether unchanged or modified.
  4941. Distributers may charge whatever fees they can obtain for Berkeley Yacc.
  4942. Programs generated by Berkeley Yacc may be distributed freely. "
  4943.  
  4944.  
  4945. 17H. bin/SrcGen
  4946. ---------------
  4947. [note: this utility hasn't been updated to work better with
  4948.  the E module system, it still outputs just the raw source
  4949.  (which is then easily incorporated in any module). If there
  4950.  is much demand I will upgrade this utility. If you want to
  4951.  add a nice GUI to your program, also take a look at
  4952.  modules/tools/EasyGUI.m, or newer toolkits suchs as the upcoming
  4953.  BGUI from Jan van den Baard, the author of GadToolsBox.]
  4954.  
  4955. SrcGen GadToolBox source generator for E: beta version
  4956.  
  4957. You'll be needing GadToolBox v2.0 or higher, and have the
  4958. gadtoolsbox.library that comes with it in your LIBS:. Now, with GTB,
  4959. make some simple example (just a window with a few gadgets/menus etc.),
  4960. save it as "bla" (filename will be "bla.gui"), and type:
  4961.  
  4962. 1> SrcGen bla
  4963. 1> EC bla
  4964. 1> bla
  4965.  
  4966. "bla.e" contains the routines for opening your interface, as well
  4967. as some routines to handle idcmpmessages, errors etc., and a dummy
  4968. "main" that just waits for one selection. here you can put in
  4969. your own code. see the commandline template how to stop SrcGen from
  4970. generating these routines.
  4971.  
  4972. That's all there's to it. If you have problems, just check the
  4973. source that has been generated.
  4974.  
  4975.  
  4976. 17I. bin/EBuild
  4977. ---------------
  4978. EBuild is a "Make" clone, and it functions likewise. Build is a tool
  4979. that helps you in recompiling necessary parts of a large application
  4980. after modification. You write a file ".build" in the directory
  4981. that contains the sources of your project. The file contains info
  4982. about which sources depend on which, and what actions need to be
  4983. performed if a module or exe needs to be rebuild. Build checks the
  4984. dates of the files to see if a source has been modified after the
  4985. last compilation, and if the source uses modules that also have
  4986. been modified, it will compile these first.
  4987.  
  4988. the syntax equals that of unix-make. in general, "#" precedes
  4989. lines with comments, and:
  4990.  
  4991. target: dep1 dep2 ...
  4992.   action1
  4993.   action2
  4994.   ...
  4995.  
  4996. target is the resulting file we're talking about, in most cases an
  4997. exe or module, but may be anything. Following the ":" you write all
  4998. files that it depends upon, most notably its source, and other modules.
  4999. The actions on the following lines are normal AmigaDos commands, and
  5000. need to be preceded by atleast one space or tab to distinquish them
  5001. from targets.
  5002.  
  5003. bla: bla.e defs.m
  5004.      ec bla quiet
  5005.  
  5006. this simple example will only recompile 'bla.e' if it was modified,
  5007. or if the defs.m which it uses was modified.
  5008.  
  5009. If you type 'build' with no args, build will ensure the
  5010. first target to be up to date.
  5011.  
  5012. TARGET,FROM/K,FORCE/S: 
  5013.  
  5014. if you supply a TARGET, this way build will start with another target.
  5015. FROM allows you to use another file than ".build", and FORCE will
  5016. rebuild everything, regardless of wether it was really necessary.
  5017.  
  5018. Example:
  5019.  
  5020.  
  5021. # test build file
  5022.  
  5023. all:    bla burp
  5024.  
  5025. defs.m:    defs.e
  5026.     ec defs quiet
  5027.  
  5028. bla:    bla.e defs.m
  5029.     ec bla quiet
  5030.  
  5031. burp:    burp.e
  5032.     ec burp quiet
  5033.  
  5034. clean:
  5035.     delete  defs.m bla burp
  5036.  
  5037.  
  5038. this build file is about two programs, bla and burp, of which bla
  5039. also depends on a module defs.m. An extra fake target 'clean' has
  5040. been added so you can type 'build clean' to delete all results.
  5041.  
  5042. Other dependencies and actions are easily added. for example,
  5043. if your project uses a parser generated by E-Yacc:
  5044.  
  5045. yyparse.m: parser.y
  5046.            eyacc parser.y
  5047.            ec yyparse quiet
  5048.  
  5049. Or incorporates macro-assembly code as often used tool module:
  5050.  
  5051. blerk.m: blerk.s
  5052.          a68k blerk.s
  5053.          o2m blerk
  5054.          copy blerk.m emodules:tools
  5055.          flushcache tools/blerk
  5056.  
  5057. Once you get to know build, you'll discover you can use it for
  5058. more purposes than just this. see it as an intelligent script tool.
  5059.  
  5060. If you want to find out the details of what build can do, read the
  5061. documentation of some unix-make, as build should be somewhat compatible
  5062. with this. what it doesn't do for now, is:
  5063.  
  5064. - rule out cyclic dependancies
  5065. - allow "\" at the end of a line for longer rules
  5066. - constant definitions
  5067.  
  5068.  
  5069.  
  5070. 18A. The E grammar
  5071. ------------------
  5072.  
  5073.  
  5074. This is a grammar of E for those who are interested. Don't expect
  5075. it to be up to date or otherwise complete/correct though (it should
  5076. be quite ok for E upto v2.1b atleast).
  5077.  
  5078. lex syntax: regular expressions
  5079. parse syntax: own ASF/SDF adaption;
  5080.  
  5081.     name    = grammar ident
  5082.     "name"    = constant
  5083.     ()    = grouping
  5084.     |    = or
  5085.     e*    = 0 or more of e
  5086.     e+    = 1 or more of e
  5087.     {e s}*    = 0 or more of e separated by s
  5088.     {e s}+    = 1 or more of e separated by s
  5089.     [e]    = e is optional
  5090.     ; e    = e is comment :-)
  5091.  
  5092.  
  5093.  
  5094. LEX
  5095. ---
  5096.  
  5097.  
  5098.  
  5099. whitespace    = [ \t]     ; also \n if last token is [,+-*/] or similar
  5100.           anything between "/*" and "*/"
  5101.           from "->" to \n
  5102. eol        = [;\n]
  5103.  
  5104. constant    = [A-Z] ( [A-Z] [A-Za-z0-9_]* )?
  5105. builtin        = [A-Z] [a-z] [A-Za-z0-9_]*
  5106. ident,objident    = [a-z] [a-zA-Z0-9_]*
  5107.  
  5108. num        = [0-9]+    ; "-" is seperate token
  5109.                   $[0-9A-Fa-f]+
  5110.           %[01]+
  5111. fnum        = [0-9]*.[0-9]*
  5112.  
  5113. stringconst    = anything in ''
  5114. charconst    = anything in ""
  5115.  
  5116.  
  5117.  
  5118. PARSE
  5119. -----
  5120.  
  5121.  
  5122. program        = opts globalpart localpart
  5123.  
  5124. globalpart    = ( modulestat | defstat | objdecl | constdecl | raisedecl )*
  5125. localpart    = ( procdecl | constdecl )+
  5126.  
  5127. modulestat    = "MODULE" { conststring "," }+ eol
  5128. defstat        = "DEF" vardecllist eol
  5129. objdecl        = "OBJECT" ident [ "OF" ident ] eol
  5130.                      ( vardecllist eol )+
  5131.                   "ENDOBJECT" eol
  5132. constdecl    = "CONST" { ( constant "=" constexp ) "," }+ |
  5133.           "ENUM" { ( constant | constant "=" constexp ) "," }+ |
  5134.           "SET" { constant "," }+
  5135. procdecl    = [ "EXPORT" ] "PROC" ident "(" argdecllist ")"
  5136.                   [ "OF" ident ] [ "HANDLE" ]
  5137.                   ( ( "RETURN" | "IS" ) { exp "," }* |
  5138.                      eol defstat* stats 
  5139.                      [ "EXCEPT" eol stats ]
  5140.                      "ENDPROC" { exp "," }* eol )
  5141. raisedecl    = "RAISE" { ( constant "IF" builtin "()" compop num ) "," }+
  5142. opts        = ( "OPT" { setting "," }+ )*        ; machine dependant
  5143.  
  5144. vardecllist    = { vardecl "," }+
  5145. vardecl        = ident [ "=" num ]
  5146.                     [ ":" ( "LONG" | "REAL" | "PTR" "TO" ptrtype ) ] |
  5147.                   ident ":" objtype |
  5148.                   ident "[" num "]" ":"
  5149.                     ( "ARRAY" |
  5150.                       "ARRAY" "OF" ptrtype |
  5151.                       "STRING" |
  5152.                       "LIST" )
  5153. argdecllist    = { argdecl "," }+
  5154. argdecl        = ident [ "=" defaultarg ]
  5155.                     [ ":" ( "LONG" | "REAL" | "PTR" "TO" ptrtype ) ]
  5156. ptrtype        = objtype | simpletype
  5157. simpletype    = CHAR | INT | LONG
  5158. objtype        = ident
  5159.  
  5160. stats        = ( ( onelinestat | multlinestat ) eol )*
  5161. onelinestat    = exp |
  5162.           lval ":=" exp |
  5163.           { var "," }+ ":=" exp |
  5164.           "IF" exp "THEN" onelinestat "ELSE" onelinestat |
  5165.           "FOR" var ":=" exp "TO" exp [ "STEP" num ]
  5166.                      "DO" onelinestat |
  5167.           "WHILE" exp "DO" onelinestat |
  5168.           "RETURN" { exp "," }* |
  5169.           "JUMP" ident |
  5170.                   ( "INC" | "DEC" ) var |        ; nearly obsolete
  5171.           asm_mnemonic { operand "," }*    |    ; machine dependant
  5172.           "INCBIN" stringconst |        ; inline asm support
  5173.           simpletype { num "," }+ |
  5174.           "VOID" exp                ; obsolete
  5175. multlinestat    = "IF" exp eol stats
  5176.                      [ ( "ELSEIF" exp eol stats )* ] 
  5177.                      [ "ELSE" eol stats ]
  5178.                      "ENDIF" |
  5179.           "FOR" var ":=" exp "TO" exp [ "STEP" num ] eol
  5180.                      stats "ENDPROC" |
  5181.           "WHILE" exp eol stats "ENDWHILE" |
  5182.           "REPEAT" eol stats "UNTIL" exp |
  5183.           "SELECT" var eol
  5184.                      ( "CASE" exp eol stats )+
  5185.                      [ "DEFAULT" eol stats ]
  5186.                      "ENDSELECT" |
  5187.                   "LOOP" eol stats "ENDLOOP"
  5188.  
  5189. explist        = { exp "," }+
  5190. exp        = [ "-" ] { item binop }+ |
  5191.           exp "BUT" exp
  5192. item        = num | fnum | lval | stringconst | charconst |
  5193.           "SIZEOF" objident |
  5194.           "IF" exp "THEN" exp "ELSE" exp |
  5195.           "[" explist "]" [ ":" ptrtype ] |
  5196.           ( builtin | ident ) "(" explist ")" |
  5197.           var ":=" exp |
  5198.           "{" ident "}" |
  5199.           "`" exp |
  5200. binop        = mathop | compop | logop
  5201. mathop        = "+" | "-" | "*" | "/"
  5202. compop        = "=" | "<>" | ">" | "<" | ">=" | "<="
  5203. logop        = "AND" | "OR"
  5204. constexp    = [ "-" ] { num ( "+" | "-" | "*" | "/" ) }+
  5205. lval        = var ( "[" [ exp ] "]" | "." ident )* [ "++" | "--" ] |
  5206.           "^" var [ "++" | "--" ] |
  5207. var        = ident
  5208. defaultarg    = num
  5209.  
  5210.  
  5211.  
  5212. 18B. Tutorial
  5213. -------------
  5214.  
  5215.  
  5216. NOTE: the original E v2.1b tutorial has been removed, since it
  5217. was not a very useful tutorial, IMHO. Instead, Jason Hulance made
  5218. an extensive E tutorial that you'd definitly want to take a look at.
  5219.  
  5220.  
  5221.  
  5222. 18C. Mapping E to C/C++/Pascal/Ada/Lisp etc.
  5223. --------------------------------------------
  5224.  
  5225.  
  5226. [some new stuff has been added here]
  5227.  
  5228. In the first/second column I will match E against AnsiC/C++, the third
  5229. column is reserved for a third language. I will mainly use Pascal here,
  5230. but where a feature asks for it, I will use others (for example, LISP
  5231. with quoted expression, Ada with exceptions etc.
  5232.  
  5233. note well: take these tables with a grain of salt. I'll try to denote
  5234. syntactic equivalences, and semantic properties as well as possible,
  5235. but different languages still need their own evaluation.
  5236.  
  5237. usage of signs:
  5238.  
  5239. -    = feature not available in language in question.
  5240. ?    = author has no clue what this feature translates to.
  5241.       (or atleast he's not sure).
  5242. ...    = feature may be available, but no appropriate 1:1 translation
  5243.       possible to make it interesting.
  5244. x,y,z    = arbitrary identifiers
  5245. e,f,g    = arbitrary expressions
  5246. s,t,u    = arbitrary statements
  5247. i,j,k    = arbitrary integers
  5248. etc.
  5249.  
  5250.  
  5251. -----------------------------------------------------------------------
  5252. STRUCTURE/STATEMENTS
  5253.  
  5254. E            C/C++            Pascal
  5255. ----------------------- ----------------------- -----------------------
  5256. PROC x()        int x() {        FUNCTION x:INTEGER;
  5257. PROC x(y,z)        int x(y,z) {        FUNCTION x(y,z:INTEGER):INTEGER;
  5258. PROC x(y=1)        int x(y=1) {        -
  5259. ENDPROC            return 0; };        x:=0; END;
  5260. ENDPROC e        return e; };        x:=e; END;
  5261. ENDPROC e,f,g        -            -
  5262. RETURN e        return e;        ?
  5263.  
  5264. IF e            if(e) {            IF e THEN BEGIN
  5265. ELSEIF e        } else if(e) {        END ELSE IF e THEN BEGIN
  5266. ELSE            } else {        END ELSE BEGIN
  5267. ENDIF            };            END;
  5268. IF e THEN s        if(e) s;        IF e THEN s;
  5269. IF e THEN s ELSE t    if(e) s else t;        IF e THEN s ELSE t;
  5270.  
  5271. FOR x:=e TO f        - (1)            FOR x:=e TO f DO BEGIN
  5272. FOR x:=e TO f STEP i    -            - (2)
  5273. EXIT e            if(e) break;        -
  5274. ENDFOR            -            END;
  5275. FOR x:=e TO f DO s    -            FOR x:=e TO f DO s;
  5276.  
  5277. WHILE e            while(e) {        WHILE e DO BEGIN
  5278. EXIT e            if(e) break;        -
  5279. ENDWHILE        };            END;
  5280. WHILE e DO s        while(e) s;        WHILE e DO s;
  5281.  
  5282. s; WHILE e        for(s;e;u) {        s; WHILE e DO BEGIN
  5283.   t; u              t;              t; u
  5284. ENDWHILE        };            END;
  5285.  
  5286. REPEAT            do {            REPEAT
  5287. UNTIL e            } while(!e);        UNTIL e;
  5288.  
  5289. LOOP            for(;;) {        WHILE TRUE DO BEGIN (?)
  5290. ENDLOOP            };            END;
  5291.  
  5292. SELECT x        switch(x) {        CASE x OF
  5293. SELECT x OF y        switch(x) {        CASE x OF
  5294. CASE 1; s...        case 1: s...; break    1: BEGIN s... END
  5295. CASE a+1        -            -
  5296. CASE 1,2,3        case 1: case 2: case3:    1,2,3:
  5297. CASE "a".."z"        -            -
  5298. ENDSELECT        };            END
  5299.  
  5300. INC x            x++;            x:=x+1; (INC())
  5301. DEC x            x--;            x:=x-1; (DEC())
  5302. JUMP lab        goto lab;        GOTO lab;
  5303. x:=e            x=e;            x:=e;
  5304.  
  5305. /* */            /* */            { }
  5306. ->            //            -
  5307.  
  5308. (1) see WHILE; C has no FOR, "for" in C is another way of writing "while"
  5309. (2) only STEP -1 as DOWNTO
  5310.  
  5311.  
  5312. -----------------------------------------------------------------------
  5313. VALUES
  5314.  
  5315. E            C/C++            Pascal
  5316. ----------------------- ----------------------- -----------------------
  5317. 1            1            1
  5318. 1.0            1.0            1.0
  5319. $1            0x1            ?
  5320. %1            ?            ?
  5321. "a"            'a'            chr(97) (?)
  5322. 'blabla'        "blabla"        'blabla'
  5323. [1,2,3]            - (1)            -
  5324. [1,2,3]:INT        -            -
  5325.  
  5326. (1) in translating from E to C, you can often simulate them with:
  5327.  
  5328. myfunc([1,2,3])
  5329.  
  5330. becomes:
  5331.  
  5332. int dummy [] = {1,2,3};
  5333. myfunc(dummy);
  5334.  
  5335.  
  5336. -----------------------------------------------------------------------
  5337. OPERATORS
  5338.  
  5339. E            C/C++            Pascal
  5340. ----------------------- ----------------------- -----------------------
  5341. + - * /            + - * /            + - * DIV
  5342. = <> > < >= <=        == != > < >= <=        = <> > < >= <=
  5343. AND OR    (log)        && ||            and or
  5344. AND OR    (bit)        & |            ?
  5345. SIZEOF x        sizeof(x)        -
  5346. `e            -            - (1)
  5347. ^x    (4)        *x            ...
  5348. {x}            &x            ...
  5349. x++            x++            -
  5350. x--            --x            -
  5351. -x            -x            -x
  5352. IF e THEN f ELSE g    e ? f : g        -
  5353. x.y            x->y            x^.y
  5354. -            x.y            x.y
  5355. x.y.z            x->y->z            x^.y^.z
  5356. x:=e            x=e            -
  5357. e BUT f            (e,f)            -
  5358. x[]            x[0] *x (2)        x[0]
  5359. x[1]            x[1]            x[1]
  5360. x[1]    (3)        &x[1]            ?
  5361. x[1].y            x[1]->y            x[1]^.y
  5362. x[]++            *x++            -
  5363. x[1].y++        *(x+1)++        -
  5364. x::y.a            ((y *)x)->a        -
  5365. x.y::z.a        ((z *)x->y)->a        -
  5366.  
  5367. (1) see QUOTED EXPRESSIONS
  5368. (2) also for others, equivalences between *(x+e) and x[e] hold.
  5369. (3) if ARRAY OF <object>
  5370. (4) ONLY for giving by reference. otherwise: "[]"
  5371.  
  5372. -----------------------------------------------------------------------
  5373. CONSTANTS/TYPES
  5374.  
  5375. E            C/C++            Pascal
  5376. ----------------------- ----------------------- -----------------------
  5377. CONST X=1        #define X 1        CONST X=1;
  5378.             const int X=1;
  5379. ENUM X,Y,Z        #define X 0 (etc.)    TYPE x=(X,Y,Z);
  5380.             enum x{X,Y,Z};
  5381. SET X,Y,Z        -            TYPE x=SET OF (X,Y,Z);
  5382.  
  5383. DEF                        VAR
  5384. x            int x; (or: long x;)    x:INTEGER;
  5385. x:LONG            int x;            x:INTEGER;
  5386. x:PTR TO y        struct y* x;        x:^y;
  5387. x:y            struct y x;        x:y;
  5388. x[10]:ARRAY OF y    struct y x[10];        x:ARRAY [0..9] OF y;
  5389. x[10]:STRING        - (1)            x:STRING[10]; (2)
  5390. x[10]:LIST        - (1)            - (1)
  5391.  
  5392. x:REG            register int x;
  5393.  
  5394. OBJECT x        struct x {    (3)    TYPE x = RECORD
  5395.   y:CHAR,z:INT          char y; short z;      y:CHAR; z:INTEGER;
  5396. ENDOBJECT        };            END;
  5397.  
  5398. (1) when translating from E to C, simulate with an array of char/int resp.,
  5399.     and do your own range-checking etc.
  5400. (2) no Wirth Pascal, but available in all popular dialects.
  5401. (3) or public class.
  5402.  
  5403.  
  5404. -----------------------------------------------------------------------
  5405. QUOTED EXPRESSIONS
  5406.  
  5407. E            LISP                MIRANDA
  5408. ----------------------- --------------------------- -------------------
  5409. `e            (QUOTE e)  'e            (3)
  5410.             (LAMBDA () e)     (1)
  5411. `x+y            '(+ x y)
  5412. Eval(`e)        (EVAL `e)
  5413. ForAll(v,l,`e)        - (2)
  5414. MapList(v,l,l,`e)    (MAPCAR (LAMBDA (V) E) L)   map (\v->e) l
  5415.  
  5416. example:
  5417.  
  5418. E:        MapList({x},[1,2,3,4],a,`x*x)
  5419. MIRANDA:    map (\x->x*x) [1,2,3,4]
  5420. LISP:        (MAPCAR (LAMBDA (X) (* X X) `(1 2 3 4))
  5421.  
  5422. (1) really QUOTE, but sometimes used where in LISP LAMBDA would be
  5423.     used, like in MapList()
  5424. (2) not even in ProLog, see other logical languages.
  5425. (3) lazyness would be used instead here
  5426.  
  5427. -----------------------------------------------------------------------
  5428. UNIFICATION AND LISP CELLS
  5429.  
  5430. E            LISP            PROLOG
  5431. ----------------------- ----------------------- -----------------------
  5432. <1|2>            (1 . 2)            [1|2]
  5433. <1,2,3>            (1 2 3)            [1,2,3]
  5434. <1,2|3>            (1 2 . 3)        [1,2|3]
  5435.  
  5436. E            HASKELL            PROLOG
  5437. ----------------------- ----------------------- -----------------------
  5438. e <=> <x|y>        (x:y) = e        e = [X|Y]
  5439. e <=> <1,2,x>        [1,2,x] = e        e = [1,2,X]
  5440. e <=> [1,x]        -            -
  5441.  
  5442.  
  5443. -----------------------------------------------------------------------
  5444. EXCEPTIONS
  5445.  
  5446. E            C++            ADA
  5447. ----------------------- ----------------------- -----------------------
  5448. PROC x() HANDLE        int x() { try {        function x is begin
  5449. EXCEPT            } catch (exc) {   (1)    exception
  5450. EXCEPT DO        -            -
  5451. ENDPROC            }};            end x;
  5452.  
  5453. Raise(e)        throw e;        raise e;
  5454. Throw(e,f)        ?            -
  5455. ReThrow()        throw e;        raise e;
  5456. RAISE "MEM" IF New()=0    -            - (2)
  5457.  
  5458.  
  5459. (1) catch handles only one specific exception, it's quite different
  5460.     from general exception handlers as used in E.
  5461. (2) the runtime system does raise some exceptions, but I'm not sure
  5462.     wether automatically raised exceptions can be _defined_ in Ada.
  5463.  
  5464.  
  5465. -----------------------------------------------------------------------
  5466. OBJECT ORIENTED PROGRAMMING
  5467.  
  5468. E                C++
  5469. ------------------------------- -----------------------
  5470. OBJECT x            class x {
  5471. OBJECT x OF y            class x : y {
  5472. self.i                this->i
  5473. PROC a OF x IS self.i        virtual int x::a() { return i; }
  5474. -                int x::a() { return i; }
  5475. PROC a OF x IS EMPTY        virtual int x::a() =0
  5476. PUBLIC                public:
  5477. a.method(1)            a->method(1)
  5478.  
  5479. [see also next part under NEW]
  5480.  
  5481. -----------------------------------------------------------------------
  5482. BUILTIN FUNCTIONS AND MEMORY ALLOCATION
  5483. (only a few are presented here, as an example)
  5484.  
  5485. E            C/C++            Pascal
  5486. ----------------------- ----------------------- -----------------------
  5487. WriteF(fs,...)        printf(fs,...);        WriteLn(a,b,...);
  5488.             cout << a << b ... ;
  5489.  
  5490. ReadStr(f,s)        scanf(fs,...)        ReadLn(s)
  5491. Val(s)                        Val()
  5492.             cin >> s;
  5493.  
  5494. StrCopy(s,s,n)    (1)    strcpy(s,s)        s:=s; (2)
  5495.  
  5496. Mod(e,e)        e%e            e MOD e
  5497. Shl(e,n)        e<<n            Shl()
  5498. Long(e)            -            -
  5499.  
  5500.  
  5501. p:=New(e)        p=malloc(e);        New(p);
  5502. NEW p            p=new type;
  5503. NEW p.constr()        p=new constr()        -
  5504. NEW [e,f,g]        -            -
  5505. Dispose(p)        free(p);        Dispose(p);
  5506. END p            delete p;
  5507.  
  5508.  
  5509. (1) when translating from C, make sure you turn the arrays of char into
  5510.     proper STRINGs.
  5511. (2) dunno what function is needed in the pointer case.
  5512.  
  5513.  
  5514. -------------------------------EOF--------------------------------------
  5515.