oleaut32 header/dates

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Cheers,
Jon

License: X11

ChangeLog:

  Jon Griffiths <jon_p_griffiths@xxxxxxxxx>

  +include/oleauto.h
    Add some missing prototype/defines.

  +dlls/oleaut32/oleaut.c
    OaBuildVersion() returns a ULONG, not UINT

 +dlls/oleaut32/variant.c
    Implement the non-variant date conversions correctly, without
going
    through 'struct tm' first. Handle negative & 'rolling' dates too.


__________________________________
Do you Yahoo!?
Protect your identity with Yahoo! Mail AddressGuard
http://antispam.yahoo.com/whatsnewfree
--- wine/include/oleauto.h	2003-09-11 16:11:34.000000000 +0000
+++ wine-develop/include/oleauto.h	2003-11-14 22:29:28.000000000 +0000
@@ -27,10 +27,17 @@
 
 DEFINE_OLEGUID(IID_StdOle, 0x00020430,0,0);
 
-/*
- * BSTR API
- */
+#define STDOLE_MAJORVERNUM  1
+#define STDOLE_MINORVERNUM  0
+#define STDOLE_LCID         0
+
+#define STDOLE2_MAJORVERNUM 2
+#define STDOLE2_MINORVERNUM 0
+#define STDOLE2_LCID        0
+
+ULONG WINAPI OaBuildVersion(void);
 
+/* BSTR functions */
 BSTR WINAPI SysAllocString(const OLECHAR*);
 BSTR WINAPI SysAllocStringByteLen(LPCSTR,UINT);
 BSTR WINAPI SysAllocStringLen(const OLECHAR*,UINT);
@@ -40,19 +47,12 @@
 int  WINAPI SysStringByteLen(BSTR);
 int  WINAPI SysStringLen(BSTR);
 
-
-/*****************************************************************
- *  ErrorInfo API
- */
-
+/* IErrorInfo helpers */
 HRESULT WINAPI SetErrorInfo(ULONG,IErrorInfo*);
 HRESULT WINAPI GetErrorInfo(ULONG,IErrorInfo**);
 HRESULT WINAPI CreateErrorInfo(ICreateErrorInfo**);
 
-/*****************************************************************
- *  SafeArray API
- */
-
+/* SafeArray functions */
 SAFEARRAY* WINAPI SafeArrayCreate(VARTYPE,UINT,SAFEARRAYBOUND*);
 SAFEARRAY* WINAPI SafeArrayCreateEx(VARTYPE,UINT,SAFEARRAYBOUND*,LPVOID);
 SAFEARRAY* WINAPI SafeArrayCreateVector(VARTYPE,LONG,ULONG);
@@ -84,73 +84,101 @@
 HRESULT WINAPI SafeArraySetIID(SAFEARRAY*,REFGUID);
 HRESULT WINAPI SafeArrayGetIID(SAFEARRAY*,GUID*);
 
-/* These are macros that help accessing the VARIANT date type.
+HRESULT WINAPI VectorFromBstr(BSTR,SAFEARRAY**);
+HRESULT WINAPI BstrFromVector(SAFEARRAY*,BSTR*);
+
+/* Object registration helpers */
+#define ACTIVEOBJECT_STRONG 0
+#define ACTIVEOBJECT_WEAK   1
+
+HRESULT WINAPI RegisterActiveObject(LPUNKNOWN,REFCLSID,DWORD,LPDWORD);
+HRESULT WINAPI RevokeActiveObject(DWORD,LPVOID);
+HRESULT WINAPI GetActiveObject(REFCLSID,LPVOID,LPUNKNOWN*);
+
+/* IRecordInfo helpers */
+HRESULT WINAPI GetRecordInfoFromTypeInfo(ITypeInfo*,IRecordInfo**);
+HRESULT WINAPI GetRecordInfoFromGuids(REFGUID,ULONG,ULONG,LCID,REFGUID,IRecordInfo**);
+
+/*
+ * Variants
  */
+
+/* Macros for accessing the fields of the VARIANT type */
 #if (__STDC__ && !defined(_FORCENAMELESSUNION)) || defined(NONAMELESSUNION)
-#define V_UNION(A, B)	((A)->n1.n2.n3.B)
-#define V_VT(A) 		((A)->n1.n2.vt)
+#define V_UNION(A,B) ((A)->n1.n2.n3.B)
+#define V_VT(A)      ((A)->n1.n2.vt)
 #else
-#define V_UNION(A, B)	((A)->B)
-#define V_VT(A) 		((A)->vt)
-#endif /* cplusplus */
+#define V_UNION(A,B) ((A)->B)
+#define V_VT(A)      ((A)->vt)
+#endif
 
-#define V_ISBYREF(A)	 (V_VT(A)&VT_BYREF)
-#define V_ISARRAY(A)	 (V_VT(A)&VT_ARRAY)
-#define V_ISVECTOR(A)	 (V_VT(A)&VT_VECTOR)
-#define V_NONE(A)		 V_I2(A)
+#define V_ISBYREF(A)  (V_VT(A) & VT_BYREF)
+#define V_ISARRAY(A)  (V_VT(A) & VT_ARRAY)
+#define V_ISVECTOR(A) (V_VT(A) & VT_VECTOR)
+#define V_NONE(A)     V_I2(A)
 
-#define V_UI1(A)		 V_UNION(A, bVal)
-#define V_UI1REF(A) 	 V_UNION(A, pbVal)
-#define V_I2(A) 		 V_UNION(A, iVal)
-#define V_I2REF(A)		 V_UNION(A, piVal)
-#define V_I4(A) 		 V_UNION(A, lVal)
-#define V_I4REF(A)		 V_UNION(A, plVal)
-#define V_R4(A) 		 V_UNION(A, fltVal)
-#define V_R4REF(A)		 V_UNION(A, pfltVal)
-#define V_R8(A) 		 V_UNION(A, dblVal)
-#define V_R8REF(A)		 V_UNION(A, pdblVal)
-#define V_I1(A) 		 V_UNION(A, cVal)
-#define V_I1REF(A)		 V_UNION(A, pcVal)
-#define V_UI2(A)		 V_UNION(A, uiVal)
-#define V_UI2REF(A) 	 V_UNION(A, puiVal)
-#define V_UI4(A)		 V_UNION(A, ulVal)
-#define V_UI4REF(A) 	 V_UNION(A, pulVal)
-#define V_INT(A)		 V_UNION(A, intVal)
-#define V_INTREF(A) 	 V_UNION(A, pintVal)
-#define V_UINT(A)		 V_UNION(A, uintVal)
-#define V_UINTREF(A)	 V_UNION(A, puintVal)
-#define V_I8(A)		 V_UNION(A, llVal)
-#define V_I8REF(A) 	 V_UNION(A, pllVal)
-#define V_UI8(A)		 V_UNION(A, ullVal)
-#define V_UI8REF(A)	 V_UNION(A, pullVal)
-#define V_CY(A) 		 V_UNION(A, cyVal)
-#define V_CYREF(A)		 V_UNION(A, pcyVal)
-#define V_DATE(A)		 V_UNION(A, date)
-#define V_DATEREF(A)	 V_UNION(A, pdate)
-#define V_BSTR(A)		 V_UNION(A, bstrVal)
-#define V_BSTRREF(A)	 V_UNION(A, pbstrVal)
-#define V_DISPATCH(A)	 V_UNION(A, pdispVal)
-#define V_DISPATCHREF(A) V_UNION(A, ppdispVal)
-#define V_ERROR(A)		 V_UNION(A, scode)
-#define V_ERRORREF(A)	 V_UNION(A, pscode)
-#define V_BOOL(A)		 V_UNION(A, boolVal)
-#define V_BOOLREF(A)	 V_UNION(A, pboolVal)
-#define V_UNKNOWN(A)	 V_UNION(A, punkVal)
-#define V_UNKNOWNREF(A)  V_UNION(A, ppunkVal)
-#define V_VARIANTREF(A)  V_UNION(A, pvarVal)
-#define V_ARRAY(A)		 V_UNION(A, parray)
-#define V_ARRAYREF(A)	 V_UNION(A, pparray)
-#define V_BYREF(A)		 V_UNION(A, byref)
-#define V_DECIMALREF(A)  V_UNION(A, pdecVal)
+#define V_ARRAY(A)       V_UNION(A,parray)
+#define V_ARRAYREF(A)    V_UNION(A,pparray)
+#define V_BOOL(A)        V_UNION(A,boolVal)
+#define V_BOOLREF(A)     V_UNION(A,pboolVal)
+#define V_BSTR(A)        V_UNION(A,bstrVal)
+#define V_BSTRREF(A)     V_UNION(A,pbstrVal)
+#define V_BYREF(A)       V_UNION(A,byref)
+#define V_CY(A)          V_UNION(A,cyVal)
+#define V_CYREF(A)       V_UNION(A,pcyVal)
+#define V_DATE(A)        V_UNION(A,date)
+#define V_DATEREF(A)     V_UNION(A,pdate)
 #if (__STDC__ && !defined(_FORCENAMELESSUNION)) || defined(NONAMELESSUNION)
