From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Original-To: caml-list@sympa.inria.fr Delivered-To: caml-list@sympa.inria.fr Received: from mail3-relais-sop.national.inria.fr (mail3-relais-sop.national.inria.fr [192.134.164.104]) by sympa.inria.fr (Postfix) with ESMTPS id A11BD7FDC8 for ; Tue, 12 Jan 2016 14:06:12 +0100 (CET) IronPort-PHdr: 9a23:jTBFFBTNUiv1Tme/MEjBQpctYtpsv+yvbD5Q0YIujvd0So/mwa64bR2N2/xhgRfzUJnB7Loc0qyN4/6mCTdLu83JmUtBWaIPfidNsd8RkQ0kDZzNImzAB9muURYHGt9fXkRu5XCxPBsdMs//Y1rPvi/6tmZKSV3BPAZ4bt74BpTVx5zukbvipduDOE4S33KUWvBbElaflU3prM4YgI9veO4a6yDihT92QdlQ3n5iPlmJnhzxtY+a9Z9n9DlM6bp6r5YTGY2zRakzTKRZATI6KCh1oZSz7ViQBTeIszE6X3gWmxdVGBPI9lWye57rrir8/KIp3SCAIczwC7Y5RDSr4rpwUxLyoDwGOjs09nqRgct12vF1uhWk8lZFwoXUaZuZfMU4W+WVX9QcSHELFpJLVidBKoq6aYYfDuNHOvxX+dqu72ASpAezUFH/TNjkzSVF0zqvhfU3 Authentication-Results: mail3-smtp-sop.national.inria.fr; spf=None smtp.pra=rich@annexia.org; spf=Pass smtp.mailfrom=rich@annexia.org; spf=Pass smtp.helo=postmaster@annexia.org Received-SPF: None (mail3-smtp-sop.national.inria.fr: no sender authenticity information available from domain of rich@annexia.org) identity=pra; client-ip=80.68.91.176; receiver=mail3-smtp-sop.national.inria.fr; envelope-from="rich@annexia.org"; x-sender="rich@annexia.org"; x-conformance=sidf_compatible Received-SPF: Pass (mail3-smtp-sop.national.inria.fr: domain of rich@annexia.org designates 80.68.91.176 as permitted sender) identity=mailfrom; client-ip=80.68.91.176; receiver=mail3-smtp-sop.national.inria.fr; envelope-from="rich@annexia.org"; x-sender="rich@annexia.org"; x-conformance=sidf_compatible; x-record-type="v=spf1" Received-SPF: Pass (mail3-smtp-sop.national.inria.fr: domain of postmaster@annexia.org designates 80.68.91.176 as permitted sender) identity=helo; client-ip=80.68.91.176; receiver=mail3-smtp-sop.national.inria.fr; envelope-from="rich@annexia.org"; x-sender="postmaster@annexia.org"; x-conformance=sidf_compatible; x-record-type="v=spf1" X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: A0B7RwBc+ZRW/7BbRFBegzpSbYJihXefdAEBAQEBAQYIgQWUFCSFIRA6AoElOxEBAQEBAQEBAYEJgi2CCAEBBDo/EAshEwcLDwUoIYhFCr9OAQEBAQEFAQEBAQEaBIYOPoUJgm0khRGBGwWXEwGFQoJzhRqPBY5TOCyCSoFAPjQFhiwBAQE X-IPAS-Result: A0B7RwBc+ZRW/7BbRFBegzpSbYJihXefdAEBAQEBAQYIgQWUFCSFIRA6AoElOxEBAQEBAQEBAYEJgi2CCAEBBDo/EAshEwcLDwUoIYhFCr9OAQEBAQEFAQEBAQEaBIYOPoUJgm0khRGBGwWXEwGFQoJzhRqPBY5TOCyCSoFAPjQFhiwBAQE X-IronPort-AV: E=Sophos;i="5.20,557,1444687200"; d="scan'208";a="160148939" Received: from annexia.org ([80.68.91.176]) by mail3-smtp-sop.national.inria.fr with ESMTP/TLS/AES128-GCM-SHA256; 12 Jan 2016 14:06:11 +0100 Received: from rich by annexia.org with local (Exim 4.84) (envelope-from ) id 1aIyeH-0004fR-2F; Tue, 12 Jan 2016 13:06:09 +0000 Date: Tue, 12 Jan 2016 13:06:09 +0000 From: "Richard W.M. Jones" To: "Neuhaeusser, Martin" Cc: "caml-list@inria.fr" Message-ID: <20160112130609.GA27249@annexia.org> References: <965631B03C670145ABB9F693E51622530D0D763B@DENBGAT9EK5MSX.ww902.siemens.net> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <965631B03C670145ABB9F693E51622530D0D763B@DENBGAT9EK5MSX.ww902.siemens.net> User-Agent: Mutt/1.5.23 (2014-03-12) Subject: Re: [Caml-list] The OCaml garbage collector, finalisers, and the right way of disposing native pointers in C bindings The other replies have covered some of the problems. You may also be interested in example code, and we've got lots :-) Most of the bugs have now been fixed, after several iterations. Here are some things to get you started. (1) Simple example of a finalizer attached to a custom block: https://github.com/libguestfs/libguestfs/blob/master/mllib/progress-c.c https://github.com/libguestfs/libguestfs/blob/master/mllib/progress.ml https://github.com/libguestfs/libguestfs/blob/master/mllib/progress.mli (2) A more complex example using generational roots to deal with callbacks from OCaml back to C: https://github.com/libguestfs/libguestfs/blob/master/ocaml/guestfs-c.c This one had a major bug, when we discovered that the root caused the handle to be always reachable, so the finalizer was not called until the program exited (the fact that we also have a #close method, which we always called, made this less obvious than you might think at first). That was fixed in: https://github.com/libguestfs/libguestfs/commit/8bbc5e73cb5b56b5cfbe979ac0e1c14d1701a0d8 (3) A tricky binding to libxml2. Because libxml2 has objects containing pointers to other objects (at the C level) we need to shadow these with OCaml structs, to ensure that an OCaml object doesn't become unreachable when it is still pointed to from another object. https://github.com/libguestfs/libguestfs/blob/master/v2v/xml-c.c https://github.com/libguestfs/libguestfs/blob/master/v2v/xml.ml https://github.com/libguestfs/libguestfs/blob/master/v2v/xml.mli If you look at the history of these files, you'll see we discovered and fixed major bugs, eg this one concerned with the order in which we freed objects: https://github.com/libguestfs/libguestfs/commit/3888582da89c757d0740d11c3a62433d748c85aa Note that (3) is a counter-example to the idea that you should use custom blocks. Custom block finalizers in OCaml have no ordering guarantee - if you need an ordering guarantee you must use an OCaml finalizer. You can probably see this stuff gets complicated quickly. Thank goodness for valgrind! Rich.