mirror of
https://github.com/nim-lang/Nim.git
synced 2025-12-31 02:12:11 +00:00
Merge pull request #245 from gradha/pr_improve_documentation
Adds to the tutorial some info about exception tracking.
This commit is contained in:
91
doc/tut2.txt
91
doc/tut2.txt
@@ -357,10 +357,14 @@ Exceptions
|
||||
==========
|
||||
|
||||
In Nimrod `exceptions`:idx: are objects. By convention, exception types are
|
||||
prefixed with an 'E', not 'T'. The ``system`` module defines an exception
|
||||
hierarchy that you might want to stick to.
|
||||
prefixed with an 'E', not 'T'. The `system <system.html>`_ module defines an
|
||||
exception hierarchy that you might want to stick to. Exceptions derive from
|
||||
E_Base, which provides the common interface.
|
||||
|
||||
Exceptions should be allocated on the heap because their lifetime is unknown.
|
||||
Exceptions have to be allocated on the heap because their lifetime is unknown.
|
||||
The compiler will prevent you from raising an exception created on the stack.
|
||||
All raised exceptions should at least specify the reason for being raised in
|
||||
the ``msg`` field.
|
||||
|
||||
A convention is that exceptions should be raised in *exceptional* cases:
|
||||
For example, if a file cannot be opened, this should not raise an
|
||||
@@ -379,7 +383,11 @@ Raising an exception is done with the ``raise`` statement:
|
||||
raise e
|
||||
|
||||
If the ``raise`` keyword is not followed by an expression, the last exception
|
||||
is *re-raised*.
|
||||
is *re-raised*. For the purpose of avoiding repeating this common code pattern,
|
||||
the template ``newException`` in the ``system`` module can be used:
|
||||
|
||||
.. code-block:: nimrod
|
||||
raise newException(EOS, "the request to the OS failed")
|
||||
|
||||
|
||||
Try statement
|
||||
@@ -426,6 +434,81 @@ the rest of the procedure - that is not within a ``finally`` clause -
|
||||
is not executed (if an exception occurs).
|
||||
|
||||
|
||||
Exception hierarchy
|
||||
-------------------
|
||||
|
||||
If you want to create your own exceptions you can inherit from E_Base, but you
|
||||
can also inherit from one of the existing exceptions if they fit your purpose.
|
||||
The exception tree is:
|
||||
|
||||
* E_Base
|
||||
* EAsynch
|
||||
* EControlC
|
||||
* ESynch
|
||||
* ESystem
|
||||
* EIO
|
||||
* EOS
|
||||
* EInvalidLibrary
|
||||
* EResourceExhausted
|
||||
* EOutOfMemory
|
||||
* EStackOverflow
|
||||
* EArithmetic
|
||||
* EDivByZero
|
||||
* EOverflow
|
||||
* EAccessViolation
|
||||
* EAssertionFailed
|
||||
* EInvalidValue
|
||||
* EInvalidKey
|
||||
* EInvalidIndex
|
||||
* EInvalidField
|
||||
* EOutOfRange
|
||||
* ENoExceptionToReraise
|
||||
* EInvalidObjectAssignment
|
||||
* EInvalidObjectConversion
|
||||
* EFloatingPoint
|
||||
* EFloatInvalidOp
|
||||
* EFloatDivByZero
|
||||
* EFloatOverflow
|
||||
* EFloatUnderflow
|
||||
* EFloatInexact
|
||||
* EDeadThread
|
||||
|
||||
See the `system <system.html>`_ module for a description of each exception.
|
||||
|
||||
|
||||
Annotating procs with raised exceptions
|
||||
---------------------------------------
|
||||
|
||||
Through the use of the optional ``{.raises.}`` pragma you can specify that a
|
||||
proc is meant to raise a specific set of exceptions, or none at all. If the
|
||||
``{.raises.}`` pragma is used, the compiler will verify that this is true. For
|
||||
instance, if you specify that a proc raises ``EIO``, and at some point it (or
|
||||
one of the procs it calls) starts raising a new exception the compiler will
|
||||
prevent that proc from compiling. Usage example:
|
||||
|
||||
.. code-block:: nimrod
|
||||
proc complexProc() {.raises: [EIO, EArithmetic].} =
|
||||
...
|
||||
|
||||
proc simpleProc() {.raises: [].} =
|
||||
...
|
||||
|
||||
Once you have code like this in place, if the list of raised exception changes
|
||||
the compiler will stop with an error specifying the line of the proc which
|
||||
stopped validating the pragma and the raised exception not being caught, along
|
||||
with the file and line where the uncaught exception is being raised, which may
|
||||
help you locate the offending code which has changed.
|
||||
|
||||
If you want to add the ``{.raises.}`` pragma to existing code, the compiler can
|
||||
also help you. You can add the ``{.effect.}`` pragma statement to your proc and
|
||||
the compiler will output all inferred effects up to that point (exception
|
||||
tracking is part of Nimrod's effect system). Another more roundabout way to
|
||||
find out the list of exceptions raised by a proc is to use the Nimrod ``doc2``
|
||||
command which generates documentation for a whole module and decorates all
|
||||
procs with the list of raised exceptions. You can read more about Nimrod's
|
||||
`effect system and related pragmas in the manual <manual.html#effect-system>`_.
|
||||
|
||||
|
||||
Generics
|
||||
========
|
||||
|
||||
|
||||
Reference in New Issue
Block a user