-#define V_DECIMAL(A)    ((A)->n1.decVal)
+#define V_DECIMAL(A)     ((A)->n1.decVal)
 #else
-#define V_DECIMAL(A)    ((A)->decVal)
+#define V_DECIMAL(A)     ((A)->decVal)
 #endif
-
-/*
- * VARIANT API
- */
+#define V_DECIMALREF(A)  V_UNION(A,pdecVal)
+#define V_DISPATCH(A)    V_UNION(A,pdispVal)
+#define V_DISPATCHREF(A) V_UNION(A,ppdispVal)
+#define V_ERROR(A)       V_UNION(A,scode)
+#define V_ERRORREF(A)    V_UNION(A,pscode)
+#define V_I1(A)          V_UNION(A,cVal)
+#define V_I1REF(A)       V_UNION(A,pcVal)
+#define V_I2(A)          V_UNION(A,iVal)
+#define V_I2REF(A)       V_UNION(A,piVal)
+#define V_I4(A)          V_UNION(A,lVal)
+#define V_I4REF(A)       V_UNION(A,plVal)
+#define V_I8(A)          V_UNION(A,llVal)
+#define V_I8REF(A)       V_UNION(A,pllVal)
+#define V_INT(A)         V_UNION(A,intVal)
+#define V_INTREF(A)      V_UNION(A,pintVal)
+#ifdef _WIN64
+#define V_INT_PTR(A)     V_I8(A)
+#define V_INT_PTRREF(A)  V_I8REF(A)
+#else
+#define V_INT_PTR(A)     V_I4(A)
+#define V_INT_PTRREF(A)  V_I4REF(A)
+#endif
+#define V_R4(A)          V_UNION(A,fltVal)
+#define V_R4REF(A)       V_UNION(A,pfltVal)
+#define V_R8(A)          V_UNION(A,dblVal)
+#define V_R8REF(A)       V_UNION(A,pdblVal)
+#define V_UINT(A)        V_UNION(A,uintVal)
+#define V_UINTREF(A)     V_UNION(A,puintVal)
+#define V_UI1(A)         V_UNION(A,bVal)
+#define V_UI1REF(A)      V_UNION(A,pbVal)
+#define V_UI2(A)         V_UNION(A,uiVal)
+#define V_UI2REF(A)      V_UNION(A,puiVal)
+#define V_UI4(A)         V_UNION(A,ulVal)
+#define V_UI4REF(A)      V_UNION(A,pulVal)
+#define V_UI8(A)         V_UNION(A,ullVal)
+#define V_UI8REF(A)      V_UNION(A,pullVal)
+#ifdef _WIN64
+#define V_UINT_PTR(A)    V_UI8(A)
+#define V_UINT_PTRREF(A) V_UI8REF(A)
+#else
+#define V_UINT_PTR(A)    V_UI4(A)
+#define V_UINT_PTRREF(A) V_UI4REF(A)
+#endif
+#define V_UNKNOWN(A)     V_UNION(A,punkVal)
+#define V_UNKNOWNREF(A)  V_UNION(A,ppunkVal)
+#define V_VARIANTREF(A)  V_UNION(A,pvarVal)
 
 void    WINAPI VariantInit(VARIANT*);
 HRESULT WINAPI VariantClear(VARIANT*);
@@ -159,62 +187,40 @@
 HRESULT WINAPI VariantChangeType(VARIANT*,VARIANT*,USHORT,VARTYPE);
 HRESULT WINAPI VariantChangeTypeEx(VARIANT*,VARIANT*,LCID,USHORT,VARTYPE);
 
-/*
- * These flags are used for the VariantChangeType and VariantChangeTypeEx APIs.
- */
-
-/*
- * This one is of general use.
- */
-#define VARIANT_NOVALUEPROP    0x1
-/*
- * This one is used for conversions of VT_BOOL to VT_BSTR,
- * the API will convert to "True"|"False" instead of "-1"|"0".
- */
-#define VARIANT_ALPHABOOL      0x2
-/*
- * This one is used for conversions to or from a VT_BSTR string,
- * it passes LOCALE_NOUSEROVERRIDE to the core (low-level) coercion routines.
- * This means it will use the system default locale settings instead of custom
- * local settings.
- */
-#define VARIANT_NOUSEROVERRIDE 0x4
-
-/*
- * This one is used for conversions of VT_BOOL to VT_BSTR,
- * Convert to the localised text of "True"|"False" instead of "-1"|"0".
- */
-#define VARIANT_LOCALBOOL      0x10
-
-/*
- * Alternate calendar support.
- */
-#define VARIANT_CALENDAR_HIJRI 0x08
-#define VARIANT_CALENDAR_THAI  0x20
-#define VARIANT_CALENDAR_GREGORIAN 0x40
+/* VariantChangeType/VariantChangeTypeEx flags */
+#define VARIANT_NOVALUEPROP        0x01 /* Don't get the default value property from IDispatch */
+#define VARIANT_ALPHABOOL          0x02 /* Coerce to "True"|"False" instead of "-1"|"0" */
+#define VARIANT_NOUSEROVERRIDE     0x04 /* Pass LOCALE_NOUSEROVERRIDE to low level conversions */
+#define VARIANT_CALENDAR_HIJRI     0x08 /* Use the Hijri calendar */
+#define VARIANT_LOCALBOOL          0x10 /* Like VARIANT_ALPHABOOL, but use localised text */
+#define VARIANT_CALENDAR_THAI      0x20 /* Use the Thai buddhist calendar */
+#define VARIANT_CALENDAR_GREGORIAN 0x40 /* Use the Gregorian calendar */
+#define VARIANT_USE_NLS            0x80 /* Format result using NLS calls */
 
 /*
- * Use NLS calls in conversion
+ * Low level Variant coercion functions
  */
-#define VARIANT_USE_NLS        0x80
 
-/*
- * Convert between SafeArray vectors and BSTR's
- */
-HRESULT WINAPI VectorFromBstr(BSTR,SAFEARRAY**);
-HRESULT WINAPI BstrFromVector(SAFEARRAY*,BSTR*);
+#define VT_HARDTYPE VT_RESERVED /* Don't coerce this variant when comparing it to others */
 
-/*
- * VARTYPE Coercion API
- */
+/* Flags for low level coercions. LOCALE_ flags can also be passed */
+#define VAR_TIMEVALUEONLY       0x001 /* Ignore date portion of VT_DATE */
+#define VAR_DATEVALUEONLY       0x002 /* Ignore time portion of VT_DATE */
+#define VAR_VALIDDATE           0x004
+#define VAR_CALENDAR_HIJRI      0x008 /* Use the Hijri calender */
+#define VAR_LOCALBOOL           0x010 /* VT_BOOL<->VT_BSTR: Use localised boolean text */
+#define VAR_FORMAT_NOSUBSTITUTE 0x020 /* Don't change format strings for un-coercable types */
+#define VAR_FOURDIGITYEARS      0x040 /* Always print years with 4 digits */
+#define VAR_CALENDAR_THAI       0x080 /* Use the Thai buddhist calendar */
+#define VAR_CALENDAR_GREGORIAN  0x100 /* Use the Gregorian calendar */
 
-/* Omits the date portion and return only the time value.
- */
-#define VAR_TIMEVALUEONLY	((DWORD)0x00000001)
-/* Omits the time portion and return only the date value.
- */
-#define VAR_DATEVALUEONLY	((DWORD)0x00000002)
+#ifndef LOCALE_USE_NLS
+/* This is missing from native winnls.h, but may be added at some point */
+#define LOCALE_USE_NLS          0x10000000
+#endif
 
+#define VTDATEGRE_MIN -657434 /* Minimum possible Gregorian date: 1/1/100 */
+#define VTDATEGRE_MAX 2958465 /* Maximum possible Gregorian date: 31/12/9999 */
 
 HRESULT WINAPI VarUI1FromI2(SHORT,BYTE*);
 HRESULT WINAPI VarUI1FromI4(LONG,BYTE*);
@@ -462,70 +468,70 @@
 #define VarUI4FromUI4( in,pOut ) ( *(pOut) =  (in) )
 #define VarI4FromI4( in,pOut )   ( *(pOut) =  (in) )
 
