caml-list - the Caml user's mailing list
 help / color / mirror / Atom feed
* [Caml-list] printing an exception changes printed backtrace
@ 2011-01-14 21:15 Ashish Agarwal
  2011-01-14 21:59 ` Daniel Bünzli
  2011-01-17 15:37 ` xclerc
  0 siblings, 2 replies; 7+ messages in thread
From: Ashish Agarwal @ 2011-01-14 21:15 UTC (permalink / raw)
  To: Caml List

[-- Attachment #1: Type: text/plain, Size: 1064 bytes --]

I observe the following unexpected behavior:

--- a.ml ---
try
  … some code ...
with e ->
(*  Printf.eprintf "%s\n" (Printexc.to_string e); *)
  Printexc.print_backtrace Legacy.stderr
------

Compiling as ocamlopt -g a.ml gives:
$ ./a.out
Raised at file "fool.ml", line 162, characters 13-22
Called from file "bar.ml", line 13, characters 5-56
Called from file "bar.ml", line 43, characters 4-63

Now this doesn't say which exception was raised, so I uncomment the
commented line. I'm expecting the identical output, but with the exception
printed first. However, I get:

$ ./a.out
Not_found
Raised at file "hashtbl.ml", line 93, characters 19-28

So it appears that printing an exception changes the backtrace. Is that
possible?

Unfortunately, I cannot reproduce this behavior in a minimal example. The
following script behaves as expected:

--- b.ml ---
let f () = raise (Failure "")
let g () = f ()
let _ =
  try g()
  with e ->
    (* Printf.eprintf "%s\n" (Printexc.to_string e); *)
    Printexc.print_backtrace stderr

[-- Attachment #2: Type: text/html, Size: 1736 bytes --]

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [Caml-list] printing an exception changes printed backtrace
  2011-01-14 21:15 [Caml-list] printing an exception changes printed backtrace Ashish Agarwal
@ 2011-01-14 21:59 ` Daniel Bünzli
  2011-01-14 22:05   ` Ashish Agarwal
  2011-01-17 15:37 ` xclerc
  1 sibling, 1 reply; 7+ messages in thread
From: Daniel Bünzli @ 2011-01-14 21:59 UTC (permalink / raw)
  To: Ashish Agarwal; +Cc: Caml List

> So it appears that printing an exception changes the backtrace. Is that
> possible?

I don't know about the details of backtrace recording but I suspect
that the call to the printing function interferes with the previously
recorded backtrace.

What works for me is to immediately get the backtrace as a string [1]
with Printexc.get_backtrace (), then print the exception and then
print the string.

Also bear in mind that sometimes native backtrace are not as precise
as those in bytecode (tail calls and optimizations ?).

Daniel

[1]
Btw. the api could really have given us a list of strings (or even of
string * string * int * (int * int)). I already had to parse that
string to properly format backtraces.

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [Caml-list] printing an exception changes printed backtrace
  2011-01-14 21:59 ` Daniel Bünzli
@ 2011-01-14 22:05   ` Ashish Agarwal
  0 siblings, 0 replies; 7+ messages in thread
From: Ashish Agarwal @ 2011-01-14 22:05 UTC (permalink / raw)
  To: Daniel Bünzli; +Cc: Caml List

[-- Attachment #1: Type: text/plain, Size: 952 bytes --]

Thanks for the workaround; that resolves the issue for me. But this seems
very unstable.


On Fri, Jan 14, 2011 at 4:59 PM, Daniel Bünzli
<daniel.buenzli@erratique.ch>wrote:

> > So it appears that printing an exception changes the backtrace. Is that
> > possible?
>
> I don't know about the details of backtrace recording but I suspect
> that the call to the printing function interferes with the previously
> recorded backtrace.
>
> What works for me is to immediately get the backtrace as a string [1]
> with Printexc.get_backtrace (), then print the exception and then
> print the string.
>
> Also bear in mind that sometimes native backtrace are not as precise
> as those in bytecode (tail calls and optimizations ?).
>
> Daniel
>
> [1]
> Btw. the api could really have given us a list of strings (or even of
> string * string * int * (int * int)). I already had to parse that
> string to properly format backtraces.
>

[-- Attachment #2: Type: text/html, Size: 1273 bytes --]

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [Caml-list] printing an exception changes printed backtrace
  2011-01-14 21:15 [Caml-list] printing an exception changes printed backtrace Ashish Agarwal
  2011-01-14 21:59 ` Daniel Bünzli
@ 2011-01-17 15:37 ` xclerc
  2011-01-17 16:41   ` Ashish Agarwal
  1 sibling, 1 reply; 7+ messages in thread
From: xclerc @ 2011-01-17 15:37 UTC (permalink / raw)
  To: Ashish Agarwal; +Cc: xclerc, Caml List


Le 14 janv. 2011 à 22:15, Ashish Agarwal a écrit :

> I observe the following unexpected behavior:
> 
> --- a.ml ---
> try
>   … some code ...
> with e ->
> (*  Printf.eprintf "%s\n" (Printexc.to_string e); *)
>   Printexc.print_backtrace Legacy.stderr
> ------
> 
> Compiling as ocamlopt -g a.ml gives:
> $ ./a.out
> Raised at file "fool.ml", line 162, characters 13-22
> Called from file "bar.ml", line 13, characters 5-56
> Called from file "bar.ml", line 43, characters 4-63
> 
> Now this doesn't say which exception was raised, so I uncomment the commented line. I'm expecting the identical output, but with the exception printed first. However, I get:
> 
> $ ./a.out
> Not_found
> Raised at file "hashtbl.ml", line 93, characters 19-28
> 
> So it appears that printing an exception changes the backtrace. Is that possible?
> 
> Unfortunately, I cannot reproduce this behavior in a minimal example. The following script behaves as expected:

It seems possible to reproduce the problem with the following source code:


let custom_printer = true

let () =
  if custom_printer then
    Printexc.register_printer
      (function
        | Not_found -> failwith "silently"
        | _ -> None)

let rec f () =
  ignore (raise Not_found);
  f ()

let () =
  try
    f ()
  with e ->
    Printf.eprintf "%s\n%!" (Printexc.to_string e);
    Printexc.print_backtrace stderr



You will get different backtraces according to the value of "custom_printer".
The underlying problem is that "Printexc.print_backtrace" prints the backtrace
for the last exception raised... which can be one raised by "Printf.eprintf" or
"Printexc.to_string", but locally caught and not exposed to the outside world.

In the code sample above, an exception is raised by the register custom
printer. By design of "Printexc.to_string", such exceptions are silently
ignored... but change the value of the last raised exception (and thus its
associated backtrace).

Your experience of the backtrace actually vanishing may be an instance of
the same problem, where it just happens that the code for the custom printer
has not been compiled with the "-g" option.


Hope this helps,

Xavier Clerc



^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [Caml-list] printing an exception changes printed backtrace
  2011-01-17 15:37 ` xclerc
@ 2011-01-17 16:41   ` Ashish Agarwal
  2011-01-17 17:02     ` Xavier Clerc
  0 siblings, 1 reply; 7+ messages in thread
From: Ashish Agarwal @ 2011-01-17 16:41 UTC (permalink / raw)
  To: xclerc; +Cc: Caml List

[-- Attachment #1: Type: text/plain, Size: 970 bytes --]

On Mon, Jan 17, 2011 at 10:37 AM, xclerc <xavier.clerc@inria.fr> wrote:


> The underlying problem is that "Printexc.print_backtrace" prints the
> backtrace
> for the last exception raised... which can be one raised by
> "Printf.eprintf" or
> "Printexc.to_string", but locally caught and not exposed to the outside
> world.
>

Okay, that makes sense.



> You will get different backtraces according to the value of
> "custom_printer".
>

I'm actually getting the same output (just "Not_found" printed). Tried
native and byte code, on two different systems.

Based on your explanation, I was expecting the following to give different
output if you change true to false. But actually nothing is printed out in
any case. So I'm really unclear now as to what print_backtrace does.

let f () =
  try raise Not_found
  with Not_found -> ()

let g () = raise (Failure "")

let () =
  try g()
  with e -> (
    if true then f() else ();
    Printexc.print_backtrace stderr
  )

[-- Attachment #2: Type: text/html, Size: 1808 bytes --]

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [Caml-list] printing an exception changes printed backtrace
  2011-01-17 16:41   ` Ashish Agarwal
@ 2011-01-17 17:02     ` Xavier Clerc
  2011-01-17 17:12       ` Ashish Agarwal
  0 siblings, 1 reply; 7+ messages in thread
From: Xavier Clerc @ 2011-01-17 17:02 UTC (permalink / raw)
  To: Ashish Agarwal; +Cc: Caml List

[-- Attachment #1: Type: text/plain, Size: 1232 bytes --]



----- Mail original -----


De: "Ashish Agarwal" <agarwal1975@gmail.com> 
À: "xclerc" <xavier.clerc@inria.fr> 
Cc: "Caml List" <caml-list@inria.fr> 
Envoyé: Lundi 17 Janvier 2011 17:41:13 
Objet: Re: [Caml-list] printing an exception changes printed backtrace 


On Mon, Jan 17, 2011 at 10:37 AM, xclerc < xavier.clerc@inria.fr > wrote: 



The underlying problem is that "Printexc.print_backtrace" prints the backtrace 
for the last exception raised... which can be one raised by "Printf.eprintf" or 
"Printexc.to_string", but locally caught and not exposed to the outside world. 



Okay, that makes sense. 




You will get different backtraces according to the value of "custom_printer". 



I'm actually getting the same output (just "Not_found" printed). Tried native and byte code, on two different systems. 


Based on your explanation, I was expecting the following to give different output if you change true to false. But actually nothing is printed out in any case. So I'm really unclear now as to what print_backtrace does. Are you sure that you compiled the source with the "-g" option, 
*and* set the OCAMLRUNPARAM environment variable to "b"? 


Regards, 

Xavier Clerc 


[-- Attachment #2: Type: text/html, Size: 2094 bytes --]

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [Caml-list] printing an exception changes printed backtrace
  2011-01-17 17:02     ` Xavier Clerc
@ 2011-01-17 17:12       ` Ashish Agarwal
  0 siblings, 0 replies; 7+ messages in thread
From: Ashish Agarwal @ 2011-01-17 17:12 UTC (permalink / raw)
  To: Xavier Clerc; +Cc: Caml List

[-- Attachment #1: Type: text/plain, Size: 1613 bytes --]

Oops. Forgot about OCAMLRUNPARAM. Both your and my example work now. Okay,
this resolves the issue in some sense; you have to be careful about
exceptions being raised that you don't see. Thanks for the explanations.


On Mon, Jan 17, 2011 at 12:02 PM, Xavier Clerc <xavier.clerc@inria.fr>wrote:

>
>
> ------------------------------
>
> *De: *"Ashish Agarwal" <agarwal1975@gmail.com>
> *À: *"xclerc" <xavier.clerc@inria.fr>
> *Cc: *"Caml List" <caml-list@inria.fr>
> *Envoyé: *Lundi 17 Janvier 2011 17:41:13
> *Objet: *Re: [Caml-list] printing an exception changes printed backtrace
>
>
> On Mon, Jan 17, 2011 at 10:37 AM, xclerc <xavier.clerc@inria.fr> wrote:
>
>
>> The underlying problem is that "Printexc.print_backtrace" prints the
>> backtrace
>> for the last exception raised... which can be one raised by
>> "Printf.eprintf" or
>> "Printexc.to_string", but locally caught and not exposed to the outside
>> world.
>>
>
> Okay, that makes sense.
>
>
>
>> You will get different backtraces according to the value of
>> "custom_printer".
>>
>
> I'm actually getting the same output (just "Not_found" printed). Tried
> native and byte code, on two different systems.
>
> Based on your explanation, I was expecting the following to give different
> output if you change true to false. But actually nothing is printed out in
> any case. So I'm really unclear now as to what print_backtrace does.
>
> Are you sure that you compiled the source with the "-g" option,
> *and* set the OCAMLRUNPARAM environment variable to "b"?
>
>
> Regards,
>
> Xavier Clerc
>
>

[-- Attachment #2: Type: text/html, Size: 2842 bytes --]

^ permalink raw reply	[flat|nested] 7+ messages in thread

end of thread, other threads:[~2011-01-17 17:13 UTC | newest]

Thread overview: 7+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-01-14 21:15 [Caml-list] printing an exception changes printed backtrace Ashish Agarwal
2011-01-14 21:59 ` Daniel Bünzli
2011-01-14 22:05   ` Ashish Agarwal
2011-01-17 15:37 ` xclerc
2011-01-17 16:41   ` Ashish Agarwal
2011-01-17 17:02     ` Xavier Clerc
2011-01-17 17:12       ` Ashish Agarwal

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).