1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586(* Copyright (C) 2014--2018 Petter A. Urkedal <paurkedal@gmail.com>
*
* This library is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or (at your
* option) any later version, with the OCaml static compilation exception.
*
* This library is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
* License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*)(* This is partly based on https://github.com/janestreet/lwt-async *)openCoreopenAsyncmoduleSystem=structtype'afuture='aDeferred.tlet(>>=)mf=Deferred.bindm~flet(>|=)=Deferred.(>>|)letreturn=Deferred.returnletjoin=Deferred.all_ignoremoduleMvar=structtype'at='aIvar.tletcreate=Ivar.createletstorexv=Ivar.fillvxletfetchv=Ivar.readvendmoduleUnix=structtypefile_descr=Async_unix.Fd.tletfdinfo=Info.of_string"Caqti_async file descriptor"letwrap_fdfufd=letfd=Fd.create(Fd.Kind.Socket`Active)ufdfdinfoinletopenDeferredinffd>>=funr->Fd.(close~file_descriptor_handling:Do_not_close_file_descriptor)fd>>=fun()->returnrletpoll?(read=false)?(write=false)?timeoutfd=letwait_read=ifreadthenAsync_unix.Fd.ready_tofd`ReadelseDeferred.never()inletwait_write=ifwritethenAsync_unix.Fd.ready_tofd`WriteelseDeferred.never()inletwait_timeout=(matchtimeoutwith|Somet->Clock.after(Time.Span.of_sect)|None->Deferred.never())inletdid_read,did_write,did_timeout=reffalse,reffalse,reffalseinDeferred.enabled[Deferred.choicewait_read(funst->did_read:=st=`Ready);Deferred.choicewait_write(funst->did_write:=st=`Ready);Deferred.choicewait_timeout(fun()->did_timeout:=true);]>>|(funf->ignore(f());(!did_read,!did_write,!did_timeout))endmoduleLog=structletlog_flevelfmt=ksprintf(funs->Log.string~level(Lazy.forceLog.Global.log)s;return())fmtleterror_ffmt=log_f`Errorfmtletwarning_ffmt=log_f`Infofmtletinfo_ffmt=log_f`Infofmtletdebug_ffmt=log_f`DebugfmtendmodulePreemptive=structletdetachfx=In_thread.run(fun()->fx)letrun_in_mainf=Thread_safe.block_on_async_exnfendendmoduleV2=Caqti_connect.Make(System)includeV2