-#define VarUI1FromInt		VarUI1FromI4
-#define VarUI1FromUint	VarUI1FromUI4
-#define VarI2FromInt		VarI2FromI4
-#define VarI2FromUint		VarI2FromUI4
-#define VarI4FromInt		VarI4FromI4
-#define VarI4FromUint		VarI4FromUI4
-#define VarI8FromInt		VarI8FromI4
-#define VarI8FromUint		VarI8FromUI4
-#define VarR4FromInt		VarR4FromI4
-#define VarR4FromUint		VarR4FromUI4
-#define VarR8FromInt		VarR8FromI4
-#define VarR8FromUint		VarR8FromUI4
-#define VarDateFromInt	VarDateFromI4
-#define VarDateFromUint	VarDateFromUI4
-#define VarCyFromInt		VarCyFromI4
-#define VarCyFromUint		VarCyFromUI4
-#define VarBstrFromInt	VarBstrFromI4
-#define VarBstrFromUint	VarBstrFromUI4
-#define VarBoolFromInt	VarBoolFromI4
-#define VarBoolFromUint	VarBoolFromUI4
-#define VarI1FromInt		VarI1FromI4
-#define VarI1FromUint		VarI1FromUI4
-#define VarUI2FromInt		VarUI2FromI4
-#define VarUI2FromUint	VarUI2FromUI4
-#define VarUI4FromInt		VarUI4FromI4
-#define VarUI4FromUint	VarUI4FromUI4
-#define VarUI8FromInt		VarUI8FromI4
-#define VarUI8FromUint	VarUI8FromUI4
-#define VarDecFromInt		VarDecFromI4
-#define VarDecFromUint	VarDecFromUI4
-#define VarIntFromUI1		VarI4FromUI1
-#define VarIntFromI2		VarI4FromI2
-#define VarIntFromI4		VarI4FromI4
-#define VarIntFromI8		VarI4FromI8
-#define VarIntFromR4		VarI4FromR4
-#define VarIntFromR8		VarI4FromR8
-#define VarIntFromDate	VarI4FromDate
-#define VarIntFromCy		VarI4FromCy
-#define VarIntFromStr		VarI4FromStr
-#define VarIntFromDisp	VarI4FromDisp
-#define VarIntFromBool	VarI4FromBool
-#define VarIntFromI1		VarI4FromI1
-#define VarIntFromUI2		VarI4FromUI2
-#define VarIntFromUI4		VarI4FromUI4
-#define VarIntFromUI8		VarI4FromUI8
-#define VarIntFromDec		VarI4FromDec
-#define VarIntFromUint	VarI4FromUI4
-#define VarUintFromUI1	VarUI4FromUI1
-#define VarUintFromI2		VarUI4FromI2
-#define VarUintFromI4		VarUI4FromI4
-#define VarUintFromI8		VarUI4FromI8
-#define VarUintFromR4		VarUI4FromR4
-#define VarUintFromR8		VarUI4FromR8
-#define VarUintFromDate	VarUI4FromDate
-#define VarUintFromCy		VarUI4FromCy
-#define VarUintFromStr	VarUI4FromStr
-#define VarUintFromDisp	VarUI4FromDisp
-#define VarUintFromBool	VarUI4FromBool
-#define VarUintFromI1		VarUI4FromI1
-#define VarUintFromUI2	VarUI4FromUI2
-#define VarUintFromUI4	VarUI4FromUI4
-#define VarUintFromUI8	VarUI4FromUI8
-#define VarUintFromDec	VarUI4FromDec
-#define VarUintFromInt	VarUI4FromI4
+#define VarUI1FromInt   VarUI1FromI4
+#define VarUI1FromUint  VarUI1FromUI4
+#define VarI2FromInt    VarI2FromI4
+#define VarI2FromUint   VarI2FromUI4
+#define VarI4FromInt    VarI4FromI4
+#define VarI4FromUint   VarI4FromUI4
+#define VarI8FromInt    VarI8FromI4
+#define VarI8FromUint   VarI8FromUI4
+#define VarR4FromInt    VarR4FromI4
+#define VarR4FromUint   VarR4FromUI4
+#define VarR8FromInt    VarR8FromI4
+#define VarR8FromUint   VarR8FromUI4
+#define VarDateFromInt  VarDateFromI4
+#define VarDateFromUint VarDateFromUI4
+#define VarCyFromInt    VarCyFromI4
+#define VarCyFromUint   VarCyFromUI4
+#define VarBstrFromInt  VarBstrFromI4
+#define VarBstrFromUint VarBstrFromUI4
+#define VarBoolFromInt  VarBoolFromI4
+#define VarBoolFromUint VarBoolFromUI4
+#define VarI1FromInt    VarI1FromI4
+#define VarI1FromUint   VarI1FromUI4
+#define VarUI2FromInt   VarUI2FromI4
+#define VarUI2FromUint  VarUI2FromUI4
+#define VarUI4FromInt   VarUI4FromI4
+#define VarUI4FromUint  VarUI4FromUI4
+#define VarUI8FromInt   VarUI8FromI4
+#define VarUI8FromUint  VarUI8FromUI4
+#define VarDecFromInt   VarDecFromI4
+#define VarDecFromUint  VarDecFromUI4
+#define VarIntFromUI1   VarI4FromUI1
+#define VarIntFromI2    VarI4FromI2
+#define VarIntFromI4    VarI4FromI4
+#define VarIntFromI8    VarI4FromI8
+#define VarIntFromR4    VarI4FromR4
+#define VarIntFromR8    VarI4FromR8
+#define VarIntFromDate  VarI4FromDate
+#define VarIntFromCy    VarI4FromCy
+#define VarIntFromStr   VarI4FromStr
+#define VarIntFromDisp  VarI4FromDisp
+#define VarIntFromBool  VarI4FromBool
+#define VarIntFromI1    VarI4FromI1
+#define VarIntFromUI2   VarI4FromUI2
+#define VarIntFromUI4   VarI4FromUI4
+#define VarIntFromUI8   VarI4FromUI8
+#define VarIntFromDec   VarI4FromDec
+#define VarIntFromUint  VarI4FromUI4
+#define VarUintFromUI1  VarUI4FromUI1
+#define VarUintFromI2   VarUI4FromI2
+#define VarUintFromI4   VarUI4FromI4
+#define VarUintFromI8   VarUI4FromI8
+#define VarUintFromR4   VarUI4FromR4
+#define VarUintFromR8   VarUI4FromR8
+#define VarUintFromDate VarUI4FromDate
+#define VarUintFromCy   VarUI4FromCy
+#define VarUintFromStr  VarUI4FromStr
+#define VarUintFromDisp VarUI4FromDisp
+#define VarUintFromBool VarUI4FromBool
+#define VarUintFromI1   VarUI4FromI1
+#define VarUintFromUI2  VarUI4FromUI2
+#define VarUintFromUI4  VarUI4FromUI4
+#define VarUintFromUI8  VarUI4FromUI8
+#define VarUintFromDec  VarUI4FromDec
+#define VarUintFromInt  VarUI4FromI4
 
 /*
  * Variant Math operations
@@ -535,6 +541,11 @@
 #define VARCMP_GT   2
 #define VARCMP_NULL 3
 
+HRESULT WINAPI VarR4CmpR8(float,double);
+
+HRESULT WINAPI VarR8Pow(double,double,double*);
+HRESULT WINAPI VarR8Round(double,int,double*);
+
 HRESULT WINAPI VarDecAbs(const DECIMAL*,DECIMAL*);
 HRESULT WINAPI VarDecAdd(const DECIMAL*,const DECIMAL*,DECIMAL*);
 HRESULT WINAPI VarDecCmp(const DECIMAL*,const DECIMAL*);
@@ -584,95 +595,120 @@
 
 HRESULT WINAPI VarCmp(LPVARIANT,LPVARIANT,LCID,ULONG);
 
+HRESULT WINAPI VarBstrCmp(BSTR,BSTR,LCID,ULONG);
+HRESULT WINAPI VarBstrCat(BSTR,BSTR,BSTR*);
 
 
-typedef struct tagPARAMDATA {
-    OLECHAR * szName;   /* parameter name */
-    VARTYPE vt;         /* parameter type */
-} PARAMDATA, * LPPARAMDATA;
-
-typedef struct tagMETHODDATA {
-    OLECHAR * szName;   /* method name */
-    PARAMDATA * ppdata; /* pointer to an array of PARAMDATAs */
-    DISPID dispid;      /* method ID */
-    UINT iMeth;         /* method index */
-    CALLCONV cc;        /* calling convention */
-    UINT cArgs;         /* count of arguments */
-    WORD wFlags;        /* same wFlags as on IDispatch::Invoke() */
-    VARTYPE vtReturn;
-} METHODDATA, * LPMETHODDATA;
-
-typedef struct tagINTERFACEDATA {
-    METHODDATA * pmethdata;  /* pointer to an array of METHODDATAs */
-    UINT         cMembers;   /* count of members */
-} INTERFACEDATA, * LPINTERFACEDATA;
-
-typedef enum tagREGKIND
-{
-    REGKIND_DEFAULT,
-    REGKIND_REGISTER,
-    REGKIND_NONE
-} REGKIND;
-
 typedef struct {
     SYSTEMTIME st;
     USHORT wDayOfYear;
 } UDATE;
 
