Replace callbacks with tasks internally

The callback system inside the interpreter required manually handling
errors at every asynchronous connection point. It was also prone to
errors when callbacks weren't called or called more than once. All of
the callbacks in the internals of the interpreter have been replaced
with 'tasks', modelled on the 'thenable' concept from JavaScript
promises. Tasks automatically pipe errors, and ensure that results can
only be processed once, while preserving the possibility of synchronous
behaviour. The external interface of the interpreter and the
asynchronous methods still use Node-style callbacks.
Factor out method lookup

A special case of method application used a string to look up a method
in an existing object, and would always assume that the method existed
in the object. Method lookup is now factored out into a method in the
runtime instead of being in the interpreter. This change removes this
potentially fallacious assumption while making method lookup available
to the runtime implementation.

Several utility functions that are now used in both the interpreter and
the runtime have also been moved into a module where they can be
accessed by both.
Allow override of variables in super objects

Variables are now treated the same as methods when attached to objects,
and can be requested through super when they are overridden. Undefined
variables now appear as regular variables, and some inconsistent use of
names and the prebuilt Unknown variable have been tidied up.