123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122(*
* Copyright (C) 2016-present David Scott <dave.scott@docker.com>
* Copyright (c) 2011-present Anil Madhavapeddy <anil@recoil.org>
* Copyright (c) 2013-present Thomas Gazagnaire <thomas@gazagnaire.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*)typewrite_error=[`Closed]letpp_write_errorppf=function|`Closed->Fmt.pfppf"attempted to write to a closed flow"type'aor_eof=[`Dataof'a|`Eof]letpp_or_eofdppf=function|`Dataa->dppfa|`Eof->Fmt.stringppf"End-of-file"moduletypeABSTRACT=sigtype+'aiotypeerrorvalpp_error:errorFmt.ttypewrite_errorvalpp_write_error:write_errorFmt.ttypebuffertypeflowvalread:flow->(bufferor_eof,error)resultiovalwrite:flow->buffer->(unit,write_error)resultiovalwritev:flow->bufferlist->(unit,write_error)resultiovalclose:flow->unitioendmoduletypeS=ABSTRACTwithtypewrite_error=private[>write_error][@@ocaml.warning"-34"]moduletypeCONCRETE=ABSTRACTwithtypeerror=[`Msgofstring]andtypewrite_error=[write_error|`Msgofstring]moduleConcrete(S:S)(IO:sigtype'at='aS.iovalmap:('a->'b)->'at->'btend)=structtype'aio='aS.iotypeerror=[`Msgofstring]typewrite_error=[`Closed|`Msgofstring]typebuffer=S.buffertypeflow=S.flowletpp_errorppf=function|`Msgs->Fmt.stringppfsletpp_write_errorppf=function|#errorase->pp_errorppfe|`Closed->pp_write_errorppf`Closedletlift_read=function|Okx->Okx|Errore->Error(`Msg(Fmt.strf"%a"S.pp_errore))letlift_write=function|Ok()->Ok()|Error`Closed->Error`Closed|Errore->Error(`Msg(Fmt.strf"%a"S.pp_write_errore))letreadt=IO.maplift_read(S.readt)letwritetb=IO.maplift_write(S.writetb)letwritevtbs=IO.maplift_write(S.writevtbs)letcloset=S.closetendmoduletypeSHUTDOWNABLE=sigincludeSvalshutdown_write:flow->unitiovalshutdown_read:flow->unitioendtypestats={read_bytes:int64;read_ops:int64;write_bytes:int64;write_ops:int64;duration:int64;}letkib=1024Llet(**)=Int64.mulletmib=kib**1024Lletgib=mib**1024Llettib=gib**1024Lletsuffix=[kib,"KiB";mib,"MiB";gib,"GiB";tib,"TiB";]letadd_suffixx=List.fold_left(funacc(y,label)->ifInt64.divxy>0LthenPrintf.sprintf"%.1f %s"Int64.((to_floatx)/.(to_floaty))labelelseacc)(Printf.sprintf"%Ld bytes"x)suffixletpp_statsppfs=Fmt.pfppf"%s bytes at %s/nanosec and %Lu IOPS/nanosec"(add_suffixs.read_bytes)(add_suffixInt64.(divs.read_bytess.duration))(Int64.divs.read_opss.duration)