Hi,
Part 3 of oleaut32 updates.
Cheers,
Jon
License: X11
Changelog:
Jon Griffiths <jon_p_griffiths@yahoo.com>
+dlls/oleaut32/dec.c dlls/oleaut32/i8.c dlls/oleaut32/r8.c
dlls/oleaut32/Makefile.in dlls/oleaut32/oleaut32.spec
dlls/oleaut32/variant.c
Implement/document decimal/i8/ui8/r8 low-level calls
Add some missing stubs
__________________________________
Do you Yahoo!?
The New Yahoo! Shopping - with improved product search
http://shopping.yahoo.com
diff -uP wine/dlls/oleaut32/dec.c wine-develop/dlls/oleaut32/dec.c
--- wine/dlls/oleaut32/dec.c 1970-01-01 01:00:00.000000000 +0100
+++ wine-develop/dlls/oleaut32/dec.c 2003-10-06 17:33:37.000000000 +0100
@@ -0,0 +1,800 @@
+/*
+ * Variant VT_DECIMAL Functions
+ *
+ * Copyright 2003 Jon Griffiths
+ *
+ * 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 2.1 of the License, or (at your option) any later version.
+ *
+ * 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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#define NONAMELESSUNION
+#define NONAMELESSSTRUCT
+#include "wine/debug.h"
+#include "winbase.h"
+#include "variant.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(ole);
+
+/************************************************************************
+ * VarDecFromUI1 (OLEAUT32.190)
+ *
+ * Convert a VT_UI1 to a DECIMAL.
+ *
+ * PARAMS
+ * bIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromUI1(BYTE bIn, DECIMAL* pDecOut)
+{
+ return _VarDecFromUI1(bIn, pDecOut);
+}
+
+/************************************************************************
+ * VarDecFromI2 (OLEAUT32.191)
+ *
+ * Convert a VT_I2 to a DECIMAL.
+ *
+ * PARAMS
+ * sIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromI2(SHORT sIn, DECIMAL* pDecOut)
+{
+ return _VarDecFromI2(sIn, pDecOut);
+}
+
+/************************************************************************
+ * VarDecFromI4 (OLEAUT32.192)
+ *
+ * Convert a VT_I4 to a DECIMAL.
+ *
+ * PARAMS
+ * sIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromI4(LONG lIn, DECIMAL* pDecOut)
+{
+ DEC_HI32(pDecOut) = 0;
+ DEC_MID32(pDecOut) = 0;
+
+ if (lIn < 0)
+ {
+ DEC_SIGNSCALE(pDecOut) = SIGNSCALE(DECIMAL_NEG,0);
+ DEC_LO32(pDecOut) = -lIn;
+ }
+ else
+ {
+ DEC_SIGNSCALE(pDecOut) = SIGNSCALE(DECIMAL_POS,0);
+ DEC_LO32(pDecOut) = lIn;
+ }
+ return S_OK;
+}
+
+/************************************************************************
+ * VarDecFromR4 (OLEAUT32.193)
+ *
+ * Convert a VT_R4 to a DECIMAL.
+ *
+ * PARAMS
+ * fltIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromR4(FLOAT fltIn, DECIMAL* pDecOut)
+{
+ return _VarDecFromR4(fltIn, pDecOut);
+}
+
+/************************************************************************
+ * VarDecFromR8 (OLEAUT32.194)
+ *
+ * Convert a VT_R8 to a DECIMAL.
+ *
+ * PARAMS
+ * dblIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromR8(double dblIn, DECIMAL* pDecOut)
+{
+ FIXME("(%g,%p)-stub!\n",dblIn,pDecOut);
+ return DISP_E_OVERFLOW;
+}
+
+/************************************************************************
+ * VarDecFromDate (OLEAUT32.195)
+ *
+ * Convert a VT_DATE to a DECIMAL.
+ *
+ * PARAMS
+ * dateIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromDate(DATE dateIn, DECIMAL* pDecOut)
+{
+ return _VarDecFromDate(dateIn, pDecOut);
+}
+
+/************************************************************************
+ * VarDecFromCy (OLEAUT32.196)
+ *
+ * Convert a VT_CY to a DECIMAL.
+ *
+ * PARAMS
+ * cyIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromCy(CY cyIn, DECIMAL* pDecOut)
+{
+ DEC_HI32(pDecOut) = 0;
+
+ /* Note: This assumes 2s complement integer representation */
+ if (cyIn.s.Hi & 0x80000000)
+ {
+ DEC_SIGNSCALE(pDecOut) = SIGNSCALE(DECIMAL_NEG,4);
+ DEC_LO64(pDecOut) = -cyIn.int64;
+ }
+ else
+ {
+ DEC_SIGNSCALE(pDecOut) = SIGNSCALE(DECIMAL_POS,4);
+ DEC_MID32(pDecOut) = cyIn.s.Hi;
+ DEC_LO32(pDecOut) = cyIn.s.Lo;
+ }
+ return S_OK;
+}
+
+/************************************************************************
+ * VarDecFromStr (OLEAUT32.197)
+ *
+ * Convert a VT_BSTR to a DECIMAL.
+ *
+ * PARAMS
+ * strIn [I] Source
+ * lcid [I] LCID for the conversion
+ * dwFlags [I] VAR_ flags from "oleauto.h"
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarDecFromStr(OLECHAR* strIn, LCID lcid, ULONG dwFlags, DECIMAL* pDecOut)
+{
+ return _VarDecFromStr(strIn, lcid, dwFlags, pDecOut);
+}
+
+/************************************************************************
+ * VarDecFromDisp (OLEAUT32.198)
+ *
+ * Convert a VT_DISPATCH to a DECIMAL.
+ *
+ * PARAMS
+ * pdispIn [I] Source
+ * lcid [I] LCID for conversion
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarDecFromDisp(IDispatch* pdispIn, LCID lcid, DECIMAL* pDecOut)
+{
+ return _VarDecFromDisp(pdispIn, lcid, pDecOut);
+}
+
+/************************************************************************
+ * VarDecFromBool (OLEAUT32.199)
+ *
+ * Convert a VT_BOOL to a DECIMAL.
+ *
+ * PARAMS
+ * bIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ *
+ * NOTES
+ * The value is converted to either 0 (if bIn is FALSE) or -1 (TRUE).
+ */
+HRESULT WINAPI VarDecFromBool(VARIANT_BOOL bIn, DECIMAL* pDecOut)
+{
+ DEC_HI32(pDecOut) = 0;
+ DEC_MID32(pDecOut) = 0;
+ if (bIn)
+ {
+ DEC_SIGNSCALE(pDecOut) = SIGNSCALE(DECIMAL_NEG,0);
+ DEC_LO32(pDecOut) = 1;
+ }
+ else
+ {
+ DEC_SIGNSCALE(pDecOut) = SIGNSCALE(DECIMAL_POS,0);
+ DEC_LO32(pDecOut) = 0;
+ }
+ return S_OK;
+}
+
+/************************************************************************
+ * VarDecFromI1 (OLEAUT32.241)
+ *
+ * Convert a VT_I1 to a DECIMAL.
+ *
+ * PARAMS
+ * cIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromI1(signed char cIn, DECIMAL* pDecOut)
+{
+ return _VarDecFromI1(cIn, pDecOut);
+}
+
+/************************************************************************
+ * VarDecFromUI2 (OLEAUT32.242)
+ *
+ * Convert a VT_UI2 to a DECIMAL.
+ *
+ * PARAMS
+ * usIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromUI2(USHORT usIn, DECIMAL* pDecOut)
+{
+ return _VarDecFromUI2(usIn, pDecOut);
+}
+
+/************************************************************************
+ * VarDecFromUI4 (OLEAUT32.243)
+ *
+ * Convert a VT_UI4 to a DECIMAL.
+ *
+ * PARAMS
+ * ulIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromUI4(ULONG ulIn, DECIMAL* pDecOut)
+{
+ DEC_SIGNSCALE(pDecOut) = SIGNSCALE(DECIMAL_POS,0);
+ DEC_HI32(pDecOut) = 0;
+ DEC_MID32(pDecOut) = 0;
+ DEC_LO32(pDecOut) = ulIn;
+ return S_OK;
+}
+
+/************************************************************************
+ * VarDecFromI8 (OLEAUT32.374)
+ *
+ * Convert a VT_I8 to a DECIMAL.
+ *
+ * PARAMS
+ * llIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromI8(LONG64 llIn, DECIMAL* pDecOut)
+{
+ PULARGE_INTEGER pLi = (PULARGE_INTEGER)&llIn;
+
+ DEC_HI32(pDecOut) = 0;
+
+ /* Note: This assumes 2s complement integer representation */
+ if (pLi->s.HighPart & 0x80000000)
+ {
+ DEC_SIGNSCALE(pDecOut) = SIGNSCALE(DECIMAL_NEG,0);
+ DEC_LO64(pDecOut) = -pLi->QuadPart;
+ }
+ else
+ {
+ DEC_SIGNSCALE(pDecOut) = SIGNSCALE(DECIMAL_POS,0);
+ DEC_MID32(pDecOut) = pLi->s.HighPart;
+ DEC_LO32(pDecOut) = pLi->s.LowPart;
+ }
+ return S_OK;
+}
+
+/************************************************************************
+ * VarDecFromUI8 (OLEAUT32.375)
+ *
+ * Convert a VT_UI8 to a DECIMAL.
+ *
+ * PARAMS
+ * ullIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarDecFromUI8(ULONG64 ullIn, DECIMAL* pDecOut)
+{
+ PULARGE_INTEGER pLi = (PULARGE_INTEGER)&ullIn;
+
+ DEC_SIGNSCALE(pDecOut) = SIGNSCALE(DECIMAL_POS,0);
+ DEC_HI32(pDecOut) = 0;
+ DEC_MID32(pDecOut) = pLi->s.HighPart;
+ DEC_LO32(pDecOut) = pLi->s.LowPart;
+ return S_OK;
+}
+
+/* Make two DECIMALS the same scale; used by math functions below */
+static HRESULT WINAPI VARIANT_DecScale(const DECIMAL** ppDecLeft, const DECIMAL** ppDecRight, DECIMAL* pDecOut)
+{
+ static DECIMAL scaleFactor;
+ DECIMAL decTemp;
+ int scaleAmount, i;
+ HRESULT hRet = S_OK;
+
+ if (DEC_SIGN(*ppDecLeft) & ~DECIMAL_NEG || DEC_SIGN(*ppDecRight) & ~DECIMAL_NEG)
+ return E_INVALIDARG;
+
+ DEC_LO32(&scaleFactor) = 10;
+
+ i = scaleAmount = DEC_SCALE(*ppDecLeft) - DEC_SCALE(*ppDecRight);
+
+ if (!scaleAmount)
+ return S_OK; /* Same scale */
+
+ if (scaleAmount > 0)
+ {
+ decTemp = *(*ppDecRight); /* Left is bigger - scale the right hand side */
+ *ppDecRight = pDecOut;
+ }
+ else
+ {
+ decTemp = *(*ppDecLeft); /* Right is bigger - scale the left hand side */
+ *ppDecLeft = pDecOut;
+ i = scaleAmount = -scaleAmount;
+ }
+
+ if (DEC_SCALE(&decTemp) + scaleAmount > DEC_MAX_SCALE)
+ return DISP_E_OVERFLOW; /* Can't scale up */
+
+ /* Multiply up the value to be scaled by the correct amount */
+ while (SUCCEEDED(hRet) && i--)
+ {
+ /* Note we are multiplying by a value with a scale of 0, so we dont recurse */
+ hRet = VarDecMul(&decTemp, &scaleFactor, pDecOut);
+ decTemp = *pDecOut;
+ }
+ DEC_SCALE(pDecOut) += scaleAmount; /* Set the new scale */
+ return hRet;
+}
+
+/* Add two unsigned 32 bit values with overflow */
+static ULONG VARIANT_Add(ULONG ulLeft, ULONG ulRight, ULONG* pulHigh)
+{
+ ULARGE_INTEGER ul64;
+
+ ul64.QuadPart = (ULONG64)ulLeft + (ULONG64)ulRight + (ULONG64)*pulHigh;
+ *pulHigh = ul64.s.HighPart;
+ return ul64.s.LowPart;
+}
+
+/* Subtract two unsigned 32 bit values with underflow */
+static ULONG VARIANT_Sub(ULONG ulLeft, ULONG ulRight, ULONG* pulHigh)
+{
+ int invert = 0;
+ ULARGE_INTEGER ul64;
+
+ ul64.QuadPart = (LONG64)ulLeft - (ULONG64)ulRight;
+ if (ulLeft < ulRight)
+ invert = 1;
+
+ if (ul64.QuadPart > (ULONG64)*pulHigh)
+ {
+ ul64.QuadPart -= (ULONG64)*pulHigh;
+ }
+ else
+ {
+ ul64.QuadPart -= (ULONG64)*pulHigh;
+ invert = 1;
+ }
+ if (invert)
+ ul64.s.HighPart = -ul64.s.HighPart ;
+ *pulHigh = ul64.s.HighPart;
+ return ul64.s.LowPart;
+}
+
+/* Compare two decimals that have the same scale */
+static inline int VARIANT_DecCmp(const DECIMAL *pDecLeft, const DECIMAL *pDecRight)
+{
+ if ( DEC_HI32(pDecLeft) < DEC_HI32(pDecRight) ||
+ (DEC_HI32(pDecLeft) <= DEC_HI32(pDecRight) && DEC_LO64(pDecLeft) < DEC_LO64(pDecRight)))
+ return -1;
+ else if (DEC_HI32(pDecLeft) == DEC_HI32(pDecRight) && DEC_LO64(pDecLeft) == DEC_LO64(pDecRight))
+ return 0;
+ return 1;
+}
+
+/************************************************************************
+ * VarDecAdd (OLEAUT32.177)
+ *
+ * Add one DECIMAL to another.
+ *
+ * PARAMS
+ * pDecLeft [I] Source
+ * pDecRight [I] Value to add
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarDecAdd(const DECIMAL* pDecLeft, const DECIMAL* pDecRight, DECIMAL* pDecOut)
+{
+ HRESULT hRet;
+ DECIMAL scaled;
+
+ hRet = VARIANT_DecScale(&pDecLeft, &pDecRight, &scaled);
+
+ if (SUCCEEDED(hRet))
+ {
+ /* Our decimals now have the same scale, we can add them as 96 bit integers */
+ ULONG overflow = 0;
+ BYTE sign = DECIMAL_POS;
+
+ /* Correct for the sign of the result */
+ if (DEC_SIGN(pDecLeft) && DEC_SIGN(pDecRight))
+ {
+ /* -x + -y : Negative */
+ sign = DECIMAL_NEG;
+ goto VarDecAdd_AsPositive;
+ }
+ else if (DEC_SIGN(pDecLeft) && !DEC_SIGN(pDecRight))
+ {
+ /* -x + y : Negative if x > y */
+ if (VARIANT_DecCmp(pDecLeft, pDecRight) > 0)
+ sign = DECIMAL_NEG;
+ DEC_LO32(pDecOut) = VARIANT_Sub(DEC_LO32(pDecRight), DEC_LO32(pDecLeft), &overflow);
+ DEC_MID32(pDecOut) = VARIANT_Sub(DEC_MID32(pDecRight), DEC_MID32(pDecLeft), &overflow);
+ DEC_HI32(pDecOut) = VARIANT_Sub(DEC_HI32(pDecRight), DEC_HI32(pDecLeft), &overflow);
+ }
+ else if (!DEC_SIGN(pDecLeft) && DEC_SIGN(pDecRight))
+ {
+ /* x + -y : Negative if x <= y */
+ if (VARIANT_DecCmp(pDecLeft, pDecRight) <= 0)
+ sign = DECIMAL_NEG;
+ DEC_LO32(pDecOut) = VARIANT_Sub(DEC_LO32(pDecLeft), DEC_LO32(pDecRight), &overflow);
+ DEC_MID32(pDecOut) = VARIANT_Sub(DEC_MID32(pDecLeft), DEC_MID32(pDecRight), &overflow);
+ DEC_HI32(pDecOut) = VARIANT_Sub(DEC_HI32(pDecLeft), DEC_HI32(pDecRight), &overflow);
+ }
+ else
+ {
+ /* x + y : Positive */
+VarDecAdd_AsPositive:
+ DEC_LO32(pDecOut) = VARIANT_Add(DEC_LO32(pDecLeft), DEC_LO32(pDecRight), &overflow);
+ DEC_MID32(pDecOut) = VARIANT_Add(DEC_MID32(pDecLeft), DEC_MID32(pDecRight), &overflow);
+ DEC_HI32(pDecOut) = VARIANT_Add(DEC_HI32(pDecLeft), DEC_HI32(pDecRight), &overflow);
+ }
+
+ if (overflow)
+ return DISP_E_OVERFLOW; /* overflowed */
+
+ DEC_SCALE(pDecOut) = DEC_SCALE(pDecLeft);
+ DEC_SIGN(pDecOut) = sign;
+ }
+ return hRet;
+}
+
+/************************************************************************
+ * VarDecDiv (OLEAUT32.178)
+ *
+ * Divide one DECIMAL by another.
+ *
+ * PARAMS
+ * pDecLeft [I] Source
+ * pDecRight [I] Value to divide by
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarDecDiv(const DECIMAL* pDecLeft, const DECIMAL* pDecRight, DECIMAL* pDecOut)
+{
+ FIXME("(%p,%p,%p)-stub!\n",pDecLeft,pDecRight,pDecOut);
+ return DISP_E_OVERFLOW;
+}
+
+/************************************************************************
+ * VarDecMul (OLEAUT32.179)
+ *
+ * Multiply one DECIMAL by another.
+ *
+ * PARAMS
+ * pDecLeft [I] Source
+ * pDecRight [I] Value to multiply by
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarDecMul(const DECIMAL* pDecLeft, const DECIMAL* pDecRight, DECIMAL* pDecOut)
+{
+ /* FIXME: This is just enough code to allow scaling, albeit very slowly */
+
+ if (!DEC_SCALE(pDecLeft) || !DEC_SCALE(pDecRight))
+ {
+ /* At least one term is an integer */
+ ULONG count;
+ DECIMAL decAdder;
+ const DECIMAL* pDecInteger = DEC_SCALE(pDecLeft) ? pDecRight : pDecLeft;
+ const DECIMAL* pDecOperand = DEC_SCALE(pDecLeft) ? pDecLeft : pDecRight;
+ HRESULT hRet = S_OK;
+
+ if (DEC_HI32(pDecInteger) || DEC_MID32(pDecInteger) ||
+ DEC_LO32(pDecInteger) > 256)
+ {
+ FIXME("(%p,%p,%p) semi-stub!\n",pDecLeft,pDecRight,pDecOut);
+ return DISP_E_OVERFLOW;
+ }
+ count = DEC_LO32(pDecInteger);
+
+ if (!count)
+ {
+ DECIMAL_SETZERO(pDecOut);
+ return S_OK;
+ }
+
+ /* Perform the multiplication as repeated addition (yes, I know this sucks) */
+ decAdder = *pDecOperand;
+
+ while (--count && SUCCEEDED(hRet))
+ {
+ hRet = VarDecAdd(&decAdder, pDecOperand, pDecOut);
+ decAdder = *pDecOut;
+ }
+ *pDecOut = decAdder;
+ return hRet;
+ }
+ FIXME("(%p,%p,%p) semi-stub!\n",pDecLeft,pDecRight,pDecOut);
+ return DISP_E_OVERFLOW;
+}
+
+/************************************************************************
+ * VarDecSub (OLEAUT32.181)
+ *
+ * Subtract one DECIMAL from another.
+ *
+ * PARAMS
+ * pDecLeft [I] Source
+ * pDecRight [I] DECIMAL to subtract from pDecLeft
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarDecSub(const DECIMAL* pDecLeft, const DECIMAL* pDecRight, DECIMAL* pDecOut)
+{
+ DECIMAL decRight;
+
+ /* Implement as addition of the negative */
+ VarDecNeg(pDecRight, &decRight);
+ return VarDecAdd(pDecLeft, &decRight, pDecOut);
+}
+
+/************************************************************************
+ * VarDecAbs (OLEAUT32.182)
+ *
+ * Convert a DECIMAL into its absolute value.
+ *
+ * PARAMS
+ * pDecIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK. This function does not fail.
+ */
+HRESULT WINAPI VarDecAbs(const DECIMAL* pDecIn, DECIMAL* pDecOut)
+{
+ *pDecOut = *pDecIn;
+ DEC_SIGN(pDecOut) &= ~DECIMAL_NEG;
+ return S_OK;
+}
+
+/************************************************************************
+ * VarDecFix (OLEAUT32.187)
+ *
+ * Return the integer portion of a DECIMAL.
+ *
+ * PARAMS
+ * pDecIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarDecFix(const DECIMAL* pDecIn, DECIMAL* pDecOut)
+{
+ if (DEC_SIGN(pDecOut) & ~DECIMAL_NEG)
+ return E_INVALIDARG;
+
+ if (!DEC_SCALE(pDecIn))
+ {
+ *pDecOut = *pDecIn; /* Already an integer */
+ return S_OK;
+ }
+
+ FIXME("semi-stub!\n");
+ return DISP_E_OVERFLOW;
+}
+
+/************************************************************************
+ * VarDecInt (OLEAUT32.188)
+ *
+ * Return the integer portion of a DECIMAL.
+ *
+ * PARAMS
+ * pDecIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarDecInt(const DECIMAL* pDecIn, DECIMAL* pDecOut)
+{
+ if (DEC_SIGN(pDecOut) & ~DECIMAL_NEG)
+ return E_INVALIDARG;
+
+ if (!DEC_SCALE(pDecIn))
+ {
+ *pDecOut = *pDecIn; /* Already an integer */
+ return S_OK;
+ }
+
+ FIXME("semi-stub!\n");
+ return DISP_E_OVERFLOW;
+}
+
+/************************************************************************
+ * VarDecNeg (OLEAUT32.189)
+ *
+ * Change the sign of a DECIMAL.
+ *
+ * PARAMS
+ * pDecIn [I] Source
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * S_OK. This function does not fail.
+ */
+HRESULT WINAPI VarDecNeg(const DECIMAL* pDecIn, DECIMAL* pDecOut)
+{
+ *pDecOut = *pDecIn;
+ DEC_SIGN(pDecOut) ^= DECIMAL_NEG;
+ return S_OK;
+}
+
+/************************************************************************
+ * VarDecRound (OLEAUT32.203)
+ *
+ * Change the precision of a DECIMAL.
+ *
+ * PARAMS
+ * pDecIn [I] Source
+ * cDecimals [I] New number of decimals to keep
+ * pDecOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK. pDecOut contains the rounded value.
+ * Failure: E_INVALIDARG if any argument is invalid.
+ */
+HRESULT WINAPI VarDecRound(const DECIMAL* pDecIn, int cDecimals, DECIMAL* pDecOut)
+{
+ if (cDecimals < 0 || (DEC_SIGN(pDecIn) & ~DECIMAL_NEG) || DEC_SCALE(pDecIn) > DEC_MAX_SCALE)
+ return E_INVALIDARG;
+
+ if (cDecimals >= DEC_SCALE(pDecIn))
+ {
+ *pDecOut = *pDecIn; /* More precision than we have */
+ return S_OK;
+ }
+
+ FIXME("semi-stub!\n");
+
+ return DISP_E_OVERFLOW;
+}
+
+/************************************************************************
+ * VarDecCmp (OLEAUT32.204)
+ *
+ * Compare two DECIMAL values.
+ *
+ * PARAMS
+ * pDecLeft [I] Source
+ * pDecRight [I] Value to compare
+ *
+ * RETURNS
+ * Success: VARCMP_LT, VARCMP_EQ or VARCMP_GT indicating that pDecLeft
+ * is less than, equal to or greater than pDecRight respectively.
+ * Failure: DISP_E_OVERFLOW, if overflow occurs during the comparason
+ */
+HRESULT WINAPI VarDecCmp(const DECIMAL* pDecLeft, const DECIMAL* pDecRight)
+{
+ HRESULT hRet;
+ DECIMAL result;
+
+ /* Subtract right from left, and compare the result to 0 */
+ hRet = VarDecSub(pDecLeft, pDecRight, &result);
+
+ if (SUCCEEDED(hRet))
+ {
+ int non_zero = DEC_HI32(&result) | DEC_MID32(&result) | DEC_LO32(&result);
+
+ if ((DEC_SIGN(&result) & DECIMAL_NEG) && non_zero)
+ hRet = (HRESULT)VARCMP_LT;
+ else if (non_zero)
+ hRet = (HRESULT)VARCMP_GT;
+ else
+ hRet = (HRESULT)VARCMP_EQ;
+ }
+ return hRet;
+}
+
+/************************************************************************
+ * VarDecCmpR8 (OLEAUT32.298)
+ *
+ * Compare a DECIMAL to a double
+ *
+ * PARAMS
+ * pDecLeft [I] DECIMAL Source
+ * dblRight [I] double to compare to pDecLeft
+ *
+ * RETURNS
+ * Success: VARCMP_LT, VARCMP_EQ or VARCMP_GT indicating that dblRight
+ * is less than, equal to or greater than pDecLeft respectively.
+ * Failure: DISP_E_OVERFLOW, if overflow occurs during the comparason
+ */
+HRESULT WINAPI VarDecCmpR8(const DECIMAL* pDecLeft, double dblRight)
+{
+ HRESULT hRet;
+ DECIMAL decRight;
+
+ hRet = VarDecFromR8(dblRight, &decRight);
+
+ if (SUCCEEDED(hRet))
+ hRet = VarDecCmp(pDecLeft, &decRight);
+
+ return hRet;
+}
diff -uP wine/dlls/oleaut32/i8.c wine-develop/dlls/oleaut32/i8.c
--- wine/dlls/oleaut32/i8.c 1970-01-01 01:00:00.000000000 +0100
+++ wine-develop/dlls/oleaut32/i8.c 2003-10-06 17:33:52.000000000 +0100
@@ -0,0 +1,662 @@
+/*
+ * Variant I8 and UI8 Functions
+ *
+ * Copyright 2003 Jon Griffiths
+ *
+ * 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 2.1 of the License, or (at your option) any later version.
+ *
+ * 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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#define NONAMELESSUNION
+#define NONAMELESSSTRUCT
+#include "wine/debug.h"
+#include "winbase.h"
+#include "variant.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(ole);
+
+/************************************************************************
+ * VarI8FromUI1 (OLEAUT32.333)
+ *
+ * Convert a VT_UI1 to a VT_I8.
+ *
+ * PARAMS
+ * bIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarI8FromUI1(BYTE bIn, LONG64* pi64Out)
+{
+ return _VarI8FromUI1(bIn, pi64Out);
+}
+
+
+/************************************************************************
+ * VarI8FromI2 (OLEAUT32.334)
+ *
+ * Convert a VT_I2 to a VT_I8.
+ *
+ * PARAMS
+ * sIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarI8FromI2(SHORT sIn, LONG64* pi64Out)
+{
+ return _VarI8FromI2(sIn, pi64Out);
+}
+
+/************************************************************************
+ * VarI8FromR4 (OLEAUT32.335)
+ *
+ * Convert a VT_R4 to a VT_I8.
+ *
+ * PARAMS
+ * fltIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source value is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarI8FromR4(FLOAT fltIn, LONG64* pi64Out)
+{
+ return _VarI8FromR4(fltIn, pi64Out);
+}
+
+/************************************************************************
+ * VarI8FromR8 (OLEAUT32.336)
+ *
+ * Convert a VT_R8 to a VT_I8.
+ *
+ * PARAMS
+ * dblIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source value is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ *
+ * NOTES
+ * Only values that fit into 63 bits are accepted. Due to rounding issues,
+ * very high or low values will not be accurately converted.
+ *
+ * Numbers are rounded using Dutch rounding, as follows:
+ *
+ *| Fractional Part Sign Direction Example
+ *| --------------- ---- --------- -------
+ *| < 0.5 + Down 0.4 -> 0.0
+ *| < 0.5 - Up -0.4 -> 0.0
+ *| > 0.5 + Up 0.6 -> 1.0
+ *| < 0.5 - Up -0.6 -> -1.0
+ *| = 0.5 + Up/Down Down if even, Up if odd
+ *| = 0.5 - Up/Down Up if even, Down if odd
+ *
+ * This system is often used in supermarkets.
+ */
+HRESULT WINAPI VarI8FromR8(double dblIn, LONG64* pi64Out)
+{
+ if ( dblIn < -4611686018427387904.0 || dblIn >= 4611686018427387904.0)
+ return DISP_E_OVERFLOW;
+ OLEAUT32_DutchRound(LONG64, dblIn, *pi64Out);
+ return S_OK;
+}
+
+/************************************************************************
+ * VarI8FromCy (OLEAUT32.337)
+ *
+ * Convert a VT_CY to a VT_I8.
+ *
+ * PARAMS
+ * cyIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ *
+ * NOTES
+ * All negative numbers are rounded down by 1, including those that are
+ * evenly divisible by 10000 (this is a Win32 bug). Positive numbers are
+ * rounded using Dutch rounding: See VarI8FromR8() for details.
+ */
+HRESULT WINAPI VarI8FromCy(CY cyIn, LONG64* pi64Out)
+{
+ *pi64Out = cyIn.int64 / CY_MULTIPLIER;
+
+ if (cyIn.int64 < 0)
+ (*pi64Out)--; /* Mimic Win32 bug */
+ else
+ {
+ cyIn.int64 -= *pi64Out * CY_MULTIPLIER; /* cyIn.s.Lo now holds fractional remainder */
+
+ if (cyIn.s.Lo > CY_HALF || (cyIn.s.Lo == CY_HALF && (*pi64Out & 0x1)))
+ (*pi64Out)++;
+ }
+ return S_OK;
+}
+
+/************************************************************************
+ * VarI8FromDate (OLEAUT32.338)
+ *
+ * Convert a VT_DATE to a VT_I8.
+ *
+ * PARAMS
+ * dateIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source value is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ * DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarI8FromDate(DATE dateIn, LONG64* pi64Out)
+{
+ return _VarI8FromDate(dateIn, pi64Out);
+}
+
+/************************************************************************
+ * VarI8FromStr (OLEAUT32.339)
+ *
+ * Convert a VT_BSTR to a VT_I8.
+ *
+ * PARAMS
+ * strIn [I] Source
+ * lcid [I] LCID for the conversion
+ * dwFlags [I] VAR_ flags from "oleauto.h"
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source value is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ * DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarI8FromStr(OLECHAR* strIn, LCID lcid, ULONG dwFlags, LONG64* pi64Out)
+{
+ return _VarI8FromStr(strIn, lcid, dwFlags, pi64Out);
+}
+
+/************************************************************************
+ * VarI8FromDisp (OLEAUT32.340)
+ *
+ * Convert a VT_DISPATCH to a VT_I8.
+ *
+ * PARAMS
+ * pdispIn [I] Source
+ * lcid [I] LCID for conversion
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source value is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ * DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarI8FromDisp(IDispatch* pdispIn, LCID lcid, LONG64* pi64Out)
+{
+ return _VarI8FromDisp(pdispIn, lcid, pi64Out);
+}
+
+/************************************************************************
+ * VarI8FromBool (OLEAUT32.341)
+ *
+ * Convert a VT_BOOL to a VT_I8.
+ *
+ * PARAMS
+ * boolIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarI8FromBool(VARIANT_BOOL boolIn, LONG64* pi64Out)
+{
+ return _VarI8FromBool(boolIn, pi64Out);
+}
+
+/************************************************************************
+ * VarI8FromI1 (OLEAUT32.342)
+ *
+ * Convert a VT_I1 to a VT_I8.
+ *
+ * PARAMS
+ * cIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarI8FromI1(signed char cIn, LONG64* pi64Out)
+{
+ return _VarI8FromI1(cIn, pi64Out);
+}
+
+/************************************************************************
+ * VarI8FromUI2 (OLEAUT32.343)
+ *
+ * Convert a VT_UI2 to a VT_I8.
+ *
+ * PARAMS
+ * usIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarI8FromUI2(USHORT usIn, LONG64* pi64Out)
+{
+ return _VarI8FromUI2(usIn, pi64Out);
+}
+
+/************************************************************************
+ * VarI8FromUI4 (OLEAUT32.344)
+ *
+ * Convert a VT_UI4 to a VT_I8.
+ *
+ * PARAMS
+ * ulIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarI8FromUI4(ULONG ulIn, LONG64* pi64Out)
+{
+ return _VarI8FromUI4(ulIn, pi64Out);
+}
+
+/************************************************************************
+ * VarI8FromDec (OLEAUT32.345)
+ *
+ * Convert a VT_DECIMAL to a VT_I8.
+ *
+ * PARAMS
+ * pDecIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source value is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarI8FromDec(DECIMAL *pdecIn, LONG64* pi64Out)
+{
+ if (!DEC_SCALE(pdecIn))
+ {
+ /* This decimal is just a 96 bit integer */
+ if (DEC_SIGN(pdecIn) & ~DECIMAL_NEG)
+ return E_INVALIDARG;
+
+ if (DEC_HI32(pdecIn) || DEC_MID32(pdecIn) & 0x80000000)
+ return DISP_E_OVERFLOW;
+
+ if (DEC_SIGN(pdecIn))
+ *pi64Out = -DEC_LO64(pdecIn);
+ else
+ *pi64Out = DEC_LO64(pdecIn);
+ return S_OK;
+ }
+ else
+ {
+ /* Decimal contains a floating point number */
+ HRESULT hRet;
+ double dbl;
+
+ hRet = _VarR8FromDec(pdecIn, &dbl);
+ if (SUCCEEDED(hRet))
+ hRet = VarI8FromR8(dbl, pi64Out);
+ return hRet;
+ }
+}
+
+/************************************************************************
+ * VarI8FromUI8 (OLEAUT32.427)
+ *
+ * Convert a VT_UI8 to a VT_I8.
+ *
+ * PARAMS
+ * ullIn [I] Source
+ * pi64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarI8FromUI8(ULONG64 ullIn, LONG64* pi64Out)
+{
+ return _VarI8FromUI8(ullIn, pi64Out);
+}
+
+/************************************************************************
+ * VarUI8FromI8 (OLEAUT32.428)
+ *
+ * Convert a VT_I8 to a VT_UI8.
+ *
+ * PARAMS
+ * ulIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarUI8FromI8(LONG64 llIn, ULONG64* pui64Out)
+{
+ return _VarUI8FromI8(llIn, pui64Out);
+}
+
+/************************************************************************
+ * VarUI8FromUI1 (OLEAUT32.429)
+ *
+ * Convert a VT_UI1 to a VT_UI8.
+ *
+ * PARAMS
+ * bIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarUI8FromUI1(BYTE bIn, ULONG64* pui64Out)
+{
+ return _VarUI8FromUI1(bIn, pui64Out);
+}
+
+/************************************************************************
+ * VarUI8FromI2 (OLEAUT32.430)
+ *
+ * Convert a VT_I2 to a VT_UI8.
+ *
+ * PARAMS
+ * sIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarUI8FromI2(SHORT sIn, ULONG64* pui64Out)
+{
+ return _VarUI8FromI2(sIn, pui64Out);
+}
+
+/************************************************************************
+ * VarUI8FromR4 (OLEAUT32.431)
+ *
+ * Convert a VT_R4 to a VT_UI8.
+ *
+ * PARAMS
+ * fltIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarUI8FromR4(FLOAT fltIn, ULONG64* pui64Out)
+{
+ return _VarUI8FromR4(fltIn, pui64Out);
+}
+
+/************************************************************************
+ * VarUI8FromR8 (OLEAUT32.432)
+ *
+ * Convert a VT_R8 to a VT_UI8.
+ *
+ * PARAMS
+ * dblIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source vale is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ *
+ * NOTES
+ * See VarI8FromR8() for details concerning rounding.
+ */
+HRESULT WINAPI VarUI8FromR8(double dblIn, ULONG64* pui64Out)
+{
+ if (dblIn < -0.5 || dblIn > 1.844674407370955e19)
+ return DISP_E_OVERFLOW;
+ OLEAUT32_DutchRound(ULONG64, dblIn, *pui64Out);
+ return S_OK;
+}
+
+/************************************************************************
+ * VarUI8FromCy (OLEAUT32.433)
+ *
+ * Convert a VT_CY to a VT_UI8.
+ *
+ * PARAMS
+ * cyIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source vale is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ *
+ * NOTES
+ * Negative values >= -5000 will be converted to 0.
+ */
+HRESULT WINAPI VarUI8FromCy(CY cyIn, ULONG64* pui64Out)
+{
+ if (cyIn.int64 < 0)
+ {
+ if (cyIn.int64 < -CY_HALF)
+ return DISP_E_OVERFLOW;
+ *pui64Out = 0;
+ }
+ else
+ {
+ *pui64Out = cyIn.int64 / CY_MULTIPLIER;
+
+ cyIn.int64 -= *pui64Out * CY_MULTIPLIER; /* cyIn.s.Lo now holds fractional remainder */
+
+ if (cyIn.s.Lo > CY_HALF || (cyIn.s.Lo == CY_HALF && (*pui64Out & 0x1)))
+ (*pui64Out)++;
+ }
+ return S_OK;
+}
+
+/************************************************************************
+ * VarUI8FromDate (OLEAUT32.434)
+ *
+ * Convert a VT_DATE to a VT_UI8.
+ *
+ * PARAMS
+ * dateIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source vale is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ * DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarUI8FromDate(DATE dateIn, ULONG64* pui64Out)
+{
+ return _VarUI8FromDate(dateIn, pui64Out);
+}
+
+/************************************************************************
+ * VarUI8FromStr (OLEAUT32.435)
+ *
+ * Convert a VT_BSTR to a VT_UI8.
+ *
+ * PARAMS
+ * strIn [I] Source
+ * lcid [I] LCID for the conversion
+ * dwFlags [I] VAR_ flags from "oleauto.h"
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source vale is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ * DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarUI8FromStr(OLECHAR* strIn, LCID lcid, ULONG dwFlags, ULONG64* pui64Out)
+{
+ return _VarUI8FromStr(strIn, lcid, dwFlags, pui64Out);
+}
+
+/************************************************************************
+ * VarUI8FromDisp (OLEAUT32.436)
+ *
+ * Convert a VT_DISPATCH to a VT_UI8.
+ *
+ * PARAMS
+ * pdispIn [I] Source
+ * lcid [I] LCID for conversion
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source vale is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ * DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarUI8FromDisp(IDispatch* pdispIn, LCID lcid, ULONG64* pui64Out)
+{
+ return _VarUI8FromDisp(pdispIn, lcid, pui64Out);
+}
+
+/************************************************************************
+ * VarUI8FromBool (OLEAUT32.437)
+ *
+ * Convert a VT_BOOL to a VT_UI8.
+ *
+ * PARAMS
+ * boolIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarUI8FromBool(VARIANT_BOOL boolIn, ULONG64* pui64Out)
+{
+ return _VarUI8FromBool(boolIn, pui64Out);
+}
+/************************************************************************
+ * VarUI8FromI1 (OLEAUT32.438)
+ *
+ * Convert a VT_I1 to a VT_UI8.
+ *
+ * PARAMS
+ * cIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: DISP_E_OVERFLOW, if the value will not fit in the destination
+ */
+HRESULT WINAPI VarUI8FromI1(signed char cIn, ULONG64* pui64Out)
+{
+ return _VarUI8FromI1(cIn, pui64Out);
+}
+
+/************************************************************************
+ * VarUI8FromUI2 (OLEAUT32.439)
+ *
+ * Convert a VT_UI2 to a VT_UI8.
+ *
+ * PARAMS
+ * usIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarUI8FromUI2(USHORT usIn, ULONG64* pui64Out)
+{
+ return _VarUI8FromUI2(usIn, pui64Out);
+}
+
+/************************************************************************
+ * VarUI8FromUI4 (OLEAUT32.440)
+ *
+ * Convert a VT_UI4 to a VT_UI8.
+ *
+ * PARAMS
+ * ulIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarUI8FromUI4(ULONG ulIn, ULONG64* pui64Out)
+{
+ return _VarUI8FromUI4(ulIn, pui64Out);
+}
+
+/************************************************************************
+ * VarUI8FromDec (OLEAUT32.441)
+ *
+ * Convert a VT_DECIMAL to a VT_UI8.
+ *
+ * PARAMS
+ * pDecIn [I] Source
+ * pui64Out [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source vale is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ *
+ * NOTES
+ * Under native Win32, if the source value has a scale of 0, its sign is
+ * ignored, i.e. this function takes the absolute value rather than fail
+ * with DISP_E_OVERFLOW. This is a bug and has been fixed in this
+ * implementation (use VarAbs() on pDecIn first if you want this behaviour).
+ */
+HRESULT WINAPI VarUI8FromDec(DECIMAL *pdecIn, ULONG64* pui64Out)
+{
+ if (!DEC_SCALE(pdecIn))
+ {
+ /* This decimal is just a 96 bit integer */
+ if (DEC_SIGN(pdecIn) & ~DECIMAL_NEG)
+ return E_INVALIDARG;
+
+ if (DEC_HI32(pdecIn))
+ return DISP_E_OVERFLOW;
+
+ if (DEC_SIGN(pdecIn))
+ {
+ WARN("Sign would be ignored under Win32!\n");
+ return DISP_E_OVERFLOW;
+ }
+
+ *pui64Out = DEC_LO64(pdecIn);
+ return S_OK;
+ }
+ else
+ {
+ /* Decimal contains a floating point number */
+ HRESULT hRet;
+ double dbl;
+
+ hRet = _VarR8FromDec(pdecIn, &dbl);
+ if (SUCCEEDED(hRet))
+ hRet = VarUI8FromR8(dbl, pui64Out);
+ return hRet;
+ }
+}
diff -uP wine/dlls/oleaut32/Makefile.in wine-develop/dlls/oleaut32/Makefile.in
--- wine/dlls/oleaut32/Makefile.in 2003-07-17 21:33:21.000000000 +0100
+++ wine-develop/dlls/oleaut32/Makefile.in 2003-10-06 17:38:40.000000000 +0100
@@ -17,12 +17,15 @@
C_SRCS = \
connpt.c \
dispatch.c \
+ dec.c \
hash.c \
+ i8.c \
oaidl_p.c \
oleaut.c \
olefont.c \
olepicture.c \
parsedt.c \
+ r8.c \
regsvr.c \
safearray.c \
stubs.c \
diff -uP wine/dlls/oleaut32/oleaut32.spec wine-develop/dlls/oleaut32/oleaut32.spec
--- wine/dlls/oleaut32/oleaut32.spec 2003-09-24 21:21:29.000000000 +0100
+++ wine-develop/dlls/oleaut32/oleaut32.spec 2003-10-06 17:59:46.000000000 +0100
@@ -82,7 +82,7 @@
82 stdcall VarR8FromCy(double ptr)
83 stdcall VarR8FromDate(double ptr)
84 stdcall VarR8FromStr(wstr long long ptr)
-85 stub VarR8FromDisp
+85 stdcall VarR8FromDisp(ptr long ptr)
86 stdcall VarR8FromBool(long ptr)
87 stdcall VarFormat(ptr ptr long long long ptr)
88 stdcall VarDateFromUI1(long ptr)
@@ -172,34 +172,34 @@
174 stdcall VarNot(ptr ptr)
175 stub VarRound # stdcall (ptr long ptr)
176 stdcall VarCmp(ptr ptr long long)
-177 stub VarDecAdd # stdcall (ptr ptr ptr)
-178 stub VarDecDiv # stdcall (ptr ptr ptr)
-179 stub VarDecMul # stdcall (ptr ptr ptr)
+177 stdcall VarDecAdd(ptr ptr ptr)
+178 stdcall VarDecDiv(ptr ptr ptr)
+179 stdcall VarDecMul(ptr ptr ptr)
180 stub CreateTypeLib2
-181 stub VarDecSub # stdcall (ptr ptr ptr)
-182 stub VarDecAbs # stdcall (ptr ptr)
+181 stdcall VarDecSub(ptr ptr ptr)
+182 stdcall VarDecAbs(ptr ptr)
183 stdcall LoadTypeLibEx (wstr long ptr)
184 stdcall SystemTimeToVariantTime(ptr ptr)
185 stdcall VariantTimeToSystemTime(double ptr)
186 stdcall UnRegisterTypeLib (ptr long long long long)
-187 stub VarDecFix # stdcall (ptr ptr)
-188 stub VarDecInt # stdcall (ptr ptr)
-189 stub VarDecNeg # stdcall (ptr ptr)
-190 stub VarDecFromUI1
-191 stub VarDecFromI2
-192 stub VarDecFromI4
-193 stub VarDecFromR4
-194 stub VarDecFromR8
-195 stub VarDecFromDate
-196 stub VarDecFromCy
+187 stdcall VarDecFix(ptr ptr)
+188 stdcall VarDecInt(ptr ptr)
+189 stdcall VarDecNeg(ptr ptr)
+190 stdcall VarDecFromUI1(long ptr)
+191 stdcall VarDecFromI2(long ptr)
+192 stdcall VarDecFromI4(long ptr)
+193 stdcall VarDecFromR4(long ptr)
+194 stdcall VarDecFromR8(double ptr)
+195 stdcall VarDecFromDate(double ptr)
+196 stdcall VarDecFromCy(long long ptr)
197 stdcall VarDecFromStr(wstr long long ptr)
-198 stub VarDecFromDisp
-199 stub VarDecFromBool
+198 stdcall VarDecFromDisp(ptr long ptr)
+199 stdcall VarDecFromBool(long ptr)
200 stdcall GetErrorInfo(long ptr) ole32.GetErrorInfo
201 stdcall SetErrorInfo(long ptr) ole32.SetErrorInfo
202 stdcall CreateErrorInfo(ptr) ole32.CreateErrorInfo
-203 stub VarDecRound # stdcall (ptr long ptr)
-204 stub VarDecCmp # stdcall (ptr ptr)
+203 stdcall VarDecRound(ptr long ptr)
+204 stdcall VarDecCmp(ptr ptr)
205 stdcall VarI2FromI1(long ptr)
206 stdcall VarI2FromUI2(long ptr)
207 stdcall VarI2FromUI4(long ptr)
@@ -215,7 +215,7 @@
217 stdcall VarR8FromI1(long ptr)
218 stdcall VarR8FromUI2(long ptr)
219 stdcall VarR8FromUI4(long ptr)
-220 stub VarR8FromDec
+220 stdcall VarR8FromDec(ptr ptr)
221 stdcall VarDateFromI1(long ptr)
222 stdcall VarDateFromUI2(long ptr)
223 stdcall VarDateFromUI4(long ptr)
@@ -236,9 +236,9 @@
238 stdcall VarUI1FromUI2(long ptr)
239 stdcall VarUI1FromUI4(long ptr)
240 stub VarUI1FromDec
-241 stub VarDecFromI1
-242 stub VarDecFromUI2
-243 stub VarDecFromUI4
+241 stdcall VarDecFromI1(long ptr)
+242 stdcall VarDecFromUI2(long ptr)
+243 stdcall VarDecFromUI4(long ptr)
244 stdcall VarI1FromUI1(long ptr)
245 stdcall VarI1FromI2(long ptr)
246 stdcall VarI1FromI4(long ptr)
@@ -293,7 +293,7 @@
295 stub LPSAFEARRAY_Size
296 stub LPSAFEARRAY_Marshal
297 stub LPSAFEARRAY_Unmarshal
-298 stub VarDecCmpR8 # stdcall (ptr double)
+298 stdcall VarDecCmpR8(ptr double)
299 stub VarCyAdd
303 stub VarCyMul
304 stdcall VarCyMulI4(double long ptr)
@@ -316,10 +316,50 @@
321 stdcall -private DllUnregisterServer() OLEAUT32_DllUnregisterServer
322 stub GetRecordInfoFromGuids # stdcall (ptr long long long ptr ptr)
323 stub GetRecordInfoFromTypeInfo # stdcall (ptr ptr)
+325 stub SetVarConversionLocaleSetting
+326 stub GetVarConversionLocaleSetting
327 stdcall SetOaNoCache()
+329 stub VarCyMulI8
330 stdcall VarDateFromUdate(ptr long ptr)
331 stdcall VarUdateFromDate(double long ptr)
332 stub GetAltMonthNames
+333 stdcall VarI8FromUI1(long long)
+334 stdcall VarI8FromI2(long long)
+335 stdcall VarI8FromR4(long long)
+336 stdcall VarI8FromR8(double long)
+337 stdcall VarI8FromCy(long long ptr)
+338 stdcall VarI8FromDate(double long)
+339 stdcall VarI8FromStr(wstr long long ptr)
+340 stdcall VarI8FromDisp(ptr long ptr)
+341 stdcall VarI8FromBool(long long)
+342 stdcall VarI8FromI1(long long)
+343 stdcall VarI8FromUI2(long long)
+344 stdcall VarI8FromUI4(long long)
+345 stdcall VarI8FromDec(ptr ptr)
+346 stub VarI2FromI8
+347 stub VarI2FromUI8
+348 stub VarI4FromI8
+349 stub VarI4FromUI8
+360 stub VarR4FromI8
+361 stub VarR4FromUI8
+362 stdcall VarR8FromI8(long long ptr)
+363 stdcall VarR8FromUI8(long long ptr)
+364 stub VarDateFromI8
+365 stub VarDateFromUI8
+366 stub VarCyFromI8
+367 stub VarCyFromUI8
+368 stub VarBstrFromI8
+369 stub VarBstrFromUI8
+370 stub VarBoolFromI8
+371 stub VarBoolFromUI8
+372 stub VarUI1FromI8
+373 stub VarUI1FromUI8
+374 stub VarDecFromI8
+375 stub VarDecFromUI8
+376 stub VarI1FromI8
+377 stub VarI1FromUI8
+378 stub VarUI2FromI8
+379 stub VarUI2FromUI8
380 stub UserHWND_from_local
381 stub UserHWND_to_local
382 stub UserHWND_free_inst
@@ -357,3 +397,20 @@
422 stub OleLoadPictureFile
423 stub OleSavePictureFile
424 stub OleLoadPicturePath
+425 stub VarUI4FromI8
+426 stub VarUI4FromUI8
+427 stdcall VarI8FromUI8(long long ptr)
+428 stdcall VarUI8FromI8(long long ptr)
+429 stdcall VarUI8FromUI1(long ptr)
+430 stdcall VarUI8FromI2(long ptr)
+431 stdcall VarUI8FromR4(long ptr)
+432 stdcall VarUI8FromR8(double ptr)
+433 stdcall VarUI8FromCy(long long ptr)
+434 stdcall VarUI8FromDate(double ptr)
+435 stdcall VarUI8FromStr(wstr long long ptr)
+436 stdcall VarUI8FromDisp(ptr long ptr)
+437 stdcall VarUI8FromBool(long ptr)
+438 stdcall VarUI8FromI1(long ptr)
+439 stdcall VarUI8FromUI2(long ptr)
+440 stdcall VarUI8FromUI4(long ptr)
+441 stdcall VarUI8FromDec(long ptr)
diff -uP wine/dlls/oleaut32/r8.c wine-develop/dlls/oleaut32/r8.c
--- wine/dlls/oleaut32/r8.c 1970-01-01 01:00:00.000000000 +0100
+++ wine-develop/dlls/oleaut32/r8.c 2003-10-06 17:39:14.000000000 +0100
@@ -0,0 +1,318 @@
+/*
+ * Variant VT_R8 (double) Functions
+ *
+ * Copyright 2003 Jon Griffiths
+ *
+ * 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 2.1 of the License, or (at your option) any later version.
+ *
+ * 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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#define NONAMELESSUNION
+#define NONAMELESSSTRUCT
+#include "wine/debug.h"
+#include "winbase.h"
+#include "variant.h"
+
+/************************************************************************
+ * VarR8FromUI1 (OLEAUT32.78)
+ *
+ * Convert a VT_UI1 to a VT_R8.
+ *
+ * PARAMS
+ * bIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarR8FromUI1(BYTE bIn, double *pDblOut)
+{
+ return _VarR8FromUI1(bIn, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromI2 (OLEAUT32.79)
+ *
+ * Convert a VT_I2 to a VT_R8.
+ *
+ * PARAMS
+ * sIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarR8FromI2(SHORT sIn, double *pDblOut)
+{
+ return _VarR8FromI2(sIn, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromI4 (OLEAUT32.80)
+ *
+ * Convert a VT_I4 to a VT_R8.
+ *
+ * PARAMS
+ * sIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarR8FromI4(LONG lIn, double *pDblOut)
+{
+ return _VarR8FromI4(lIn, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromR4 (OLEAUT32.81)
+ *
+ * Convert a VT_R4 to a VT_R8.
+ *
+ * PARAMS
+ * fltIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarR8FromR4(FLOAT fltIn, double *pDblOut)
+{
+ return _VarR8FromR4(fltIn, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromCy (OLEAUT32.82)
+ *
+ * Convert a VT_CY to a VT_R8.
+ *
+ * PARAMS
+ * cyIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarR8FromCy(CY cyIn, double *pDblOut)
+{
+ return _VarR8FromCy(cyIn, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromDate (OLEAUT32.83)
+ *
+ * Convert a VT_DATE to a VT_R8.
+ *
+ * PARAMS
+ * dateIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarR8FromDate(DATE dateIn, double *pDblOut)
+{
+ return _VarR8FromDate(dateIn, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromStr (OLEAUT32.84)
+ *
+ * Convert a VT_BSTR to a VT_R8.
+ *
+ * PARAMS
+ * strIn [I] Source
+ * lcid [I] LCID for the conversion
+ * dwFlags [I] VAR_ flags from "oleauto.h"
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if strIn or pDblOut is invalid.
+ * DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarR8FromStr(OLECHAR* strIn, LCID lcid, ULONG dwFlags, double *pDblOut)
+{
+ return _VarR8FromStr(strIn, lcid, dwFlags, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromDisp (OLEAUT32.85)
+ *
+ * Convert a VT_DISPATCH to a VT_R8.
+ *
+ * PARAMS
+ * pdispIn [I] Source
+ * lcid [I] LCID for conversion
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source value is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ * DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarR8FromDisp(IDispatch* pdispIn, LCID lcid, double *pDblOut)
+{
+ return _VarR8FromDisp(pdispIn, lcid, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromBool (OLEAUT32.86)
+ *
+ * Convert a VT_BOOL to a VT_R8.
+ *
+ * PARAMS
+ * boolIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarR8FromBool(VARIANT_BOOL boolIn, double *pDblOut)
+{
+ return _VarR8FromBool(boolIn, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromI1 (OLEAUT32.217)
+ *
+ * Convert a VT_I1 to a VT_R8.
+ *
+ * PARAMS
+ * cIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source value is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ * DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarR8FromI1(signed char cIn, double *pDblOut)
+{
+ return _VarR8FromI1(cIn, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromUI2 (OLEAUT32.218)
+ *
+ * Convert a VT_UI2 to a VT_R8.
+ *
+ * PARAMS
+ * usIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source value is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ * DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarR8FromUI2(USHORT usIn, double *pDblOut)
+{
+ return _VarR8FromUI2(usIn, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromUI4 (OLEAUT32.219)
+ *
+ * Convert a VT_UI4 to a VT_R8.
+ *
+ * PARAMS
+ * ulIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source value is invalid
+ * DISP_E_OVERFLOW, if the value will not fit in the destination
+ * DISP_E_TYPEMISMATCH, if the type cannot be converted
+ */
+HRESULT WINAPI VarR8FromUI4(ULONG ulIn, double *pDblOut)
+{
+ return _VarR8FromUI4(ulIn, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromDec (OLEAUT32.220)
+ *
+ * Convert a VT_DECIMAL to a VT_R8.
+ *
+ * PARAMS
+ * pDecIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * Success: S_OK.
+ * Failure: E_INVALIDARG, if the source value is invalid.
+ */
+HRESULT WINAPI VarR8FromDec(DECIMAL* pDecIn, double *pDblOut)
+{
+ BYTE scale = DEC_SCALE(pDecIn);
+ double divisor = 1.0, highPart;
+
+ if (scale > DEC_MAX_SCALE || DEC_SIGN(pDecIn) & ~DECIMAL_NEG)
+ return E_INVALIDARG;
+
+ while (scale--)
+ divisor *= 10;
+
+ if (DEC_SIGN(pDecIn))
+ divisor = -divisor;
+
+ if (DEC_HI32(pDecIn))
+ {
+ highPart = (double)DEC_HI32(pDecIn) / divisor;
+ highPart *= 1.0e64;
+ }
+ else
+ highPart = 0.0;
+
+ *pDblOut = (double)DEC_LO64(pDecIn) / divisor + highPart;
+ return S_OK;
+}
+
+/************************************************************************
+ * VarR8FromI8 (OLEAUT32.362)
+ *
+ * Convert a VT_I8 to a VT_R8.
+ *
+ * PARAMS
+ * ullIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarR8FromI8(LONG64 llIn, double *pDblOut)
+{
+ return _VarR8FromI8(llIn, pDblOut);
+}
+
+/************************************************************************
+ * VarR8FromUI8 (OLEAUT32.363)
+ *
+ * Convert a VT_UI8 to a VT_R8.
+ *
+ * PARAMS
+ * ullIn [I] Source
+ * pDblOut [O] Destination
+ *
+ * RETURNS
+ * S_OK.
+ */
+HRESULT WINAPI VarR8FromUI8(ULONG64 ullIn, double *pDblOut)
+{
+ return _VarR8FromUI8(ullIn, pDblOut);
+}
diff -uP wine/dlls/oleaut32/variant.c wine-develop/dlls/oleaut32/variant.c
--- wine/dlls/oleaut32/variant.c 2003-10-06 13:03:24.000000000 +0100
+++ wine-develop/dlls/oleaut32/variant.c 2003-10-06 17:39:57.000000000 +0100
@@ -2844,133 +2844,6 @@
}
/******************************************************************************
- * VarR8FromUI1 [OLEAUT32.78]
- */
-HRESULT WINAPI VarR8FromUI1(BYTE bIn, double* pdblOut)
-{
- TRACE("( %d, %p ), stub\n", bIn, pdblOut );
-
- *pdblOut = (double) bIn;
-
- return S_OK;
-}
-
-/******************************************************************************
- * VarR8FromI2 [OLEAUT32.79]
- */
-HRESULT WINAPI VarR8FromI2(short sIn, double* pdblOut)
-{
- TRACE("( %d, %p ), stub\n", sIn, pdblOut );
-
- *pdblOut = (double) sIn;
-
- return S_OK;
-}
-
-/******************************************************************************
- * VarR8FromI4 [OLEAUT32.80]
- */
-HRESULT WINAPI VarR8FromI4(LONG lIn, double* pdblOut)
-{
- TRACE("( %ld, %p ), stub\n", lIn, pdblOut );
-
- *pdblOut = (double) lIn;
-
- return S_OK;
-}
-
-/******************************************************************************
- * VarR8FromR4 [OLEAUT32.81]
- */
-HRESULT WINAPI VarR8FromR4(FLOAT fltIn, double* pdblOut)
-{
- TRACE("( %f, %p ), stub\n", fltIn, pdblOut );
-
- *pdblOut = (double) fltIn;
-
- return S_OK;
-}
-
-/******************************************************************************
- * VarR8FromDate [OLEAUT32.83]
- */
-HRESULT WINAPI VarR8FromDate(DATE dateIn, double* pdblOut)
-{
- TRACE("( %f, %p ), stub\n", dateIn, pdblOut );
-
- *pdblOut = (double) dateIn;
-
- return S_OK;
-}
-
-/******************************************************************************
- * VarR8FromBool [OLEAUT32.86]
- */
-HRESULT WINAPI VarR8FromBool(VARIANT_BOOL boolIn, double* pdblOut)
-{
- TRACE("( %d, %p ), stub\n", boolIn, pdblOut );
-
- *pdblOut = (double) boolIn;
-
- return S_OK;
-}
-
-/******************************************************************************
- * VarR8FromI1 [OLEAUT32.217]
- */
-HRESULT WINAPI VarR8FromI1(signed char cIn, double* pdblOut)
-{
- TRACE("( %c, %p ), stub\n", cIn, pdblOut );
-
- *pdblOut = (double) cIn;
-
- return S_OK;
-}
-
-/******************************************************************************
- * VarR8FromUI2 [OLEAUT32.218]
- */
-HRESULT WINAPI VarR8FromUI2(USHORT uiIn, double* pdblOut)
-{
- TRACE("( %d, %p ), stub\n", uiIn, pdblOut );
-
- *pdblOut = (double) uiIn;
-
- return S_OK;
-}
-
-/******************************************************************************
- * VarR8FromUI4 [OLEAUT32.219]
- */
-HRESULT WINAPI VarR8FromUI4(ULONG ulIn, double* pdblOut)
-{
- TRACE("( %ld, %p ), stub\n", ulIn, pdblOut );
-
- *pdblOut = (double) ulIn;
-
- return S_OK;
-}
-
-/******************************************************************************
- * VarR8FromStr [OLEAUT32.84]
- */
-HRESULT WINAPI VarR8FromStr(OLECHAR* strIn, LCID lcid, ULONG dwFlags, double* pdblOut)
-{
- TRACE("(%s, 0x%08lx, 0x%08lx, %p)\n", debugstr_w(strIn), lcid, dwFlags, pdblOut);
- return _VarR8FromStr(strIn, lcid, dwFlags, pdblOut);
-}
-
-/**********************************************************************
- * VarR8FromCy [OLEAUT32.82]
- * Convert currency to double
- */
-HRESULT WINAPI VarR8FromCy(CY cyIn, double* pdblOut) {
- *pdblOut = (double)((((double)cyIn.s.Hi * 4294967296.0) + (double)cyIn.s.Lo) / 10000);
- TRACE("%lu %ld -> %f\n", cyIn.s.Hi, cyIn.s.Lo, *pdblOut);
- return S_OK;
-}
-
-/******************************************************************************
* VarDateFromUI1 [OLEAUT32.88]
*/
HRESULT WINAPI VarDateFromUI1(BYTE bIn, DATE* pdateOut)
@@ -4166,52 +4039,6 @@
}
/**********************************************************************
- * VarDecFromStr [OLEAUT32.@]
- */
-HRESULT WINAPI VarDecFromStr(OLECHAR* strIn, LCID lcid, ULONG dwFlags,
- DECIMAL* pdecOut)
-{ WCHAR *p=strIn;
- ULONGLONG t;
- ULONG cy;
-
- DECIMAL_SETZERO(pdecOut);
-
- if(*p == (WCHAR)'-')pdecOut->u.s.sign= DECIMAL_NEG;
- if((*p == (WCHAR)'-') || (*p == (WCHAR)'+')) p++;
- for(;*p != (WCHAR)0; p++) {
- if((*p < (WCHAR)'0')||(*p > (WCHAR)'9')) goto error ;
- t = (ULONGLONG)pdecOut->u1.s1.Lo32 *(ULONGLONG)10
- + (ULONGLONG)(*p -(WCHAR)'0');
- cy = (ULONG)(t >> 32);
- pdecOut->u1.s1.Lo32 = (ULONG)(t & (ULONGLONG)UI4_MAX);
- t = (ULONGLONG)pdecOut->u1.s1.Mid32 * (ULONGLONG)10
- + (ULONGLONG)cy;
- cy = (ULONG)(t >> 32);
- pdecOut->u1.s1.Mid32 = (ULONG)(t & (ULONGLONG)UI4_MAX);
- t = (ULONGLONG)pdecOut->Hi32 * (ULONGLONG)10
- + (ULONGLONG)cy;
- cy = (ULONG)(t >> 32);
- pdecOut->Hi32 = (ULONG)(t & (ULONGLONG)UI4_MAX);
- if(cy) goto overflow ;
- }
- TRACE("%s -> sign %02x,hi %08lx,mid %08lx, lo%08lx, scale %08x\n",
- debugstr_w(strIn),
- pdecOut->u.s.sign, pdecOut->Hi32, pdecOut->u1.s1.Mid32,
- pdecOut->u1.s1.Lo32, pdecOut->u.s.scale);
- return S_OK;
-
-overflow:
- /* like NT4 SP5 */
- pdecOut->Hi32 = pdecOut->u1.s1.Mid32 = pdecOut->u1.s1.Lo32 = 0xffffffff;
- return DISP_E_OVERFLOW;
-
-error:
- ERR("%s: unknown char at pos %d\n",
- debugstr_w(strIn), p - strIn + 1);
- return DISP_E_TYPEMISMATCH;
-}
-
-/**********************************************************************
* DosDateTimeToVariantTime [OLEAUT32.14]
* Convert dos representation of time to the date and time representation
* stored in a variant.