Showing posts with label exceptions. Show all posts
Showing posts with label exceptions. Show all posts

2013-04-29

security through instruction restrictions:

3.19: adda/exceptions/security through instruction restrictions:
. my style of exceptions has been
having the raiser call the caller's handler;
but, if the caller's code can be corrupted,
then the exception raiser could be exploited .
. it's fun to think about a perfect language,
one that's not corruptable;
but it's safer to have layers of security,
and not depend on a perfect language system .
. say the exception raiser is in ROM
(as it is a library routine)
but the exception handler has a jump instruction
that bypasses a safety guard;
what could save us is a VM that knows when it is
inside an exception handler,
and never executes a jump in such situations .

2013-03-09

exceptions ok unless requirements preclude

1.30: adda/cstr/exceptions/ok unless requirements preclude them:
. I thought Parasail's author explained somewhere
how exceptions really messed up multi-threads;
review my blog of that ...
(parasail-is-big-win-for-reliable).
. I decided a thread hang was no big deal;
in critical applications
exceptions are absolutely useless;
but if our point is to encourage programming
we should cater to all styles of thinking .
. we just need to protect the coder's user too:

2012-11-17

rationales for go.lang's surprises

8.22: news.adda/go/assertions are no way to panic:
Why does Go not have assertions?
[ assertions allow you to say
crash if this condition doesn't hold true
because something is wrong
and the program will need debugging .]
. assertions are undeniably convenient
to avoid thinking about proper
error handling and reporting;
but, servers should not crash from non-fatal errors;
and, errors should be direct and to the point,
saving the programmer from interpreting a
large crash trace .
Precise errors are particularly important
when the programmer seeing the errors
is not familiar with the code.
no exceptions? well, panic is just as useful:
. func panic(interface{})
func recover() interface{} .
. these built-in functions assist in reporting and handling
run-time panics and program-defined error conditions.
. When a function F calls panic,
normal execution of F stops immediately.
Any functions whose execution was
deferred by the invocation of F
are run in the usual way,
and then F returns to its caller.
To the caller,
F then behaves like a call to panic,
terminating its own execution
and running deferred functions.
This continues until all functions in the goroutine
have ceased execution, in reverse order.
At that point, the program is terminated
and the error condition is reported,
including the value of the argument to panic.
This termination sequence is called panicking.
panic(42); panic("unreachable");
panic(Error("cannot parse")).
. The recover function allows a program to
manage behavior of a panicking goroutine.
Executing a recover call inside a deferred function
stops the panicking sequence by
restoring normal execution,
and retrieves the error value passed to the call of panic.
If recover is called outside the deferred function
it will not stop a panicking sequence.
In this case, or when the goroutine is not panicking,
recover returns nil.

2012-08-26

dialogging exceptions

7.28: adda/cstr/dialogging exceptions/
syntax and fleshing out semantics:

. in adda, dialogging exceptions are
the kind of exceptions which are not call-killing:
they simply give the caller a chance to
fix things in the event of a missing resource:
eg, if a service finds a parameter missing
such as when a file is found to be unreachable,
it will give the caller's file-missing handler
a chance to assign a new file url to an address .
[7.29:
. dialogging exceptions are basically like
implicit parameters that accept a procedure for
what to do in the case of an exceptional situation;
ie, in the usual exception,
the service is quitting and that kills
the whole block that called that service;
so control jumps to the block's exception handlers;
whereas, in the case of dialogging exceptions,
the service is not quitting;
it merely calls an exception handler .]