-typedef struct {
-    INT   cDig;
-    ULONG dwInFlags;
-    ULONG dwOutFlags;
-    INT   cchUsed;
-    INT   nBaseShift;
-    INT   nPwr10;
+typedef struct
+{
+    INT   cDig;       /* Number of parsed digits */
+    ULONG dwInFlags;  /* Acceptable state of the input string (NUMPRS_ flags) */
+    ULONG dwOutFlags; /* Parsed state of the output string (NUMPRS_ flags) */
+    INT   cchUsed;    /* Number of characters parsed from input string */
+    INT   nBaseShift; /* Base of the number (but apparently unused) */
+    INT   nPwr10;     /* Scale of the number in powers of 10 */
 } NUMPARSE;
 
-#define NUMPRS_LEADING_WHITE    0x0001
-#define NUMPRS_TRAILING_WHITE   0x0002
-#define NUMPRS_LEADING_PLUS     0x0004
-#define NUMPRS_TRAILING_PLUS    0x0008
-#define NUMPRS_LEADING_MINUS    0x0010
-#define NUMPRS_TRAILING_MINUS   0x0020
-#define NUMPRS_HEX_OCT          0x0040
-#define NUMPRS_PARENS           0x0080
-#define NUMPRS_DECIMAL          0x0100
-#define NUMPRS_THOUSANDS        0x0200
-#define NUMPRS_CURRENCY         0x0400
-#define NUMPRS_EXPONENT         0x0800
-#define NUMPRS_USE_ALL          0x1000
-#define NUMPRS_STD              0x1FFF
-
-#define NUMPRS_NEG              0x10000
-#define NUMPRS_INEXACT          0x20000
+#define NUMPRS_LEADING_WHITE  0x00001 /* Leading whitespace */
+#define NUMPRS_TRAILING_WHITE 0x00002 /* Trailing whitespace */
+#define NUMPRS_LEADING_PLUS   0x00004 /* Leading '+' sign */
+#define NUMPRS_TRAILING_PLUS  0x00008 /* Trailing '+' sign */
+#define NUMPRS_LEADING_MINUS  0x00010 /* Leading '-' sign */
+#define NUMPRS_TRAILING_MINUS 0x00020 /* Trailing '-' sign */
+#define NUMPRS_HEX_OCT        0x00040 /* Octal number (with a leading 0) */
+#define NUMPRS_PARENS         0x00080 /* Parentheses for negative numbers */
+#define NUMPRS_DECIMAL        0x00100 /* Decimal seperator */
+#define NUMPRS_THOUSANDS      0x00200 /* Thousands seperator */
+#define NUMPRS_CURRENCY       0x00400 /* Currency symbol */
+#define NUMPRS_EXPONENT       0x00800 /* Exponent (e.g. "e-14") */
+#define NUMPRS_USE_ALL        0x01000 /* Parse the entire string */
+#define NUMPRS_STD            0x01FFF /* Standard flags for internal coercions (All of the above) */
+#define NUMPRS_NEG            0x10000 /* Number is negative (dwOutFlags only) */
+#define NUMPRS_INEXACT        0x20000 /* Number is represented inexactly (dwOutFlags only) */
 
-#define VTBIT_I1        (1 << VT_I1)
-#define VTBIT_UI1       (1 << VT_UI1)
-#define VTBIT_I2        (1 << VT_I2)
-#define VTBIT_UI2       (1 << VT_UI2)
-#define VTBIT_I4        (1 << VT_I4)
-#define VTBIT_UI4       (1 << VT_UI4)
-#define VTBIT_I8        (1 << VT_I8)
-#define VTBIT_UI8       (1 << VT_UI8)
-#define VTBIT_R4        (1 << VT_R4)
-#define VTBIT_R8        (1 << VT_R8)
-#define VTBIT_CY        (1 << VT_CY)
-#define VTBIT_DECIMAL   (1 << VT_DECIMAL)
+#define VTBIT_I1      (1 << VT_I1)
+#define VTBIT_UI1     (1 << VT_UI1)
+#define VTBIT_I2      (1 << VT_I2)
+#define VTBIT_UI2     (1 << VT_UI2)
+#define VTBIT_I4      (1 << VT_I4)
+#define VTBIT_UI4     (1 << VT_UI4)
+#define VTBIT_I8      (1 << VT_I8)
+#define VTBIT_UI8     (1 << VT_UI8)
+#define VTBIT_R4      (1 << VT_R4)
+#define VTBIT_R8      (1 << VT_R8)
+#define VTBIT_CY      (1 << VT_CY)
+#define VTBIT_DECIMAL (1 << VT_DECIMAL)
 
 HRESULT WINAPI VarParseNumFromStr(OLECHAR*,LCID,ULONG,NUMPARSE*,BYTE*);
 HRESULT WINAPI VarNumFromParseNum(NUMPARSE*,BYTE*,ULONG,VARIANT*);
 
-INT WINAPI DosDateTimeToVariantTime(USHORT,USHORT,DATE*);
-INT WINAPI VariantTimeToDosDateTime(DATE,USHORT*,USHORT*);
+INT WINAPI DosDateTimeToVariantTime(USHORT,USHORT,double*);
+INT WINAPI VariantTimeToDosDateTime(double,USHORT*,USHORT*);
 
-HRESULT WINAPI VariantTimeToSystemTime(DOUBLE,LPSYSTEMTIME);
-HRESULT WINAPI SystemTimeToVariantTime(LPSYSTEMTIME,double*);
+INT WINAPI VariantTimeToSystemTime(DOUBLE,LPSYSTEMTIME);
+INT WINAPI SystemTimeToVariantTime(LPSYSTEMTIME,double*);
 
 HRESULT WINAPI VarDateFromUdate(UDATE*,ULONG,DATE*);
+HRESULT WINAPI VarDateFromUdateEx(UDATE*,LCID,ULONG,DATE*);
 HRESULT WINAPI VarUdateFromDate(DATE,ULONG,UDATE*);
 
-ULONG WINAPI LHashValOfNameSysA(SYSKIND,LCID,LPCSTR);
-ULONG WINAPI LHashValOfNameSys (SYSKIND,LCID,LPCOLESTR);
+/* Variant formatting */
+HRESULT WINAPI VarWeekdayName(int,int,int,ULONG,BSTR*);
+HRESULT WINAPI VarMonthName(int,int,ULONG,BSTR*);
+HRESULT WINAPI GetAltMonthNames(LCID,LPOLESTR**);
+
+HRESULT WINAPI VarFormat(LPVARIANT,LPOLESTR,int,int,ULONG,BSTR*);
+HRESULT WINAPI VarFormatCurrency(LPVARIANT,int,int,int,int,ULONG,BSTR*);
+HRESULT WINAPI VarFormatDateTime(LPVARIANT,int,ULONG,BSTR*);
+HRESULT WINAPI VarFormatNumber(LPVARIANT,int,int,int,int,ULONG,BSTR*);
+HRESULT WINAPI VarFormatPercent(LPVARIANT,int,int,int,int,ULONG,BSTR*);
+
+HRESULT WINAPI VarFormatFromTokens(LPVARIANT,LPOLESTR,LPBYTE,ULONG,BSTR*,LCID);
+HRESULT WINAPI VarTokenizeFormatString(LPOLESTR,LPBYTE,int,int,int,LCID,int*);
+
+
+/*
+ * IDispatch types and helper functions
+ */
+
+/* A structure describing a single parameter to a com object method. */
+typedef struct tagPARAMDATA
+{
+    OLECHAR *szName; /* Name of Parameter */
+    VARTYPE  vt;     /* Type of Parameter */
+} PARAMDATA, *LPPARAMDATA;
+
+/* A structure describing a single method of a com object. */
+typedef struct tagMETHODDATA
+{
+    OLECHAR   *szName;   /* Name of method */
+    PARAMDATA *ppdata;   /* Parameters of the method */
+    DISPID     dispid;   /* Id of the method */
+    UINT       iMeth;    /* Vtable index of the method */
+    CALLCONV   cc;       /* Calling convention of the method */
+    UINT       cArgs;    /* Number of parameters in the method */
+    WORD       wFlags;   /* Type of the method (DISPATCH_ flags) */
+    VARTYPE    vtReturn; /* Type of the return value */
+} METHODDATA, *LPMETHODDATA;
+
+/* Structure describing a single com object */
+typedef struct tagINTERFACEDATA
+{
+    METHODDATA *pmethdata;  /* Methods of the object */
+    UINT        cMembers;   /* Number of methods in the object */
+} INTERFACEDATA, *LPINTERFACEDATA;
+
+typedef enum tagREGKIND
+{
+    REGKIND_DEFAULT,
+    REGKIND_REGISTER,
+    REGKIND_NONE
+} REGKIND;
 
 HRESULT WINAPI DispGetParam(DISPPARAMS*,UINT,VARTYPE,VARIANT*,UINT*);
 HRESULT WINAPI DispGetIDsOfNames(ITypeInfo*,OLECHAR**,UINT,DISPID*);
@@ -689,13 +725,25 @@
  * TypeLib API
  */
 
-#define MEMBERID_NIL DISPID_UNKNOWN
+ULONG WINAPI LHashValOfNameSysA(SYSKIND,LCID,LPCSTR);
+ULONG WINAPI LHashValOfNameSys(SYSKIND,LCID,LPCOLESTR);
+
+#define LHashValOfName(lcid,name) LHashValOfNameSys(SYS_WIN32,lcid,name)
+#define WHashValOfLHashVal(hash) ((USHORT)((hash) & 0xffff))
+#define IsHashValCompatible(hash1,hash2) ((hash1) & 0xff0000 == (hash2) & 0xff0000)
+
+#define MEMBERID_NIL   DISPID_UNKNOWN
+#define ID_DEFAULTINST -2
 
 #define DISPATCH_METHOD         0x1
 #define DISPATCH_PROPERTYGET    0x2
 #define DISPATCH_PROPERTYPUT    0x4
 #define DISPATCH_PROPERTYPUTREF 0x8
 
+#define LOAD_TLB_AS_32BIT       0x20
+#define LOAD_TLB_AS_64BIT       0x40
+#define MASK_TO_RESET_TLB_BITS  ~(LOAD_TLB_AS_32BIT|LOAD_TLB_AS_64BIT)
+
 HRESULT WINAPI CreateTypeLib(SYSKIND,const OLECHAR*,ICreateTypeLib**);
 HRESULT WINAPI CreateTypeLib2(SYSKIND,LPCOLESTR,ICreateTypeLib2**);
 HRESULT WINAPI LoadRegTypeLib(REFGUID,WORD,WORD,LCID,ITypeLib**);
@@ -705,6 +753,8 @@
 HRESULT WINAPI RegisterTypeLib(ITypeLib*,OLECHAR*,OLECHAR*);
 HRESULT WINAPI UnRegisterTypeLib(REFGUID,WORD,WORD,LCID,SYSKIND);
 
+VOID WINAPI ClearCustData(LPCUSTDATA);
+
 #ifdef __cplusplus
 } /* extern "C" */
 #endif
