never executed always true always false
    1 -- GENERATED by C->Haskell Compiler, version 0.28.8 Switcheroo, 25 November 2017 (Haskell)
    2 -- Edit the ORIGNAL .chs file instead!
    3 
    4 
    5 module QuantLib.Commodity
    6   (
    7     CommodityType
    8   , commodityType
    9   , nullCommodityType
   10   , commodityTypeCode
   11   , commodityTypeName
   12   , commodityTypeEmpty
   13 
   14   , UnitOfMeasure
   15   , UnitOfMeasureType(..)
   16   , unitOfMeasure
   17   , unitOfMeasureName
   18   , unitOfMeasureCode
   19   , unitOfMeasureType
   20   , unitOfMeasureEmpty
   21   , lotUnitOfMeasure
   22   , barrelUnitOfMeasure
   23   , mtUnitOfMeasure
   24   , mbUnitOfMeasure
   25   , gallonUnitOfMeasure
   26   , litreUnitOfMeasure
   27   , kilolitreUnitOfMeasure
   28   , tokyoKilolitreUnitOfMeasure
   29 
   30   , PaymentTerm
   31   , PaymentTermEventType(..)
   32   , paymentTerm
   33   , paymentTermName
   34   , paymentTermEventType
   35   , paymentTermOffsetDays
   36   , paymentTermCalendar
   37   , paymentTermEmpty
   38   , paymentTermGetPaymentDate
   39 
   40   , Quantity
   41   , roundedQuantity
   42   , closeQuantity
   43   , closeEnoughQuantity
   44 
   45   , CommodityUnitCost
   46 
   47   , DateInterval
   48   , isDateBetween
   49   , intersection
   50 
   51   , PricingPeriod
   52   , pricingPeriodStartDate
   53   , pricingPeriodEndDate
   54   , pricingPeriodPaymentDate
   55   , pricingPeriodQuantity
   56   , PricingPeriods
   57   , pricingPeriod
   58 
   59   , UnitOfMeasureConversion
   60   , UnitOfMeasureConversionType(..)
   61   , unitOfMeasureConversion
   62   , unitOfMeasureConversionSource
   63   , unitOfMeasureConversionTarget
   64   , unitOfMeasureConversionCommodityType
   65   , unitOfMeasureConversionType
   66   , unitOfMeasureConversionFactor
   67   , unitOfMeasureConversionCode
   68   , convertQuantity
   69   , chainUnitOfMeasureConversion
   70 
   71   , lookupUomConversion
   72   , addUomConversion
   73   , clearUomConversions
   74 
   75   , commoditySettingsCurrency
   76   , setCommoditySettingsCurrency
   77   , commoditySettingsUnitOfMeasure
   78   , setCommoditySettingsUnitOfMeasure
   79   ) where
   80 import qualified Foreign.C.String as C2HSImp
   81 import qualified Foreign.C.Types as C2HSImp
   82 import qualified Foreign.ForeignPtr as C2HSImp
   83 import qualified Foreign.Marshal.Utils as C2HSImp
   84 import qualified Foreign.Ptr as C2HSImp
   85 import qualified System.IO.Unsafe as C2HSImp
   86 
   87 
   88 import QuantLib.Internal
   89 import QuantLib.Internal.Type
   90 import QuantLib.Internal.Common
   91 import Foreign.Marshal.Alloc(alloca)
   92 
   93 
   94 
   95 
   96 
   97 
   98 
   99 
  100 
  101 
  102 
  103 
  104 
  105 
  106 
  107 
  108 
  109 
  110 
  111 
  112 data UnitOfMeasureConversionType = UomDirect
  113                                  | UomDerived
  114   deriving (Enum,Show,Eq,Read)
  115 
  116 
  117 
  118 -- |Construct a custom commodity type identified by its code (e.g. \"HO\") and descriptive name
  119 -- (e.g. \"Heating Oil\"). QuantLib has no fixed enum of commodity types -- every instance is
  120 -- user-registered by code, the same way a custom 'QuantLib.Currency.currency'' is.
  121 commodityType :: (String) -- ^code
  122  -> (String) -- ^name
  123  -> IO ((CommodityType))
  124 commodityType a1 a2 =
  125   C2HSImp.withCString a1 $ \a1' -> 
  126   C2HSImp.withCString a2 $ \a2' -> 
  127   preErrorCheck $ \a3' -> 
  128   commodityType'_ a1' a2' a3' >>= \res ->
  129   peekCommodityType res >>= \res' ->
  130   errorCheck  a3'>>
  131   return (res')
  132 
  133 
  134 
  135 -- |The fixed placeholder commodity type QuantLib itself uses where no real commodity type
  136 -- applies (e.g. in unit-of-measure-only conversions).
  137 nullCommodityType :: IO ((CommodityType))
  138 nullCommodityType =
  139   preErrorCheck $ \a1' -> 
  140   nullCommodityType'_ a1' >>= \res ->
  141   peekCommodityType res >>= \res' ->
  142   errorCheck  a1'>>
  143   return (res')
  144 
  145 
  146 
  147 -- |The commodity code, e.g. \"HO\".
  148 commodityTypeCode :: (CommodityType) -> (String)
  149 commodityTypeCode a1 =
  150   C2HSImp.unsafePerformIO $
  151   withCommodityType a1 $ \a1' -> 
  152   commodityTypeCode'_ a1' >>= \res ->
  153   peekDynString res >>= \res' ->
  154   return (res')
  155 
  156 
  157 
  158 -- |The descriptive name, e.g. \"Heating Oil\".
  159 commodityTypeName :: (CommodityType) -> (String)
  160 commodityTypeName a1 =
  161   C2HSImp.unsafePerformIO $
  162   withCommodityType a1 $ \a1' -> 
  163   commodityTypeName'_ a1' >>= \res ->
  164   peekDynString res >>= \res' ->
  165   return (res')
  166 
  167 
  168 
  169 -- |Whether this is a usable instance (as opposed to one built via a default constructor).
  170 commodityTypeEmpty :: (CommodityType) -> (Bool)
  171 commodityTypeEmpty a1 =
  172   C2HSImp.unsafePerformIO $
  173   withCommodityType a1 $ \a1' -> 
  174   commodityTypeEmpty'_ a1' >>= \res ->
  175   let {res' = C2HSImp.toBool res} in
  176   return (res')
  177 
  178 
  179 
  180 -- |Construct a custom unit of measure from its descriptive name (e.g. \"Barrels\"), code (e.g.
  181 -- \"BBL\"), and type (mass/volume/energy/quantity).
  182 unitOfMeasure :: (String) -- ^name
  183  -> (String) -- ^code
  184  -> (UnitOfMeasureType) -> IO ((UnitOfMeasure))
  185 unitOfMeasure a1 a2 a3 =
  186   C2HSImp.withCString a1 $ \a1' -> 
  187   C2HSImp.withCString a2 $ \a2' -> 
  188   let {a3' = fromEnumC a3} in 
  189   preErrorCheck $ \a4' -> 
  190   unitOfMeasure'_ a1' a2' a3' a4' >>= \res ->
  191   peekUnitOfMeasure res >>= \res' ->
  192   errorCheck  a4'>>
  193   return (res')
  194 
  195 
  196 
  197 -- |The descriptive name, e.g. \"Barrels\".
  198 unitOfMeasureName :: (UnitOfMeasure) -> (String)
  199 unitOfMeasureName a1 =
  200   C2HSImp.unsafePerformIO $
  201   withUnitOfMeasure a1 $ \a1' -> 
  202   unitOfMeasureName'_ a1' >>= \res ->
  203   peekDynString res >>= \res' ->
  204   return (res')
  205 
  206 
  207 
  208 -- |The code, e.g. \"BBL\", \"MT\".
  209 unitOfMeasureCode :: (UnitOfMeasure) -> (String)
  210 unitOfMeasureCode a1 =
  211   C2HSImp.unsafePerformIO $
  212   withUnitOfMeasure a1 $ \a1' -> 
  213   unitOfMeasureCode'_ a1' >>= \res ->
  214   peekDynString res >>= \res' ->
  215   return (res')
  216 
  217 
  218 
  219 -- |The unit's type (mass/volume/energy/quantity).
  220 unitOfMeasureType :: (UnitOfMeasure) -> (UnitOfMeasureType)
  221 unitOfMeasureType a1 =
  222   C2HSImp.unsafePerformIO $
  223   withUnitOfMeasure a1 $ \a1' -> 
  224   unitOfMeasureType'_ a1' >>= \res ->
  225   let {res' = toEnumC res} in
  226   return (res')
  227 
  228 
  229 
  230 -- |Whether this is a usable instance (as opposed to one built via a default constructor).
  231 unitOfMeasureEmpty :: (UnitOfMeasure) -> (Bool)
  232 unitOfMeasureEmpty a1 =
  233   C2HSImp.unsafePerformIO $
  234   withUnitOfMeasure a1 $ \a1' -> 
  235   unitOfMeasureEmpty'_ a1' >>= \res ->
  236   let {res' = C2HSImp.toBool res} in
  237   return (res')
  238 
  239 
  240 
  241 -- |The lot, a dimensionless 'UnitOfMeasure::Quantity' unit.
  242 lotUnitOfMeasure :: IO ((UnitOfMeasure))
  243 lotUnitOfMeasure =
  244   preErrorCheck $ \a1' -> 
  245   lotUnitOfMeasure'_ a1' >>= \res ->
  246   peekUnitOfMeasure res >>= \res' ->
  247   errorCheck  a1'>>
  248   return (res')
  249 
  250 
  251 -- |Barrels (BBL), the base petroleum volume unit.
  252 barrelUnitOfMeasure :: IO ((UnitOfMeasure))
  253 barrelUnitOfMeasure =
  254   preErrorCheck $ \a1' -> 
  255   barrelUnitOfMeasure'_ a1' >>= \res ->
  256   peekUnitOfMeasure res >>= \res' ->
  257   errorCheck  a1'>>
  258   return (res')
  259 
  260 
  261 -- |Metric tonnes (MT).
  262 mtUnitOfMeasure :: IO ((UnitOfMeasure))
  263 mtUnitOfMeasure =
  264   preErrorCheck $ \a1' -> 
  265   mtUnitOfMeasure'_ a1' >>= \res ->
  266   peekUnitOfMeasure res >>= \res' ->
  267   errorCheck  a1'>>
  268   return (res')
  269 
  270 
  271 -- |Thousand barrels (MB).
  272 mbUnitOfMeasure :: IO ((UnitOfMeasure))
  273 mbUnitOfMeasure =
  274   preErrorCheck $ \a1' -> 
  275   mbUnitOfMeasure'_ a1' >>= \res ->
  276   peekUnitOfMeasure res >>= \res' ->
  277   errorCheck  a1'>>
  278   return (res')
  279 
  280 
  281 -- |US gallons.
  282 gallonUnitOfMeasure :: IO ((UnitOfMeasure))
  283 gallonUnitOfMeasure =
  284   preErrorCheck $ \a1' -> 
  285   gallonUnitOfMeasure'_ a1' >>= \res ->
  286   peekUnitOfMeasure res >>= \res' ->
  287   errorCheck  a1'>>
  288   return (res')
  289 
  290 
  291 -- |Litres.
  292 litreUnitOfMeasure :: IO ((UnitOfMeasure))
  293 litreUnitOfMeasure =
  294   preErrorCheck $ \a1' -> 
  295   litreUnitOfMeasure'_ a1' >>= \res ->
  296   peekUnitOfMeasure res >>= \res' ->
  297   errorCheck  a1'>>
  298   return (res')
  299 
  300 
  301 -- |Kilolitres.
  302 kilolitreUnitOfMeasure :: IO ((UnitOfMeasure))
  303 kilolitreUnitOfMeasure =
  304   preErrorCheck $ \a1' -> 
  305   kilolitreUnitOfMeasure'_ a1' >>= \res ->
  306   peekUnitOfMeasure res >>= \res' ->
  307   errorCheck  a1'>>
  308   return (res')
  309 
  310 
  311 -- |Tokyo kilolitres.
  312 tokyoKilolitreUnitOfMeasure :: IO ((UnitOfMeasure))
  313 tokyoKilolitreUnitOfMeasure =
  314   preErrorCheck $ \a1' -> 
  315   tokyoKilolitreUnitOfMeasure'_ a1' >>= \res ->
  316   peekUnitOfMeasure res >>= \res' ->
  317   errorCheck  a1'>>
  318   return (res')
  319 
  320 
  321 
  322 -- |Construct a payment term: a named offset (in calendar-adjusted days) from either the trade
  323 -- date or the pricing-period end date.
  324 paymentTerm :: (String) -- ^name
  325  -> (PaymentTermEventType) -> (Int) -- ^offsetDays
  326  -> (Calendar) -> IO ((PaymentTerm))
  327 paymentTerm a1 a2 a3 a4 =
  328   C2HSImp.withCString a1 $ \a1' -> 
  329   let {a2' = fromEnumC a2} in 
  330   let {a3' = fromIntegral a3} in 
  331   withCalendar a4 $ \a4' -> 
  332   preErrorCheck $ \a5' -> 
  333   paymentTerm'_ a1' a2' a3' a4' a5' >>= \res ->
  334   peekPaymentTerm res >>= \res' ->
  335   errorCheck  a5'>>
  336   return (res')
  337 
  338 
  339 
  340 -- |The payment term's name, e.g. \"Pricing end + 5 days\".
  341 paymentTermName :: (PaymentTerm) -> (String)
  342 paymentTermName a1 =
  343   C2HSImp.unsafePerformIO $
  344   withPaymentTerm a1 $ \a1' -> 
  345   paymentTermName'_ a1' >>= \res ->
  346   peekDynString res >>= \res' ->
  347   return (res')
  348 
  349 
  350 
  351 -- |Whether the offset is measured from the trade date or the pricing date.
  352 paymentTermEventType :: (PaymentTerm) -> (PaymentTermEventType)
  353 paymentTermEventType a1 =
  354   C2HSImp.unsafePerformIO $
  355   withPaymentTerm a1 $ \a1' -> 
  356   paymentTermEventType'_ a1' >>= \res ->
  357   let {res' = toEnumC res} in
  358   return (res')
  359 
  360 
  361 
  362 -- |The number of (calendar-adjusted) offset days.
  363 paymentTermOffsetDays :: (PaymentTerm) -> (Int)
  364 paymentTermOffsetDays a1 =
  365   C2HSImp.unsafePerformIO $
  366   withPaymentTerm a1 $ \a1' -> 
  367   paymentTermOffsetDays'_ a1' >>= \res ->
  368   let {res' = fromIntegral res} in
  369   return (res')
  370 
  371 
  372 
  373 -- |The calendar used to adjust the payment date.
  374 paymentTermCalendar :: (PaymentTerm) -> IO ((Calendar))
  375 paymentTermCalendar a1 =
  376   withPaymentTerm a1 $ \a1' -> 
  377   preErrorCheck $ \a2' -> 
  378   paymentTermCalendar'_ a1' a2' >>= \res ->
  379   peekCalendar res >>= \res' ->
  380   errorCheck  a2'>>
  381   return (res')
  382 
  383 
  384 
  385 -- |Whether this is a usable instance (as opposed to one built via a default constructor).
  386 paymentTermEmpty :: (PaymentTerm) -> (Bool)
  387 paymentTermEmpty a1 =
  388   C2HSImp.unsafePerformIO $
  389   withPaymentTerm a1 $ \a1' -> 
  390   paymentTermEmpty'_ a1' >>= \res ->
  391   let {res' = C2HSImp.toBool res} in
  392   return (res')
  393 
  394 
  395 
  396 -- |Applies the term's offset (and calendar adjustment) to a trade or pricing-period-end date to
  397 -- get the actual payment date.
  398 paymentTermGetPaymentDate :: (PaymentTerm) -> (Day) -> IO ((Day))
  399 paymentTermGetPaymentDate a1 a2 =
  400   withPaymentTerm a1 $ \a1' -> 
  401   withDay a2 $ \a2' -> 
  402   preErrorCheck $ \a3' -> 
  403   paymentTermGetPaymentDate'_ a1' a2' a3' >>= \res ->
  404   let {res' = toDay res} in
  405   errorCheck  a3'>>
  406   return (res')
  407 
  408 
  409 
  410 -- |An amount of a commodity: a 'CommodityType', a 'UnitOfMeasure', and a plain amount. Marshalled
  411 -- as a flat triple rather than a wrapper type (per the @Money@-as-tuple convention) -- and, unlike
  412 -- 'CommodityUnitCost' below, its three inspectors are just tuple projections, so they need no
  413 -- binding at all. c2hs's @&@ tuple-splitter only ever consumes two C arguments (confirmed against
  414 -- its source, not just by trial), so every function below that takes or returns a 'Quantity'
  415 -- marshals it as three flat 'CommodityType'\/'UnitOfMeasure'\/'Double' arguments instead of one
  416 -- combined tuple.
  417 type Quantity = (CommodityType, UnitOfMeasure, Double)
  418 
  419 quantityRoundedAmount :: (UnitOfMeasure) -> (Double) -> (Double)
  420 quantityRoundedAmount a1 a2 =
  421   C2HSImp.unsafePerformIO $
  422   withUnitOfMeasure a1 $ \a1' -> 
  423   let {a2' = realToFrac a2} in 
  424   quantityRoundedAmount'_ a1' a2' >>= \res ->
  425   let {res' = realToFrac res} in
  426   return (res')
  427 
  428 
  429 
  430 -- |Round a quantity's amount per its unit of measure's rounding convention. The commodity type and
  431 -- unit of measure are unaffected by rounding, so they're carried straight through in Haskell
  432 -- rather than round-tripped through the C++ call.
  433 roundedQuantity :: Quantity -> Quantity
  434 roundedQuantity (ct, uom, amount) = (ct, uom, quantityRoundedAmount uom amount)
  435 
  436 qlQuantityClose_ :: (CommodityType) -> (UnitOfMeasure) -> (Double) -> (CommodityType) -> (UnitOfMeasure) -> (Double) -> (Int) -> IO ((Bool))
  437 qlQuantityClose_ a1 a2 a3 a4 a5 a6 a7 =
  438   withCommodityType a1 $ \a1' -> 
  439   withUnitOfMeasure a2 $ \a2' -> 
  440   let {a3' = realToFrac a3} in 
  441   withCommodityType a4 $ \a4' -> 
  442   withUnitOfMeasure a5 $ \a5' -> 
  443   let {a6' = realToFrac a6} in 
  444   let {a7' = fromIntegral a7} in 
  445   preErrorCheck $ \a8' -> 
  446   qlQuantityClose_'_ a1' a2' a3' a4' a5' a6' a7' a8' >>= \res ->
  447   let {res' = C2HSImp.toBool res} in
  448   errorCheck  a8'>>
  449   return (res')
  450 
  451 
  452 
  453 -- |Whether two quantities are close to within @n@ ULPs (default 42 upstream), after converting
  454 -- the second to the first's unit of measure if their units differ (which throws unless a
  455 -- conversion is reachable -- see 'lookupUomConversion').
  456 closeQuantity :: Quantity -> Quantity -> Int -> IO Bool
  457 closeQuantity (ct1, uom1, amt1) (ct2, uom2, amt2) n = qlQuantityClose_ ct1 uom1 amt1 ct2 uom2 amt2 n
  458 
  459 qlQuantityCloseEnough_ :: (CommodityType) -> (UnitOfMeasure) -> (Double) -> (CommodityType) -> (UnitOfMeasure) -> (Double) -> (Int) -> IO ((Bool))
  460 qlQuantityCloseEnough_ a1 a2 a3 a4 a5 a6 a7 =
  461   withCommodityType a1 $ \a1' -> 
  462   withUnitOfMeasure a2 $ \a2' -> 
  463   let {a3' = realToFrac a3} in 
  464   withCommodityType a4 $ \a4' -> 
  465   withUnitOfMeasure a5 $ \a5' -> 
  466   let {a6' = realToFrac a6} in 
  467   let {a7' = fromIntegral a7} in 
  468   preErrorCheck $ \a8' -> 
  469   qlQuantityCloseEnough_'_ a1' a2' a3' a4' a5' a6' a7' a8' >>= \res ->
  470   let {res' = C2HSImp.toBool res} in
  471   errorCheck  a8'>>
  472   return (res')
  473 
  474 
  475 
  476 -- |As 'closeQuantity', but using QuantLib's relative (rather than absolute) closeness test.
  477 closeEnoughQuantity :: Quantity -> Quantity -> Int -> IO Bool
  478 closeEnoughQuantity (ct1, uom1, amt1) (ct2, uom2, amt2) n = qlQuantityCloseEnough_ ct1 uom1 amt1 ct2 uom2 amt2 n
  479 
  480 -- |A commodity's unit cost: a cash amount (a @(Double, Currency)@ pair, standing in for
  481 -- QuantLib's @Money@) per 'UnitOfMeasure'. A plain tuple, like 'Quantity' -- it carries no
  482 -- calculation of its own upstream.
  483 type CommodityUnitCost = (Double, Currency, UnitOfMeasure)
  484 
  485 -- |A date range, inclusive of both ends. No C++ call is needed for either operation below --
  486 -- 'Day' (from @Data.Time.Calendar@) already has the 'Ord' instance QuantLib's own comparisons rely
  487 -- on, so both are plain Haskell functions rather than shim calls.
  488 type DateInterval = (Day, Day)
  489 
  490 -- |Whether a date falls within the interval, optionally excluding either end.
  491 isDateBetween :: DateInterval
  492               -> Day -- ^date
  493               -> Bool -- ^includeFirst
  494               -> Bool -- ^includeLast
  495               -> Bool
  496 isDateBetween (startDate, endDate) date includeFirst includeLast =
  497   (if includeFirst then date >= startDate else date > startDate) &&
  498   (if includeLast then date <= endDate else date < endDate)
  499 
  500 -- |The overlap of two date intervals, or 'Nothing' if they don't overlap at all (upstream returns
  501 -- a default-constructed, both-dates-null 'DateInterval' in this case; a 'Maybe' is the natural
  502 -- Haskell equivalent).
  503 intersection :: DateInterval -> DateInterval -> Maybe DateInterval
  504 intersection (s1, e1) (s2, e2)
  505   | (s1 < s2 && e1 < s2) || (s1 > e2 && e1 > e2) = Nothing
  506   | otherwise = Just (max s1 s2, min e1 e2)
  507 
  508 -- |A 'DateInterval' over which a fixed 'Quantity' of a commodity is priced, paid on
  509 -- 'pricingPeriodPaymentDate'. Unlike 'Quantity'\/'CommodityUnitCost', this is a real record
  510 -- rather than a tuple, per the user's explicit choice -- it's used as a named unit across every
  511 -- energy-swap constructor (Stage 6), where a flat tuple would be unreadable positionally.
  512 data PricingPeriod = PricingPeriod
  513   { pricingPeriodStartDate :: Day
  514   , pricingPeriodEndDate :: Day
  515   , pricingPeriodPaymentDate :: Day
  516   , pricingPeriodQuantity :: Quantity
  517   } deriving (Show, Eq)
  518 
  519 type PricingPeriods = [PricingPeriod]
  520 
  521 -- |Construct a 'PricingPeriod', enforcing upstream's @DateInterval@ invariant that the end date
  522 -- is not before the start date.
  523 pricingPeriod :: Day -> Day -> Day -> Quantity -> PricingPeriod
  524 pricingPeriod startDate endDate
  525   | endDate < startDate = error "pricingPeriod: end date must be >= start date"
  526   | otherwise = PricingPeriod startDate endDate
  527 
  528 -- |Construct a conversion factor between two units of measure for a given commodity type: a unit
  529 -- of @source@ is worth @conversionFactor@ units of @target@.
  530 unitOfMeasureConversion :: (CommodityType) -> (UnitOfMeasure) -- ^source
  531  -> (UnitOfMeasure) -- ^target
  532  -> (Double) -- ^conversionFactor
  533  -> IO ((UnitOfMeasureConversion))
  534 unitOfMeasureConversion a1 a2 a3 a4 =
  535   withCommodityType a1 $ \a1' -> 
  536   withUnitOfMeasure a2 $ \a2' -> 
  537   withUnitOfMeasure a3 $ \a3' -> 
  538   let {a4' = realToFrac a4} in 
  539   preErrorCheck $ \a5' -> 
  540   unitOfMeasureConversion'_ a1' a2' a3' a4' a5' >>= \res ->
  541   peekUnitOfMeasureConversion res >>= \res' ->
  542   errorCheck  a5'>>
  543   return (res')
  544 
  545 
  546 
  547 -- |The source unit of measure.
  548 unitOfMeasureConversionSource :: (UnitOfMeasureConversion) -> IO ((UnitOfMeasure))
  549 unitOfMeasureConversionSource a1 =
  550   withUnitOfMeasureConversion a1 $ \a1' -> 
  551   preErrorCheck $ \a2' -> 
  552   unitOfMeasureConversionSource'_ a1' a2' >>= \res ->
  553   peekUnitOfMeasure res >>= \res' ->
  554   errorCheck  a2'>>
  555   return (res')
  556 
  557 
  558 
  559 -- |The target unit of measure.
  560 unitOfMeasureConversionTarget :: (UnitOfMeasureConversion) -> IO ((UnitOfMeasure))
  561 unitOfMeasureConversionTarget a1 =
  562   withUnitOfMeasureConversion a1 $ \a1' -> 
  563   preErrorCheck $ \a2' -> 
  564   unitOfMeasureConversionTarget'_ a1' a2' >>= \res ->
  565   peekUnitOfMeasure res >>= \res' ->
  566   errorCheck  a2'>>
  567   return (res')
  568 
  569 
  570 
  571 -- |The commodity type this conversion applies to.
  572 unitOfMeasureConversionCommodityType :: (UnitOfMeasureConversion) -> IO ((CommodityType))
  573 unitOfMeasureConversionCommodityType a1 =
  574   withUnitOfMeasureConversion a1 $ \a1' -> 
  575   preErrorCheck $ \a2' -> 
  576   unitOfMeasureConversionCommodityType'_ a1' a2' >>= \res ->
  577   peekCommodityType res >>= \res' ->
  578   errorCheck  a2'>>
  579   return (res')
  580 
  581 
  582 
  583 -- |Whether the conversion was given directly, or derived by chaining two other conversions.
  584 unitOfMeasureConversionType :: (UnitOfMeasureConversion) -> (UnitOfMeasureConversionType)
  585 unitOfMeasureConversionType a1 =
  586   C2HSImp.unsafePerformIO $
  587   withUnitOfMeasureConversion a1 $ \a1' -> 
  588   unitOfMeasureConversionType'_ a1' >>= \res ->
  589   let {res' = (toEnum . fromIntegral) res} in
  590   return (res')
  591 
  592 
  593 
  594 -- |The conversion factor: a unit of the source is worth this many units of the target.
  595 unitOfMeasureConversionFactor :: (UnitOfMeasureConversion) -> (Double)
  596 unitOfMeasureConversionFactor a1 =
  597   C2HSImp.unsafePerformIO $
  598   withUnitOfMeasureConversion a1 $ \a1' -> 
  599   unitOfMeasureConversionFactor'_ a1' >>= \res ->
  600   let {res' = realToFrac res} in
  601   return (res')
  602 
  603 
  604 
  605 -- |A code identifying the conversion, e.g. \"Heating OilMTBBL\".
  606 unitOfMeasureConversionCode :: (UnitOfMeasureConversion) -> (String)
  607 unitOfMeasureConversionCode a1 =
  608   C2HSImp.unsafePerformIO $
  609   withUnitOfMeasureConversion a1 $ \a1' -> 
  610   unitOfMeasureConversionCode'_ a1' >>= \res ->
  611   peekDynString res >>= \res' ->
  612   return (res')
  613 
  614 
  615 
  616 qlUnitOfMeasureConversionConvert_ :: (UnitOfMeasureConversion) -> (CommodityType) -> (UnitOfMeasure) -> (Double) -> IO ((Double), (CommodityType), (UnitOfMeasure))
  617 qlUnitOfMeasureConversionConvert_ a1 a2 a3 a4 =
  618   withUnitOfMeasureConversion a1 $ \a1' -> 
  619   withCommodityType a2 $ \a2' -> 
  620   withUnitOfMeasure a3 $ \a3' -> 
  621   let {a4' = realToFrac a4} in 
  622   alloca $ \a5' -> 
  623   alloca $ \a6' -> 
  624   preErrorCheck $ \a7' -> 
  625   qlUnitOfMeasureConversionConvert_'_ a1' a2' a3' a4' a5' a6' a7' >>= \res ->
  626   let {res' = realToFrac res} in
  627   peekCommodityTypePtr  a5'>>= \a5'' -> 
  628   peekUnitOfMeasurePtr  a6'>>= \a6'' -> 
  629   errorCheck  a7'>>
  630   return (res', a5'', a6'')
  631 
  632 
  633 
  634 -- |Apply the conversion factor to a quantity, converting it from the conversion's source to its
  635 -- target unit of measure (or vice versa). Throws if the quantity's unit of measure is on neither
  636 -- side of the conversion.
  637 convertQuantity :: UnitOfMeasureConversion -> Quantity -> IO Quantity
  638 convertQuantity conv (ct, uom, amount) = do
  639   (amount', ct', uom') <- qlUnitOfMeasureConversionConvert_ conv ct uom amount
  640   pure (ct', uom', amount')
  641 
  642 -- |Combine two conversions sharing a common unit of measure into a derived conversion between
  643 -- their other two units. Throws if the conversions don't share a common unit.
  644 chainUnitOfMeasureConversion :: (UnitOfMeasureConversion) -> (UnitOfMeasureConversion) -> IO ((UnitOfMeasureConversion))
  645 chainUnitOfMeasureConversion a1 a2 =
  646   withUnitOfMeasureConversion a1 $ \a1' -> 
  647   withUnitOfMeasureConversion a2 $ \a2' -> 
  648   preErrorCheck $ \a3' -> 
  649   chainUnitOfMeasureConversion'_ a1' a2' a3' >>= \res ->
  650   peekUnitOfMeasureConversion res >>= \res' ->
  651   errorCheck  a3'>>
  652   return (res')
  653 
  654 
  655 
  656 -- |Look up a (possibly derived, via triangulation) conversion between two units of measure for a
  657 -- given commodity type. Throws if none can be found. Pre-populated with a set of known petroleum
  658 -- conversion factors even before any 'addUomConversion' call.
  659 lookupUomConversion :: (CommodityType) -> (UnitOfMeasure) -- ^source
  660  -> (UnitOfMeasure) -- ^target
  661  -> (UnitOfMeasureConversionType) -> IO ((UnitOfMeasureConversion))
  662 lookupUomConversion a1 a2 a3 a4 =
  663   withCommodityType a1 $ \a1' -> 
  664   withUnitOfMeasure a2 $ \a2' -> 
  665   withUnitOfMeasure a3 $ \a3' -> 
  666   let {a4' = (fromIntegral . fromEnum) a4} in 
  667   preErrorCheck $ \a5' -> 
  668   lookupUomConversion'_ a1' a2' a3' a4' a5' >>= \res ->
  669   peekUnitOfMeasureConversion res >>= \res' ->
  670   errorCheck  a5'>>
  671   return (res')
  672 
  673 
  674 
  675 -- |Register a conversion with the global unit-of-measure conversion repository, replacing any
  676 -- existing conversion between the same commodity type and pair of units.
  677 addUomConversion :: (UnitOfMeasureConversion) -> IO ()
  678 addUomConversion a1 =
  679   withUnitOfMeasureConversion a1 $ \a1' -> 
  680   addUomConversion'_ a1' >>
  681   return ()
  682 
  683 
  684 
  685 -- |Reset the unit-of-measure conversion repository back to its built-in set of known petroleum
  686 -- conversion factors, discarding anything added via 'addUomConversion'.
  687 clearUomConversions :: IO ()
  688 clearUomConversions =
  689   clearUomConversions'_ >>
  690   return ()
  691 
  692 
  693 
  694 -- |The global commodity currency setting (defaults to USD).
  695 commoditySettingsCurrency :: IO ((Currency))
  696 commoditySettingsCurrency =
  697   preErrorCheck $ \a1' -> 
  698   commoditySettingsCurrency'_ a1' >>= \res ->
  699   peekCurrency res >>= \res' ->
  700   errorCheck  a1'>>
  701   return (res')
  702 
  703 
  704 
  705 -- |Set the global commodity currency setting.
  706 setCommoditySettingsCurrency :: (Currency) -> IO ()
  707 setCommoditySettingsCurrency a1 =
  708   withCurrency a1 $ \a1' -> 
  709   setCommoditySettingsCurrency'_ a1' >>
  710   return ()
  711 
  712 
  713 
  714 -- |The global commodity unit-of-measure setting (defaults to barrels).
  715 commoditySettingsUnitOfMeasure :: IO ((UnitOfMeasure))
  716 commoditySettingsUnitOfMeasure =
  717   preErrorCheck $ \a1' -> 
  718   commoditySettingsUnitOfMeasure'_ a1' >>= \res ->
  719   peekUnitOfMeasure res >>= \res' ->
  720   errorCheck  a1'>>
  721   return (res')
  722 
  723 
  724 
  725 -- |Set the global commodity unit-of-measure setting.
  726 setCommoditySettingsUnitOfMeasure :: (UnitOfMeasure) -> IO ()
  727 setCommoditySettingsUnitOfMeasure a1 =
  728   withUnitOfMeasure a1 $ \a1' -> 
  729   setCommoditySettingsUnitOfMeasure'_ a1' >>
  730   return ()
  731 
  732 
  733 
  734 -- vim: set ff=unix ts=8 sts=2 sw=2 et:
  735 
  736 foreign import ccall safe "QuantLib/Commodity.chs.h qlCommodityType"
  737   commodityType'_ :: ((C2HSImp.Ptr C2HSImp.CChar) -> ((C2HSImp.Ptr C2HSImp.CChar) -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CCommodityType))))))
  738 
  739 foreign import ccall safe "QuantLib/Commodity.chs.h qlNullCommodityType"
  740   nullCommodityType'_ :: ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CCommodityType))))
  741 
  742 foreign import ccall safe "QuantLib/Commodity.chs.h qlCommodityTypeCode"
  743   commodityTypeCode'_ :: ((C2HSImp.Ptr (CCommodityType)) -> (IO (C2HSImp.Ptr C2HSImp.CChar)))
  744 
  745 foreign import ccall safe "QuantLib/Commodity.chs.h qlCommodityTypeName"
  746   commodityTypeName'_ :: ((C2HSImp.Ptr (CCommodityType)) -> (IO (C2HSImp.Ptr C2HSImp.CChar)))
  747 
  748 foreign import ccall safe "QuantLib/Commodity.chs.h qlCommodityTypeEmpty"
  749   commodityTypeEmpty'_ :: ((C2HSImp.Ptr (CCommodityType)) -> (IO C2HSImp.CInt))
  750 
  751 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasure"
  752   unitOfMeasure'_ :: ((C2HSImp.Ptr C2HSImp.CChar) -> ((C2HSImp.Ptr C2HSImp.CChar) -> (C2HSImp.CInt -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure)))))))
  753 
  754 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureName"
  755   unitOfMeasureName'_ :: ((C2HSImp.Ptr (CUnitOfMeasure)) -> (IO (C2HSImp.Ptr C2HSImp.CChar)))
  756 
  757 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureCode"
  758   unitOfMeasureCode'_ :: ((C2HSImp.Ptr (CUnitOfMeasure)) -> (IO (C2HSImp.Ptr C2HSImp.CChar)))
  759 
  760 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureUnitType"
  761   unitOfMeasureType'_ :: ((C2HSImp.Ptr (CUnitOfMeasure)) -> (IO C2HSImp.CInt))
  762 
  763 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureEmpty"
  764   unitOfMeasureEmpty'_ :: ((C2HSImp.Ptr (CUnitOfMeasure)) -> (IO C2HSImp.CInt))
  765 
  766 foreign import ccall safe "QuantLib/Commodity.chs.h qlLotUnitOfMeasure"
  767   lotUnitOfMeasure'_ :: ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure))))
  768 
  769 foreign import ccall safe "QuantLib/Commodity.chs.h qlBarrelUnitOfMeasure"
  770   barrelUnitOfMeasure'_ :: ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure))))
  771 
  772 foreign import ccall safe "QuantLib/Commodity.chs.h qlMTUnitOfMeasure"
  773   mtUnitOfMeasure'_ :: ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure))))
  774 
  775 foreign import ccall safe "QuantLib/Commodity.chs.h qlMBUnitOfMeasure"
  776   mbUnitOfMeasure'_ :: ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure))))
  777 
  778 foreign import ccall safe "QuantLib/Commodity.chs.h qlGallonUnitOfMeasure"
  779   gallonUnitOfMeasure'_ :: ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure))))
  780 
  781 foreign import ccall safe "QuantLib/Commodity.chs.h qlLitreUnitOfMeasure"
  782   litreUnitOfMeasure'_ :: ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure))))
  783 
  784 foreign import ccall safe "QuantLib/Commodity.chs.h qlKilolitreUnitOfMeasure"
  785   kilolitreUnitOfMeasure'_ :: ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure))))
  786 
  787 foreign import ccall safe "QuantLib/Commodity.chs.h qlTokyoKilolitreUnitOfMeasure"
  788   tokyoKilolitreUnitOfMeasure'_ :: ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure))))
  789 
  790 foreign import ccall safe "QuantLib/Commodity.chs.h qlPaymentTerm"
  791   paymentTerm'_ :: ((C2HSImp.Ptr C2HSImp.CChar) -> (C2HSImp.CInt -> (C2HSImp.CInt -> ((C2HSImp.Ptr (CCalendar)) -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CPaymentTerm))))))))
  792 
  793 foreign import ccall safe "QuantLib/Commodity.chs.h qlPaymentTermName"
  794   paymentTermName'_ :: ((C2HSImp.Ptr (CPaymentTerm)) -> (IO (C2HSImp.Ptr C2HSImp.CChar)))
  795 
  796 foreign import ccall safe "QuantLib/Commodity.chs.h qlPaymentTermEventType_"
  797   paymentTermEventType'_ :: ((C2HSImp.Ptr (CPaymentTerm)) -> (IO C2HSImp.CInt))
  798 
  799 foreign import ccall safe "QuantLib/Commodity.chs.h qlPaymentTermOffsetDays"
  800   paymentTermOffsetDays'_ :: ((C2HSImp.Ptr (CPaymentTerm)) -> (IO C2HSImp.CInt))
  801 
  802 foreign import ccall safe "QuantLib/Commodity.chs.h qlPaymentTermCalendar"
  803   paymentTermCalendar'_ :: ((C2HSImp.Ptr (CPaymentTerm)) -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CCalendar)))))
  804 
  805 foreign import ccall safe "QuantLib/Commodity.chs.h qlPaymentTermEmpty"
  806   paymentTermEmpty'_ :: ((C2HSImp.Ptr (CPaymentTerm)) -> (IO C2HSImp.CInt))
  807 
  808 foreign import ccall safe "QuantLib/Commodity.chs.h qlPaymentTermGetPaymentDate"
  809   paymentTermGetPaymentDate'_ :: ((C2HSImp.Ptr (CPaymentTerm)) -> (C2HSImp.CInt -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO C2HSImp.CInt))))
  810 
  811 foreign import ccall safe "QuantLib/Commodity.chs.h qlQuantityRoundedAmount"
  812   quantityRoundedAmount'_ :: ((C2HSImp.Ptr (CUnitOfMeasure)) -> (C2HSImp.CDouble -> (IO C2HSImp.CDouble)))
  813 
  814 foreign import ccall safe "QuantLib/Commodity.chs.h qlQuantityClose"
  815   qlQuantityClose_'_ :: ((C2HSImp.Ptr (CCommodityType)) -> ((C2HSImp.Ptr (CUnitOfMeasure)) -> (C2HSImp.CDouble -> ((C2HSImp.Ptr (CCommodityType)) -> ((C2HSImp.Ptr (CUnitOfMeasure)) -> (C2HSImp.CDouble -> (C2HSImp.CInt -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO C2HSImp.CInt)))))))))
  816 
  817 foreign import ccall safe "QuantLib/Commodity.chs.h qlQuantityCloseEnough"
  818   qlQuantityCloseEnough_'_ :: ((C2HSImp.Ptr (CCommodityType)) -> ((C2HSImp.Ptr (CUnitOfMeasure)) -> (C2HSImp.CDouble -> ((C2HSImp.Ptr (CCommodityType)) -> ((C2HSImp.Ptr (CUnitOfMeasure)) -> (C2HSImp.CDouble -> (C2HSImp.CInt -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO C2HSImp.CInt)))))))))
  819 
  820 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversion"
  821   unitOfMeasureConversion'_ :: ((C2HSImp.Ptr (CCommodityType)) -> ((C2HSImp.Ptr (CUnitOfMeasure)) -> ((C2HSImp.Ptr (CUnitOfMeasure)) -> (C2HSImp.CDouble -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasureConversion))))))))
  822 
  823 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversionSource"
  824   unitOfMeasureConversionSource'_ :: ((C2HSImp.Ptr (CUnitOfMeasureConversion)) -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure)))))
  825 
  826 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversionTarget"
  827   unitOfMeasureConversionTarget'_ :: ((C2HSImp.Ptr (CUnitOfMeasureConversion)) -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure)))))
  828 
  829 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversionCommodityType"
  830   unitOfMeasureConversionCommodityType'_ :: ((C2HSImp.Ptr (CUnitOfMeasureConversion)) -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CCommodityType)))))
  831 
  832 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversionType_"
  833   unitOfMeasureConversionType'_ :: ((C2HSImp.Ptr (CUnitOfMeasureConversion)) -> (IO C2HSImp.CInt))
  834 
  835 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversionFactor"
  836   unitOfMeasureConversionFactor'_ :: ((C2HSImp.Ptr (CUnitOfMeasureConversion)) -> (IO C2HSImp.CDouble))
  837 
  838 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversionCode"
  839   unitOfMeasureConversionCode'_ :: ((C2HSImp.Ptr (CUnitOfMeasureConversion)) -> (IO (C2HSImp.Ptr C2HSImp.CChar)))
  840 
  841 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversionConvert"
  842   qlUnitOfMeasureConversionConvert_'_ :: ((C2HSImp.Ptr (CUnitOfMeasureConversion)) -> ((C2HSImp.Ptr (CCommodityType)) -> ((C2HSImp.Ptr (CUnitOfMeasure)) -> (C2HSImp.CDouble -> ((C2HSImp.Ptr (C2HSImp.Ptr (CCommodityType))) -> ((C2HSImp.Ptr (C2HSImp.Ptr (CUnitOfMeasure))) -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO C2HSImp.CDouble))))))))
  843 
  844 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversionChain"
  845   chainUnitOfMeasureConversion'_ :: ((C2HSImp.Ptr (CUnitOfMeasureConversion)) -> ((C2HSImp.Ptr (CUnitOfMeasureConversion)) -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasureConversion))))))
  846 
  847 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversionManagerLookup"
  848   lookupUomConversion'_ :: ((C2HSImp.Ptr (CCommodityType)) -> ((C2HSImp.Ptr (CUnitOfMeasure)) -> ((C2HSImp.Ptr (CUnitOfMeasure)) -> (C2HSImp.CInt -> ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasureConversion))))))))
  849 
  850 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversionManagerAdd"
  851   addUomConversion'_ :: ((C2HSImp.Ptr (CUnitOfMeasureConversion)) -> (IO ()))
  852 
  853 foreign import ccall safe "QuantLib/Commodity.chs.h qlUnitOfMeasureConversionManagerClear"
  854   clearUomConversions'_ :: (IO ())
  855 
  856 foreign import ccall safe "QuantLib/Commodity.chs.h qlCommoditySettingsCurrency"
  857   commoditySettingsCurrency'_ :: ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CCurrency))))
  858 
  859 foreign import ccall safe "QuantLib/Commodity.chs.h qlCommoditySettingsSetCurrency"
  860   setCommoditySettingsCurrency'_ :: ((C2HSImp.Ptr (CCurrency)) -> (IO ()))
  861 
  862 foreign import ccall safe "QuantLib/Commodity.chs.h qlCommoditySettingsUnitOfMeasure"
  863   commoditySettingsUnitOfMeasure'_ :: ((C2HSImp.Ptr (C2HSImp.Ptr C2HSImp.CChar)) -> (IO (C2HSImp.Ptr (CUnitOfMeasure))))
  864 
  865 foreign import ccall safe "QuantLib/Commodity.chs.h qlCommoditySettingsSetUnitOfMeasure"
  866   setCommoditySettingsUnitOfMeasure'_ :: ((C2HSImp.Ptr (CUnitOfMeasure)) -> (IO ()))