. for dialogging exceptions,
the handler is expected to return a resource;
so we need syntax for an exception's
returning a value;
it's like a signal but you need a
pointer or inout param because
it's not just reading but writing to the param .
. what if the handler can't help?
if the param is a pointer
it can return nil to indicate failure
indicating the handler is of no help,
so the service then knows to
clean up and throw a returning exception
or give some other indication of failure .
[8.8:
. it's just like a dialog is to the user;
and in that situation,
the user can either find the resourse
and ok the dialog, or cancel it .
. for our example, the service declares:
FileNotFound( f/.filename ).dialog;
-- notice the arg is a pointer type;
and then the handler responds like this:
# a return would be ( f/`= $the/find.txt; );
-- the "(/) is dereferencing the pointer;
and, the target is assigned a literal filename .
# a cancel would be ( f`= none )
-- the pointer itself is assigned no address .
ipc:
. how are we dealing with
pointers that are sent across processes
(ie, how is an arbitrary pointer being thread safe?);
well, in the case of exceptions there are no surprises;
because, it's by invitation only:
the exception raiser is providing an address
for the caller to put a patch into .

8.9: ok,cancel as dialog-local keywords:
. another idea is that the handler's parameter
needs to be an out-mode not a pointer;
and, to handle the dialog
it assigns to the parameter and calls ok;
if the handler has nothing to return,
then it calls cancel to
allow for the service to clean up,
and then it can either propagate an exception
or make a change in strategy,
and then exit from the enclosing block,
or enter some tagged block; eg,
( --. begin a block containing a dialog handler .
...
[service that needs a file](f)
-- call the service that may dialog later .
;
on FileNotFound( out f.filename ).dialog:
( f`= [find a new file];
[file was found] ? ok
else: ( cancel; raise MissingResource )
)-FileNotFound
) --end of block with a dialog handler .]

2011-12-31

exceptions - events declared in the interface

adda/type/exceptions/events declared in the interface:
. the singleton pattern in the cocoa text has an example
where some device mgt needs to know when the app is closing
(ie, the app class provides a notification service,
and it needs to be registered with this service).
. generally,
if there is an event that type mgt needs,
declaring it in its interface should register it
to receive notifcations of any such events .
. notifications are interrupting the control flow
but unlike during ada exceptions,
the flow can return back to its routine .

exceptions - when to use error logging instead

adda/cstr/exceptions/when to use error logging instead:
. if the misuse of an interface will be caught during compilation
then a logged warning is appropriate;
otherwise, the bug catch will be depending on
how much testing the client coder does,
so if the bug gets to the user,
there should be an exception to get some runtime backup;
ie, the code will be responding to exceptions with
certain fixes or apologies;
conversely, if the coder isn't catching exceptions
then that is some half-baked, dangerous code,
and the user should be made aware it
so then the denial of service implied by an uncaught exception
is warranted .

2010-11-12

a doctor with good bed-side manners

11.6: adde/a doctor with good bed-side manners:

. a recent discussion about hypervisors
was discussing sophisticated ways to handle
extreme but transient mem'space shortages .
when multitasking several app's,
. the main approach should be
good bed-side manners:

. a study of why doctors get sued discovered
that, of the doctors who were sued the least,
what they had in common was
having good bed-side manners
(I would imagine that this would include
being honest with self and patient
with what they can expect,
and what their other options are).
. for a computer OS, that means
when a memory shortage comes up,
the OS is:
# making time to dialog with users:
(explaining why this app is bogged down
by the extent of its workload,
not getting the mem or cpu it needs,
what library components it's using
-- details that can be provided
only when the system is managed:
ie, the algorithm is compiled in a way
that keeps the os in charge,
and in the know).

# always keeping up with all user input:
(ie, the gui is on the highest priority thread;
the ability to take and display user input
is never frozen, and the input is always backed
by the os itself, a buggy app can't lose it .)
--
. this kind of control can get expensive,
and combining it with high-performance app's
might require networking 2 boxes or cores:
one for the user`interface,
and the other for app's to stay on task;
[11.9: but,
if 2 boxes are not available,
adda's translation should be providing
true multitasking by embedding into app's
frequent calls to the gui coroutine,
which then gives the os a chance to
stay in touch with the user .]

exception mgt

11.9: adda/exception mgt/intro:
. we expect some errors;
because, we'd like to
use some software before having to
formally verify its correctness,
so, we compensate
by finding ways to limit damage:

# isolation:
. modules should never crash other modules:
we can verify a microvisor or microkernel,
and it enforces the firewalls between processes .
. addx should be such a microkernel design;
[11.12: just as the app doesn't have
direct access to the user (it's the mvc`model
while adde is the view&controller )
it also has no direct access to the machine:
all c-level activity is handled by addx|addm .]

# regularly yielding to the gui coroutine:
. a critical priority of addx
is never letting the gui be unresponsive;
this is done by having adda embedding calls to addx
at every place in a subrogram that could
mean more than a milisec of cpu time:
# inside every function call,
# inside every loop .
. this is cooperative multi-tasking with
system-enforced coroutine yielding
for paravirtualizing true multi-tasking .

# regular reporting to supervisor:
. getting a regular progress report
will limit waiting on the down employee .
. employees can be waiting on
down service providers;
loops can be waiting on a terminal condition
that never arrives;
as when there's unexpected input;
mutual recursions (eg, f->g->h->f)
are another form of looping;
deadlocks can cause indefinite waiting,
but those can be avoided by
proper use of concurrency,
and by not locking resources
(using queues instead).
. a subprogram can be waiting because of
a failure to establish dialog with the user
(eg, if the system allows a window to be
always on top,
then dialog windows may be hidden from view).
. all threads are periodically tested for
whether they're waiting for a job offer,
for a {service, resource},
or are performing a service;
in which case,
addx measures how long ago the thread
produced its latest progress report .
. the progress reports read like a narrative
that a human would appreciate;
to make these reports quick,
msg's are encoded, so that each msg
is represented by some value in a byte (0...255)
(or a 16-bit integer if this subprogram had
more than 256 msg's).

# blackbox recorder:
. it tells us what was going on
just before a crash .
. it saves the progress reports,
and the recent call chain .

# a debug mode:
. when users' tools are not working well,
some users may like to see what's wrong
by using developers' visualization tools;
eg,
a freezing problem can be illustrated
as a looping call chain:
. the tool collects all the recent calls
(saved by the blackbox recorder)
then tries to find a recursion,
and shows the list of calls that are repeated .

11.8: sci.adda/exception mgt/reporting#loop count approximations:
[11.11: obs:
. it would be better to use progress reporting .]
. if adda can't statically figure out
when a loop won't terminate,
it should remind coders to give
approximate loop counts;
then the run-time can use that how?
sci:
. before the loop entry,
adda sets the counter, and a limit,
then has the scheduler check the limit .
. scheduler doesn't have to check all the time;
but if 2sec's go by,
nearly all loops are done by then,
if there is no limit given,
it starts giving it more cpu time if it can,
so the real time is compressed,
if another sec goes by
and there's other jobs to do,
then it starts getting starved ?
it could be doing a huge job!

2010-07-27

exceptions of Golang and Vala

7.17: news.adda/google'golang/design/exceptions:
. coupling exceptions to a
control structure,
as in the try-catch-finally idiom,
results in convoluted code.
. a routine that signals an exception
will then run a recovery routine
as it is closing for the return
-- sufficient to handle catastrophe
but requires no extra control structures
and, when used well,
can result in clean error-handling code.
7.25: news.adda/exceptions/Vala:

. vala has checked exceptions, not class-based, no wrapping
[. I changed the lexicon to match Ada's,
and much of the syntax to match adda's:]

. error domain with multiple error codes:
MyError.exception: { FOO, BAR }

. must be declared in method signature,
part of the contract:
method().proc raises MyError:
( raise FOO (message: "not enough foo") );

. must be handled or propagated:
[this is a declare block
(having an ex.label (exception)
defines a try-catch block)]

.(
method ();
ex:
e.MyError:
stderr(e`message);
)
. Although the compiler emits
warnings for ignored errors
it does not abort the compilation process.
This allows prototyping without proper error handling
and will hopefully prevent
forgotten empty catch blocks.

2010-06-30

adda exceptions performance

6.27: web.adda/exceptions/performance:
. I'm wondering how c++ exceptions
were inherently slowing c programs:
the addx vision of exceptions
is that there is always a scheduler
pre-empting functions for multitasking;
and, this scheduler is
gathering all the exceptions in a library;
... but it's not just routines
that handle exceptions:
every sub.block with a routine
can provide a unique handler for an exception;
and, these "(catch blocks) can be nested .
impl' idea#1:
. catch.blocks need to push their address
onto an exception stack;
then after an exception,
the scheduler can look on this exception stack
to the addresses of handlers .
. a program that has no handlers
would have an exception stack with
only one item:
the system's set of handlers .

web: Exceptions performance penalty:
In C++ Programming Language 3rd edition section 14.8
Stroustrup writes that it's possible to
implement exception handling
in such a way that there is
no run time overhead
when no exception is thrown
-- but it's not easy .
There is generally some overhead
as we have to keep track of the local objects
whose constructors have run,
so when exception is thrown
their destructors are called.
see Scott Meyer's "More effective C++" .

. g++ creates exception tables.
From the value of program counter
you can know which function/scope you're in.
For each scope you then know
which destructors have to be called
and using the stack address
you delete the apropriate objects.

We suppose that you can get
{ __builtin_return_address (LEVEL)
, __builtin_frame_address (LEVEL)
} for the ESP and EPC
of the caller of level LEVEL.

2010-01-30

adda`exceptions

1.8: adda/exceptions

[1.9: review of exceptions:
. there are 2 types:
# dialog-acceptions
are accepting a callback to resume,
(similar to the mac dialog) .
# failure-exceptions
are like the ada'exception,
which is simply canceling the job,
and asking the caller what it wanted to do
in the event a call had failed .
. failure-exceptions are part of the contract
between client(caller) and service(subroutine) :
the subroutine's list of exceptions
are telling the caller that if the call fails
then the reason for the failure will be given;
eg:
f`exception?
( [file not found]: handler#1
, [user unresponsive]: handler#2
) .
. if subprogram f didn't declare any exceptions?
or if you were not concerned with
the reason for the failure?
then you could simply use f's name
as an exception case:
eg,
exception?
( f: handler#1 .
, others: ... )
.
there are 2 ways for declaring exceptions:
. the ada way has symbols declared to be
an exception.type,
eg, (e.exception; raise e);
and then the caller can ask:
(was e raised?) .
. the other common way
is using the name of a datatype or class;
ie, you can ask:
"(was the failure from any operation owned by
number.type ?)
. along the same lines, you can be more specific
by asking which subprogram or operation
was in effect when the exception was raised .
eg,
asking "(did f cause the exception?)
would be the same as asking
"(was it any exception raised by f
or by employees of f ?
).

. exceptions should be part of the subprogram interface;
this is in contrast to ada's idea
which requires exceptions to be
packaged with a subprogram:
ie, instead of submitting just a sub' to the library,
the sub' and it's exceptions must be
components of a package;
then importing the package from the library
brings you both the sub' and its exceptions .

. when using subprogram names as exception cases,
there can be some confusion due to
overloading of sub' names,
so the syntax must allow for use of the full name
including the parameter types,
which may preclude the use of declarations
within an exception-casing.stmt
(atleast not at the top level);
[1.19: or,
overloaded operators can be viewed as
belonging to a particular datatype or package,
so then for function f belonging to t.type,
there would be the exception case: t`f .
. then using an overloaded name without qualification
would mean every member of the overload class . ]

. raising an exception means
asking whether any in command chain
is catching this exception,
if no,
then the system knows to hang up the whole process,
else
having an exception handler in the employer chain
gives the system a place to roll back to .
. this is all the info needed by the system
by runtime
the sub decides on exceptions to propagate;
if the sup happens to catch, ok .
todo:
. the details of this rollback require a review
of how nested and recursive subunits
complicate where on the stack an instance is .
todo:
. what does either say about
contracts and exceptions?

. even if a sub' doesn't declare an exception
then there are still certain system exceptions
that are implicitely declared for every sub' .
. it is very common for sub's to fail because of
misusing sytem resources, eg:
exception?
( [out of mem]: handler#1
, [access violation]: handler#2
, others: handler#3 ...
) .

1.20: exception/translation:

. anything you do with {setjump, signal}
can bring out bugs in compiler
and make your app less robust;
so, it's best to first check your sdk
for platform-specific ways to
make your app responsive to user interupts .
. while setjump is good at
quickly unwinding the stack,
can it really be the case
that a rarely occuring situation
is the right place to worry about being quick
at the expense of program stability ?
. signals may still be useful,
but platform-specific frameworks
usually provide you with full-featured
event-loop programming that includes
all the signals you'll need .

declaring dialog-exceptions:
. dialog-exceptions are just call-backs,
so a subprogram can declare them as globals
(see adda/dstr/param'blocks)

addm`exceptions

1.20: addm/exceptions:

. I first had the idea of stacking
more than the usual return address,
for the 2 cases of whether or not
the system was in an exception-raised mode .
. however, in recursive situations
that would use a lot more memory;
ie, an extra pointer per call,
when the alternative is to have a
conditional at the call's return point
which could be shared by all those recursive calls .
. then I found a way in which
it wouldn't even need the conditional.stmt:
. for a call.stmt that may involve an exception,
place a goto.stmt after it;
then make the call's return address
to land beyond the goto.stmt .
. in an exception.mode, the system would
treat the return address differently,
decrementing it before using it,
which would then cause the return to
land on the goto that would jump to the
exception-casing stmt,
or if letting a super.routine handle it,
the goto could just land at the
[cleanup and exit].section .