diff -ur --minimal wine/dlls/oleaut32/oleaut.c wine-develop/dlls/oleaut32/oleaut.c
--- wine/dlls/oleaut32/oleaut.c	2003-10-16 21:20:12.000000000 +0000
+++ wine-develop/dlls/oleaut32/oleaut.c	2003-11-14 22:45:29.000000000 +0000
@@ -550,7 +550,7 @@
  * Currently the versions returned are 2.20 for Win3.1, 2.30 for Win95 & NT 3.51,
  * and 2.40 for all later versions. The build number is maximum, i.e. 0xffff.
  */
-UINT WINAPI OaBuildVersion()
+ULONG WINAPI OaBuildVersion()
 {
     switch(GetVersion() & 0x8000ffff)  /* mask off build number */
     {
diff -ur --minimal wine/dlls/oleaut32/variant.c wine-develop/dlls/oleaut32/variant.c
--- wine/dlls/oleaut32/variant.c	2003-11-14 21:20:54.000000000 +0000
+++ wine-develop/dlls/oleaut32/variant.c	2003-11-15 00:05:57.000000000 +0000
@@ -2,6 +2,10 @@
  * VARIANT
  *
  * Copyright 1998 Jean-Claude Cote
+ * Copyright 2003 Jon Griffiths
+ * The alorithm for conversion from Julian days to day/month/year is based on
+ * that devised by Henry Fliegel, as implemented in PostgreSQL, which is
+ * Copyright 1994-7 Regents of the University of California
  *
  * This library is free software; you can redistribute it and/or
  * modify it under the terms of the GNU Lesser General Public
@@ -4206,27 +4210,427 @@
     return DISP_E_TYPEMISMATCH;
 }
 
+/* Date Conversions */
+
+#define IsLeapYear(y) (((y % 4) == 0) && (((y % 100) != 0) || ((y % 400) == 0)))
+
+/* Convert a VT_DATE value to a Julian Date */
+static inline int VARIANT_JulianFromDate(int dateIn)
+{
+  int julianDays = dateIn;
+
+  julianDays -= DATE_MIN; /* Convert to + days from 1 Jan 100 AD */
+  julianDays += 1757585;  /* Convert to + days from 23 Nov 4713 BC (Julian) */
+  return julianDays;
+}
+
+/* Convert a Julian Date to a VT_DATE value */
+static inline int VARIANT_DateFromJulian(int dateIn)
+{
+  int julianDays = dateIn;
+
+  julianDays -= 1757585;  /* Convert to + days from 1 Jan 100 AD */
+  julianDays += DATE_MIN; /* Convert to +/- days from 1 Jan 1899 AD */
+  return julianDays;
+}
+
+/* Convert a Julian date to Day/Month/Year - from PostgreSQL */
+static inline void VARIANT_DMYFromJulian(int jd, USHORT *year, USHORT *month, USHORT *day)
+{
+  int j, i, l, n;
+
+  l = jd + 68569;
+  n = l * 4 / 146097;
+  l -= (n * 146097 + 3) / 4;
+  i = (4000 * (l + 1)) / 1461001;
+  l += 31 - (i * 1461) / 4;
+  j = (l * 80) / 2447;
+  *day = l - (j * 2447) / 80;
+  l = j / 11;
+  *month = (j + 2) - (12 * l);
+  *year = 100 * (n - 49) + i + l;
+}
+
+/* Convert Day/Month/Year to a Julian date - from PostgreSQL */
+static inline double VARIANT_JulianFromDMY(USHORT year, USHORT month, USHORT day)
+{
+  int m12 = (month - 14) / 12;
+
+  return ((1461 * (year + 4800 + m12)) / 4 + (367 * (month - 2 - 12 * m12)) / 12 -
+           (3 * ((year + 4900 + m12) / 100)) / 4 + day - 32075);
+}
+
+/* Macros for accessing DOS format date/time fields */
+#define DOS_YEAR(x)   (1980 + (x >> 9))
+#define DOS_MONTH(x)  ((x >> 5) & 0xf)
+#define DOS_DAY(x)    (x & 0x1f)
+#define DOS_HOUR(x)   (x >> 11)
+#define DOS_MINUTE(x) ((x >> 5) & 0x3f)
+#define DOS_SECOND(x) ((x & 0x1f) << 1)
+/* Create a DOS format date/time */
+#define DOS_DATE(d,m,y) (d | (m << 5) | ((y-1980) << 9))
+#define DOS_TIME(h,m,s) ((s >> 1) | (m << 5) | (h << 11))
+
+/* Roll a date forwards or backwards to correct it */
+static HRESULT VARIANT_RollUdate(UDATE *lpUd)
+{
+  static const BYTE days[] = { 0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
+
+  TRACE("Raw date: %d/%d/%d %d:%d:%d\n", lpUd->st.wDay, lpUd->st.wMonth,
+        lpUd->st.wYear, lpUd->st.wHour, lpUd->st.wMinute, lpUd->st.wSecond);
+
+  /* Years < 100 are treated as 1900 + year */
+  if (lpUd->st.wYear < 100)
+    lpUd->st.wYear += 1900;
+
+  if (!lpUd->st.wMonth)
+  {
+    /* Roll back to December of the previous year */
+    lpUd->st.wMonth = 12;
+    lpUd->st.wYear--;
+  }
+  else while (lpUd->st.wMonth > 12)
+  {
+    /* Roll forward the correct number of months */
+    lpUd->st.wYear++;
+    lpUd->st.wMonth -= 12;
+  }
+
+  if (lpUd->st.wYear > 9999 || lpUd->st.wHour > 23 ||
+      lpUd->st.wMinute > 59 || lpUd->st.wSecond > 59)
+    return E_INVALIDARG; /* Invalid values */
+
+  if (!lpUd->st.wDay)
+  {
+    /* Roll back the date one day */
+    if (lpUd->st.wMonth == 1)
+    {
+      /* Roll back to December 31 of the previous year */
+      lpUd->st.wDay   = 31;
+      lpUd->st.wMonth = 12;
+      lpUd->st.wYear--;
+    }
+    else
+    {
+      lpUd->st.wMonth--; /* Previous month */
+      if (lpUd->st.wMonth == 2 && IsLeapYear(lpUd->st.wYear))
+        lpUd->st.wDay = 29; /* Februaury has 29 days on leap years */
+      else
+        lpUd->st.wDay = days[lpUd->st.wMonth]; /* Last day of the month */
+    }
+  }
+  else if (lpUd->st.wDay > 28)
+  {
+    int rollForward = 0;
+
+    /* Possibly need to roll the date forward */
+    if (lpUd->st.wMonth == 2 && IsLeapYear(lpUd->st.wYear))
+      rollForward = lpUd->st.wDay - 29; /* Februaury has 29 days on leap years */
+    else
+      rollForward = lpUd->st.wDay - days[lpUd->st.wMonth];
+
+    if (rollForward > 0)
+    {
+      lpUd->st.wDay = rollForward;
+      lpUd->st.wMonth++;
+      if (lpUd->st.wMonth > 12)
+      {
+        lpUd->st.wMonth = 1; /* Roll forward into January of the next year */
+        lpUd->st.wYear++;
+      }
+    }
+  }
+  TRACE("Rolled date: %d/%d/%d %d:%d:%d\n", lpUd->st.wDay, lpUd->st.wMonth,
+        lpUd->st.wYear, lpUd->st.wHour, lpUd->st.wMinute, lpUd->st.wSecond);
+  return S_OK;
+}
+
 /**********************************************************************
  *              DosDateTimeToVariantTime [OLEAUT32.14]
- * Convert dos representation of time to the date and time representation
- * stored in a variant.
+ *
+ * Convert a Dos format date and time into variant VT_DATE format.
+ *
+ * PARAMS
+ *  wDosDate [I] Dos format date
+ *  wDosTime [I] Dos format time
+ *  pDateOut [O] Destination for VT_DATE format
+ *
+ * RETURNS
+ *  Success: TRUE. pDateOut contains the converted time.
+ *  Failure: FALSE, if wDosDate or wDosTime are invalid (see notes).
+ *
+ * NOTES
+ * - Dos format dates can only hold dates from 1-Jan-1980 to 31-Dec-2099.
+ * - Dos format times are accurate to only 2 second precision.
+ * - The format of a Dos Date is:
+ *| Bits   Values  Meaning
+ *| ----   ------  -------
+ *| 0-4    1-31    Day of the week. 0 rolls back one day. A value greater than
+ *|                the days in the month rolls forward the extra days.
+ *| 5-8    1-12    Month of the year. 0 rolls back to December of the previous
+ *|                year. 13-15 are invalid.
+ *| 9-15   0-119   Year based from 1980 (Max 2099). 120-127 are invalid.
+ * - The format of a Dos Time is:
+ *| Bits   Values  Meaning
+ *| ----   ------  -------
+ *| 0-4    0-29    Seconds/2. 30 and 31 are invalid.
+ *| 5-10   0-59    Minutes. 60-63 are invalid.
+ *| 11-15  0-23    Hours (24 hour clock). 24-32 are invalid.
  */
 INT WINAPI DosDateTimeToVariantTime(USHORT wDosDate, USHORT wDosTime,
-                                    DATE *pvtime)
+                                    double *pDateOut)
 {
-    struct tm t;
+  UDATE ud;
 
-    TRACE("( 0x%x, 0x%x, %p ), stub\n", wDosDate, wDosTime, pvtime );
+  TRACE("(0x%x(%d/%d/%d),0x%x(%d:%d:%d),%p)\n",
+        wDosDate, DOS_YEAR(wDosDate), DOS_MONTH(wDosDate), DOS_DAY(wDosDate),
+        wDosTime, DOS_HOUR(wDosTime), DOS_MINUTE(wDosTime), DOS_SECOND(wDosTime),
+        pDateOut);
 
-    t.tm_sec = (wDosTime & 0x001f) * 2;
-    t.tm_min = (wDosTime & 0x07e0) >> 5;
-    t.tm_hour = (wDosTime & 0xf800) >> 11;
+  ud.st.wYear = DOS_YEAR(wDosDate);
+  ud.st.wMonth = DOS_MONTH(wDosDate);
+  if (ud.st.wYear > 2099 || ud.st.wMonth > 12)
+    return FALSE;
+  ud.st.wDay = DOS_DAY(wDosDate);
+  ud.st.wHour = DOS_HOUR(wDosTime);
+  ud.st.wMinute = DOS_MINUTE(wDosTime);
+  ud.st.wSecond = DOS_SECOND(wDosTime);
+  ud.st.wDayOfWeek = ud.st.wMilliseconds = 0;
 
-    t.tm_mday = (wDosDate & 0x001f);
-    t.tm_mon = (wDosDate & 0x01e0) >> 5;
-    t.tm_year = ((wDosDate & 0xfe00) >> 9) + 1980;
+  return !VarDateFromUdate(&ud, 0, pDateOut);
+}
 
-    return TmToDATE( &t, pvtime );
+/**********************************************************************
+ *              VariantTimeToDosDateTime [OLEAUT32.13]
+ *
+ * Convert a variant format date into a Dos format date and time.
+ *
+ *  dateIn    [I] VT_DATE time format
+ *  pwDosDate [O] Destination for Dos format date
+ *  pwDosTime [O] Destination for Dos format time
+ *
+ * RETURNS
+ *  Success: TRUE. pwDosDate and pwDosTime contains the converted values.
+ *  Failure: FALSE, if dateIn cannot be represented in Dos format.
+ *
+ * NOTES
+ *   See DosDateTimeToVariantTime() for Dos format details and bugs.
+ */
+INT WINAPI VariantTimeToDosDateTime(double dateIn, USHORT *pwDosDate, USHORT *pwDosTime)
+{
+  UDATE ud;
+
+  TRACE("(%g,%p,%p)\n", dateIn, pwDosDate, pwDosTime);
+
+  if (FAILED(VarUdateFromDate(dateIn, 0, &ud)))
+    return FALSE;
+
+  if (ud.st.wYear < 1980 || ud.st.wYear > 2099)
+    return FALSE;
+
+  *pwDosDate = DOS_DATE(ud.st.wDay, ud.st.wMonth, ud.st.wYear);
+  *pwDosTime = DOS_TIME(ud.st.wHour, ud.st.wMinute, ud.st.wSecond);
+
+  TRACE("Returning 0x%x(%d/%d/%d), 0x%x(%d:%d:%d)\n",
+        *pwDosDate, DOS_YEAR(*pwDosDate), DOS_MONTH(*pwDosDate), DOS_DAY(*pwDosDate),
+        *pwDosTime, DOS_HOUR(*pwDosTime), DOS_MINUTE(*pwDosTime), DOS_SECOND(*pwDosTime));
+  return TRUE;
+}
+
+/***********************************************************************
+ *              SystemTimeToVariantTime [OLEAUT32.184]
+ *
+ * Convert a System format date and time into variant VT_DATE format.
+ *
+ * PARAMS
+ *  lpSt     [I] System format date and time
+ *  pDateOut [O] Destination for VT_DATE format date
+ *
+ * RETURNS
+ *  Success: TRUE. *pDateOut contains the converted value.
+ *  Failure: FALSE, if lpSt cannot be represented in VT_DATE format.
+ */
+INT WINAPI SystemTimeToVariantTime(LPSYSTEMTIME lpSt, double *pDateOut)
+{
+  UDATE ud;
+
+  TRACE("(%p->%d/%d/%d %d:%d:%d,%p)\n", lpSt, lpSt->wDay, lpSt->wMonth,
+        lpSt->wYear, lpSt->wHour, lpSt->wMinute, lpSt->wSecond, pDateOut);
+
+  if (lpSt->wMonth > 12)
+    return FALSE;
+
+  memcpy(&ud.st, lpSt, sizeof(ud.st));
+  return !VarDateFromUdate(&ud, 0, pDateOut);
+}
+
+/***********************************************************************
+ *              VariantTimeToSystemTime [OLEAUT32.185]
+ *
+ * Convert a variant VT_DATE into a System format date and time.
+ *
+ * PARAMS
+ *  datein [I] Variant VT_DATE format date
+ *  lpSt   [O] Destination for System format date and time
+ *
+ * RETURNS
+ *  Success: TRUE. *lpSt contains the converted value.
+ *  Failure: FALSE, if dateIn is too large or small.
+ */
+INT WINAPI VariantTimeToSystemTime(double dateIn, LPSYSTEMTIME lpSt)
+{
+  UDATE ud;
+
+  TRACE("(%g,%p)\n", dateIn, lpSt);
+
+  if (FAILED(VarUdateFromDate(dateIn, 0, &ud)))
+    return FALSE;
+
+  memcpy(lpSt, &ud.st, sizeof(ud.st));
+  return TRUE;
+}
+
+/***********************************************************************
+ *              VarDateFromUdate [OLEAUT32.330]
+ *
+ * Convert an unpacked format date and time to a variant VT_DATE.
+ *
+ * PARAMS
+ *  pUdateIn [I] Unpacked format date and time to convert
+ *  dwFlags  [I] Flags controlling the conversion (VAR_ flags from "oleauto.h")
+ *  pDateOut [O] Destination for variant VT_DATE.
+ *
+ * RETURNS
+ *  Success: S_OK. *pDateOut contains the converted value.
+ *  Failure: E_INVALIDARG, if pUdateIn cannot be represented in VT_DATE format.
+ */
+HRESULT WINAPI VarDateFromUdate(UDATE *pUdateIn, ULONG dwFlags, DATE *pDateOut)
+{
+  UDATE ud;
+  double dateVal;
+
+  TRACE("(%p->%d/%d/%d %d:%d:%d:%d %d %d,0x%08lx,%p)\n", pUdateIn,
+        pUdateIn->st.wMonth, pUdateIn->st.wDay, pUdateIn->st.wYear,
+        pUdateIn->st.wHour, pUdateIn->st.wMinute, pUdateIn->st.wSecond,
+        pUdateIn->st.wMilliseconds, pUdateIn->st.wDayOfWeek,
+        pUdateIn->wDayOfYear, dwFlags, pDateOut);
+
+  memcpy(&ud, pUdateIn, sizeof(ud));
+
+  if (dwFlags & VAR_VALIDDATE)
+    WARN("Ignoring VAR_VALIDDATE\n");
+
+  if (FAILED(VARIANT_RollUdate(&ud)))
+    return E_INVALIDARG;
+
+  /* Date */
+  dateVal = VARIANT_DateFromJulian(VARIANT_JulianFromDMY(ud.st.wYear, ud.st.wMonth, ud.st.wDay));
+
+  /* Time */
+  dateVal += ud.st.wHour / 24.0;
+  dateVal += ud.st.wMinute / 1440.0;
+  dateVal += ud.st.wSecond / 86400.0;
+  dateVal += ud.st.wMilliseconds / 86400000.0;
+
+  TRACE("Returning %g\n", dateVal);
+  *pDateOut = dateVal;
+  return S_OK;
+}
+
+/***********************************************************************
+ *              VarUdateFromDate [OLEAUT32.331]
+ *
+ * Convert a variant VT_DATE into an unpacked format date and time.
+ *
+ * PARAMS
+ *  datein    [I] Variant VT_DATE format date
+ *  dwFlags   [I] Flags controlling the conversion (VAR_ flags from "oleauto.h")
+ *  lpUdate [O] Destination for unpacked format date and time
+ *
+ * RETURNS
+ *  Success: S_OK. *lpUdate contains the converted value.
+ *  Failure: E_INVALIDARG, if dateIn is too large or small.
+ */
+HRESULT WINAPI VarUdateFromDate(DATE dateIn, ULONG dwFlags, UDATE *lpUdate)
+{
+  /* Cumulative totals of days per month */
+  static const USHORT cumulativeDays[] =
+  {
+    0, 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334
+  };
+  double datePart, timePart;
+  int julianDays;
+
+  TRACE("(%g,0x%08lx,%p)\n", dateIn, dwFlags, lpUdate);
+
+  if (dateIn <= (DATE_MIN - 1.0) || dateIn >= (DATE_MAX + 1.0))
+    return E_INVALIDARG;
+
+  datePart = dateIn < 0.0 ? ceil(dateIn) : floor(dateIn);
+  /* Compensate for int truncation (always downwards) */
+  timePart = dateIn - datePart + 0.00000000001;
+  if (timePart >= 1.0)
+    timePart -= 0.00000000001;
+
+  /* Date */
+  julianDays = VARIANT_JulianFromDate(dateIn);
+  VARIANT_DMYFromJulian(julianDays, &lpUdate->st.wYear, &lpUdate->st.wMonth,
+                        &lpUdate->st.wDay);
+
+  datePart = (datePart + 1.5) / 7.0;
+  lpUdate->st.wDayOfWeek = (datePart - floor(datePart)) * 7;
+  if (lpUdate->st.wDayOfWeek == 0)
+    lpUdate->st.wDayOfWeek = 5;
+  else if (lpUdate->st.wDayOfWeek == 1)
+    lpUdate->st.wDayOfWeek = 6;
+  else
+    lpUdate->st.wDayOfWeek -= 2;
+
+  if (lpUdate->st.wMonth > 2 && IsLeapYear(lpUdate->st.wYear))
+    lpUdate->wDayOfYear = 1; /* After February, in a leap year */
+  else
+    lpUdate->wDayOfYear = 0;
+
+  lpUdate->wDayOfYear += cumulativeDays[lpUdate->st.wMonth];
+  lpUdate->wDayOfYear += lpUdate->st.wDay;
+
+  /* Time */
+  timePart *= 24.0;
+  lpUdate->st.wHour = timePart;
+  timePart -= lpUdate->st.wHour;
+  timePart *= 60.0;
+  lpUdate->st.wMinute = timePart;
+  timePart -= lpUdate->st.wMinute;
+  timePart *= 60.0;
+  lpUdate->st.wSecond = timePart;
+  timePart -= lpUdate->st.wSecond;
+  lpUdate->st.wMilliseconds = 0;
+  if (timePart > 0.0005)
+  {
+    /* Round the milliseconds, adjusting the time/date forward if needed */
+    if (lpUdate->st.wSecond < 59)
+      lpUdate->st.wSecond++;
+    else
+    {
+      lpUdate->st.wSecond = 0;
+      if (lpUdate->st.wMinute < 59)
+        lpUdate->st.wMinute++;
+      else
+      {
+        lpUdate->st.wMinute = 0;
+        if (lpUdate->st.wHour < 23)
+          lpUdate->st.wHour++;
+        else
+        {
+          lpUdate->st.wHour = 0;
+          /* Roll over a whole day */
+          if (++lpUdate->st.wDay > 28)
+            VARIANT_RollUdate(lpUdate);
+        }
+      }
+    }
+  }
+  return S_OK;
 }
 
 #define GET_NUMBER_TEXT(fld,name) \
@@ -5004,288 +5408,6 @@
 }
 
 /**********************************************************************
- *              VariantTimeToDosDateTime [OLEAUT32.13]
- * Convert variant representation of time to the date and time representation
- * stored in dos.
- */
-INT WINAPI VariantTimeToDosDateTime(DATE pvtime, USHORT *wDosDate, USHORT *wDosTime)
-{
-    struct tm t;
-    *wDosTime = 0;
-    *wDosDate = 0;
-
-    TRACE("( 0x%x, 0x%x, %p ), stub\n", *wDosDate, *wDosTime, &pvtime );
-
-    if (DateToTm(pvtime, 0, &t) < 0) return 0;
-
-    *wDosTime = *wDosTime | (t.tm_sec / 2);
-    *wDosTime = *wDosTime | (t.tm_min << 5);
-    *wDosTime = *wDosTime | (t.tm_hour << 11);
-
-    *wDosDate = *wDosDate | t.tm_mday ;
-    *wDosDate = *wDosDate | t.tm_mon << 5;
-    *wDosDate = *wDosDate | ((t.tm_year - 1980) << 9) ;
-
-    return 1;
-}
-
-
-/***********************************************************************
- *              SystemTimeToVariantTime [OLEAUT32.184]
- */
-HRESULT WINAPI SystemTimeToVariantTime( LPSYSTEMTIME  lpSystemTime, double *pvtime )
-{
-    struct tm t;
-
-    TRACE(" %d/%d/%d %d:%d:%d\n",
-          lpSystemTime->wMonth, lpSystemTime->wDay,
-          lpSystemTime->wYear, lpSystemTime->wHour,
-          lpSystemTime->wMinute, lpSystemTime->wSecond);
-
-    if (lpSystemTime->wYear >= 1900)
-    {
-        t.tm_sec = lpSystemTime->wSecond;
-        t.tm_min = lpSystemTime->wMinute;
-        t.tm_hour = lpSystemTime->wHour;
-
-        t.tm_mday = lpSystemTime->wDay;
-        t.tm_mon = lpSystemTime->wMonth - 1; /* tm_mon is 0..11, wMonth is 1..12 */
-        t.tm_year = lpSystemTime->wYear;
-
-        return TmToDATE( &t, pvtime );
-    }
-    else
-    {
-        double tmpDate;
-        long firstDayOfNextYear;
-        long thisDay;
-        long leftInYear;
-        long result;
-
-        double decimalPart = 0.0;
-
-        t.tm_sec = lpSystemTime->wSecond;
-        t.tm_min = lpSystemTime->wMinute;
-        t.tm_hour = lpSystemTime->wHour;
-
-        /* Step year forward the same number of years before 1900 */
-        t.tm_year = 1900 + 1899 - lpSystemTime->wYear;
-        t.tm_mon = lpSystemTime->wMonth - 1;
-        t.tm_mday = lpSystemTime->wDay;
-
-        /* Calculate date */
-        TmToDATE( &t, pvtime );
-
-        thisDay = (double) floor( *pvtime );
-        decimalPart = fmod( *pvtime, thisDay );
-
-        /* Now, calculate the same time for the first of Jan that year */
-        t.tm_mon = 0;
-        t.tm_mday = 1;
-        t.tm_sec = 0;
-        t.tm_min = 0;
-        t.tm_hour = 0;
-        t.tm_year = t.tm_year+1;
-        TmToDATE( &t, &tmpDate );
-        firstDayOfNextYear = (long) floor(tmpDate);
-
-        /* Finally since we know the size of the year, subtract the two to get
-           remaining time in the year                                          */
-        leftInYear = firstDayOfNextYear - thisDay;
-
-        /* Now we want full years up to the year in question, and remainder of year
-           of the year in question */
-        if (isleap(lpSystemTime->wYear) ) {
-           TRACE("Extra day due to leap year\n");
-           result = 2.0 - ((firstDayOfNextYear - 366) + leftInYear - 2.0);
-        } else {
-           result = 2.0 - ((firstDayOfNextYear - 365) + leftInYear - 2.0);
-        }
-        *pvtime = (double) result + decimalPart;
-        TRACE("<1899 support: returned %f, 1st day %ld, thisday %ld, left %ld\n", *pvtime, firstDayOfNextYear, thisDay, leftInYear);
-
-        return 1;
-    }
-
-    return 0;
-}
-
-/***********************************************************************
- *              VariantTimeToSystemTime [OLEAUT32.185]
- */
-HRESULT WINAPI VariantTimeToSystemTime( double vtime, LPSYSTEMTIME  lpSystemTime )
-{
-    double t = 0, timeofday = 0;
-
-    static const BYTE Days_Per_Month[] =    {0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
-    static const BYTE Days_Per_Month_LY[] = {0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
-
-    /* The Month_Code is used to find the Day of the Week (LY = LeapYear)*/
-    static const BYTE Month_Code[] =    {0, 1, 4, 4, 0, 2, 5, 0, 3, 6, 1, 4, 6};
-    static const BYTE Month_Code_LY[] = {0, 0, 3, 4, 0, 2, 5, 0, 3, 6, 1, 4, 6};
-
-    /* The Century_Code is used to find the Day of the Week */
-    static const BYTE Century_Code[]  = {0, 6, 4, 2};
-
-    struct tm r;
-
-    TRACE(" Variant = %f SYSTEMTIME ptr %p\n", vtime, lpSystemTime);
-
-    if (vtime >= 0)
-    {
-
-        if (DateToTm(vtime, 0, &r ) <= 0) return 0;
-
-        lpSystemTime->wSecond = r.tm_sec;
-        lpSystemTime->wMinute = r.tm_min;
-        lpSystemTime->wHour = r.tm_hour;
-        lpSystemTime->wDay = r.tm_mday;
-        lpSystemTime->wMonth = r.tm_mon;
-
-        if (lpSystemTime->wMonth == 12)
-            lpSystemTime->wMonth = 1;
-        else
-            lpSystemTime->wMonth++;
-
-        lpSystemTime->wYear = r.tm_year;
-    }
-    else
-    {
-        vtime = -1*vtime;
-
-        if (DateToTm(vtime, 0, &r ) <= 0) return 0;
-
-        lpSystemTime->wSecond = r.tm_sec;
-        lpSystemTime->wMinute = r.tm_min;
-        lpSystemTime->wHour = r.tm_hour;
-
-        lpSystemTime->wMonth = 13 - r.tm_mon;
-
-        if (lpSystemTime->wMonth == 1)
-            lpSystemTime->wMonth = 12;
-        else
-            lpSystemTime->wMonth--;
-
-        lpSystemTime->wYear = 1899 - (r.tm_year - 1900);
-
-        if (!isleap(lpSystemTime->wYear) )
-            lpSystemTime->wDay = Days_Per_Month[13 - lpSystemTime->wMonth] - r.tm_mday;
-        else
-            lpSystemTime->wDay = Days_Per_Month_LY[13 - lpSystemTime->wMonth] - r.tm_mday;
-
-
-    }
-
-    if (!isleap(lpSystemTime->wYear))
-    {
-        /*
-          (Century_Code+Month_Code+Year_Code+Day) % 7
-
-          The century code repeats every 400 years , so the array
-          works out like this,
-
-          Century_Code[0] is for 16th/20th Centry
-          Century_Code[1] is for 17th/21th Centry
-          Century_Code[2] is for 18th/22th Centry
-          Century_Code[3] is for 19th/23th Centry
-
-          The year code is found with the formula (year + (year / 4))
-          the "year" must be between 0 and 99 .
-
-          The Month Code (Month_Code[1]) starts with January and
-          ends with December.
-        */
-
-        lpSystemTime->wDayOfWeek = (
-            Century_Code[(( (lpSystemTime->wYear+100) - lpSystemTime->wYear%100) /100) %4]+
-            ((lpSystemTime->wYear%100)+(lpSystemTime->wYear%100)/4)+
-            Month_Code[lpSystemTime->wMonth]+
-            lpSystemTime->wDay) % 7;
-
-        if (lpSystemTime->wDayOfWeek == 0) lpSystemTime->wDayOfWeek = 7;
-        else lpSystemTime->wDayOfWeek -= 1;
-    }
-    else
-    {
-        lpSystemTime->wDayOfWeek = (
-            Century_Code[(((lpSystemTime->wYear+100) - lpSystemTime->wYear%100)/100)%4]+
-            ((lpSystemTime->wYear%100)+(lpSystemTime->wYear%100)/4)+
-            Month_Code_LY[lpSystemTime->wMonth]+
-            lpSystemTime->wDay) % 7;
-
-        if (lpSystemTime->wDayOfWeek == 0) lpSystemTime->wDayOfWeek = 7;
-        else lpSystemTime->wDayOfWeek -= 1;
-    }
-
-    t = floor(vtime);
-    timeofday = vtime - t;
-
-    lpSystemTime->wMilliseconds = (timeofday
-                                   - lpSystemTime->wHour*(1/24)
-                                   - lpSystemTime->wMinute*(1/1440)
-                                   - lpSystemTime->wSecond*(1/86400) )*(1/5184000);
-
-    return 1;
-}
-
-/***********************************************************************
- *              VarUdateFromDate [OLEAUT32.331]
- */
-HRESULT WINAPI VarUdateFromDate( DATE datein, ULONG dwFlags, UDATE *pudateout)
-{
-    HRESULT i = 0;
-    static const BYTE Days_Per_Month[] =    {0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
-    static const BYTE Days_Per_Month_LY[] = {0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
-
-    TRACE("DATE = %f\n", (double)datein);
-    i = VariantTimeToSystemTime(datein, &(pudateout->st) );
-
-    if (i)
-    {
-        pudateout->wDayOfYear = 0;
-
-        if (isleap(pudateout->st.wYear))
-        {
-            for (i =1; i<pudateout->st.wMonth; i++)
-                pudateout->wDayOfYear += Days_Per_Month[i];
-        }
-        else
-        {
-            for (i =1; i<pudateout->st.wMonth; i++)
-                pudateout->wDayOfYear += Days_Per_Month_LY[i];
-        }
-
-        pudateout->wDayOfYear += pudateout->st.wDay;
-        dwFlags = 0; /*VAR_VALIDDATE*/
-    }
-    else dwFlags = 0;
-
-    return i;
-}
-
-/***********************************************************************
- *              VarDateFromUdate [OLEAUT32.330]
- */
-HRESULT WINAPI VarDateFromUdate(UDATE *pudateout,
-                                ULONG dwFlags, DATE *datein)
-{
-    HRESULT i;
-    double t = 0;
-    TRACE(" %d/%d/%d %d:%d:%d\n",
-          pudateout->st.wMonth, pudateout->st.wDay,
-          pudateout->st.wYear, pudateout->st.wHour,
-          pudateout->st.wMinute, pudateout->st.wSecond);
-
-
-    i = SystemTimeToVariantTime(&(pudateout->st), &t);
-    *datein = t;
-
-    if (i) return S_OK;
-    else return E_INVALIDARG;
-}
-
-
-/**********************************************************************
  *              VarBstrCmp [OLEAUT32.314]
  *
  * flags can be:

[Index of Archives]     [Gimp for Windows]     [Red Hat]     [Samba]     [Yosemite Camping]     [Graphics Cards]     [Wine Home]

  Powered by Linux