From: Jacek Generowicz
Subject: Conditions and transfer of data
Date: 
Message-ID: <tyf7kghxje2.fsf@pcitapi22.cern.ch>
I have a loop which performs some mathematical calculations. I write a
record of its progress to a file. Sometimes, an arithmetic error
occurs; in such cases I would like my log file to contain all the data
that has been calculated up to the time the error occured.

Trying to wrap the whole loop in with-open-file and writing the data
as they are produced, doesn't work in this case, as the following
extract of the Spec explains:

  If a new output file is being written, and control leaves
  abnormally, the file is aborted and the file system is left, so far
  as possible, as if the file had never been opened.

An alternative would be to collect the data for later output ... but
in the exceptional case (being unfamiliar with the CL condition
handling system) I haven't found a way of transferring the collected
data to whatever handles the condition.

For example

   (unwind-protect
       (loop for i from 1 with a = 10.0 
        do (setq a (* a 10)) ;deliberately generating FP overflow
        collect a into log)
     (print log))

doesn't work, because log is unknown in the cleanup form.

Looking at using handlers, it seems that all that can be passed to the
handling code is the condition itself; I see no way of passing the
collected data.

Prods in the right direction would be appreciated,

Thanks,

Jacek

From: Kenny Tilton
Subject: Re: Conditions and transfer of data
Date: 
Message-ID: <hDzr9.10635$gB.3561409@twister.nyc.rr.com>
Jacek Generowicz wrote in message ...
>I have a loop which performs some mathematical calculations. I write a
>record of its progress to a file. Sometimes, an arithmetic error
>occurs; in such cases I would like my log file to contain all the data
>that has been calculated up to the time the error occured.
>
>Trying to wrap the whole loop in with-open-file and writing the data
>as they are produced, doesn't work in this case, as the following
>extract of the Spec explains:
>
>  If a new output file is being written, and control leaves
>  abnormally, the file is aborted and the file system is left, so far
>  as possible, as if the file had never been opened.

So don't leave with-open-file abnormally. Trap any error, exit w-o-f
normally, then do what you like with the error.

kenny
clinisys
From: Knut Anders Hatlen
Subject: Re: Conditions and transfer of data
Date: 
Message-ID: <86n0pdxg0t.fsf@stjernegris.hatlen.net>
Jacek Generowicz wrote:

> For example
> 
>    (unwind-protect
>        (loop for i from 1 with a = 10.0 
>         do (setq a (* a 10)) ;deliberately generating FP overflow
>         collect a into log)
>      (print log))
> 
> doesn't work, because log is unknown in the cleanup form.

Then you have to make log visible for the handler.

(let ((log '()))
  (handler-bind ((arithmetic-error
                  #'(lambda (cond)
                      (declare (ignore cond))
                      (format *error-output* "Log: ~S~%" (nreverse log)))))
    (do ((a 10.0 (* a 10)))
        (nil)
      (push a log))))

Hope this helps!

-- 
Knut Anders
From: Kaz Kylheku
Subject: Re: Conditions and transfer of data
Date: 
Message-ID: <cf333042.0210181146.284656a4@posting.google.com>
Jacek Generowicz <················@cern.ch> wrote in message news:<···············@pcitapi22.cern.ch>...
> For example
> 
>    (unwind-protect
>        (loop for i from 1 with a = 10.0 
>         do (setq a (* a 10)) ;deliberately generating FP overflow
>         collect a into log)
>      (print log))
> 
> doesn't work, because log is unknown in the cleanup form.

Here is yet another way:

    (loop for i from 1 with a = 10.0
       do (restart-case
            (setf a (* a 10))
            (print-list ()
              :report "Show what has been collected so far."
              (print log))
            (continue () 
              :report "Leave loop, returning what has been collected."
              (return log)))
          collect a into log)

> Looking at using handlers, it seems that all that can be passed to the
> handling code is the condition itself; I see no way of passing the
> collected data.

You could write a macro which throws a custom condition if the
evaluation of some forms signal an error:

  (when-error (setf a (* 10 a))
     (error (make-condition 'my-condition ...)))