/*
 * Wine row server interface.
 *
 * Copyright (C) 2010 Huw Davies
 *
 * 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., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
 */

import "oledb.idl";

[
    object,
    uuid(38248178-cf6d-11de-abe5-000c2916d865),
    pointer_default(unique)
]
interface IWineRowServer : IUnknown
{
    [local] HRESULT SetInnerUnk([in] IUnknown *unknown);

    [local] HRESULT GetMarshal([out] IMarshal **marshal);


    /* IRow */

typedef struct
{
    DBID columnid;
    DBLENGTH max_len;
    DBTYPE type;
    BYTE precision;
    BYTE scale;
} wine_getcolumns_in;

typedef struct
{
    VARIANT v;
    DBLENGTH data_len;
    DBSTATUS status;
} wine_getcolumns_out;

    HRESULT GetColumns([in] DBORDINAL num_cols,
                       [in, size_is((ULONG)num_cols)] wine_getcolumns_in *in_data,
                       [out, size_is((ULONG)num_cols)] wine_getcolumns_out *out_cols);

    HRESULT GetSourceRowset([in] REFIID riid,
                            [out, iid_is(riid)] IUnknown **ppRowset,
                            [out] HROW *phRow);

    HRESULT Open([in, unique] IUnknown *pUnkOuter,
                 [in] DBID *pColumnID,
                 [in] REFGUID rguidColumnType,
                 [in] DWORD dwBindFlags,
                 [in] REFIID riid,
                 [out, iid_is(riid)] IUnknown **ppUnk);

    /* IRowChange */
typedef struct
{
    VARIANT v;
    DBID columnid;
    DBLENGTH data_len;
    DBSTATUS status;
    DBLENGTH max_len;
    DBTYPE type;
    BYTE precision;
    BYTE scale;
} wine_setcolumns_in;

    HRESULT SetColumns([in] DBORDINAL num_cols,
                       [in, size_is((ULONG)num_cols)] wine_setcolumns_in *in_data,
                       [out, size_is((ULONG)num_cols)] DBSTATUS *status);

    /* IRowset */
    HRESULT AddRefRows([in] DBCOUNTITEM cRows,
                       [in, size_is((ULONG)cRows)] const HROW rghRows[],
                       [out, size_is((ULONG)cRows)] DBREFCOUNT rgRefCounts[],
                       [out, size_is((ULONG)cRows)] DBROWSTATUS rgRowStatus[]);

    HRESULT GetData([in] HROW hRow,
                    [in] HACCESSOR hAccessor,
                    [in, out, size_is(size)] BYTE *pData,
                    [in] DWORD size);

    HRESULT GetNextRows([in] HCHAPTER hReserved,
                        [in] DBROWOFFSET lRowsOffset,
                        [in] DBROWCOUNT cRows,
                        [out] DBCOUNTITEM *pcRowObtained,
                        [out, size_is(,(ULONG)cRows)] HROW **prghRows);

    HRESULT ReleaseRows([in] DBCOUNTITEM cRows,
                        [in, size_is((ULONG)cRows)] const HROW rghRows[],
                        [in, size_is((ULONG)cRows)] DBROWOPTIONS rgRowOptions[],
                        [out, size_is((ULONG)cRows)] DBREFCOUNT rgRefCounts[],
                        [out, size_is((ULONG)cRows)] DBROWSTATUS rgRowStatus[]);

    HRESULT RestartPosition([in] HCHAPTER hReserved);

    /* IRowsetLocate */

    HRESULT Compare([in] HCHAPTER hReserved,
                    [in] DBBKMARK cbBookmark1,
                    [in, size_is((ULONG)cbBookmark1)] const BYTE *pBookmark1,
                    [in] DBBKMARK cbBookmark2,
                    [in, size_is((ULONG)cbBookmark2)] const BYTE *pBookmark2,
                    [out] DBCOMPARE *pComparison);

    HRESULT GetRowsAt([in] HWATCHREGION hReserved1,
                      [in] HCHAPTER hReserved2,
                      [in] DBBKMARK cbBookmark,
                      [in, size_is((ULONG)cbBookmark)] const BYTE *pBookmark,
                      [in] DBROWOFFSET lRowsOffset,
                      [in] DBROWCOUNT cRows,
                      [out] DBCOUNTITEM *pcRowsObtained,
                      [out, size_is(,(ULONG)cRows)] HROW **prghRows);

    HRESULT GetRowsByBookmark([in] HCHAPTER hReserved,
                              [in] DBCOUNTITEM cRows,
                              [in, size_is((ULONG)cRows)] const DBBKMARK rgcbBookmarks[],
                              [in, size_is((ULONG)cRows)] const BYTE *rgpBookmarks[],
                              [out, size_is((ULONG)cRows)] HROW rghRows[],
                              [out, size_is((ULONG)cRows)] DBROWSTATUS rgRowStatus[]);

    HRESULT Hash([in] HCHAPTER hReserved,
                 [in] DBBKMARK cBookmarks,
                 [in, size_is((ULONG)cBookmarks)] const DBBKMARK rgcbBookmarks[],
                 [in, size_is((ULONG)cBookmarks)] const BYTE *rgpBookmarks[],
                 [out, size_is((ULONG)cBookmarks)] DBHASHVALUE rgHashedValues[],
                 [out, size_is((ULONG)cBookmarks)] DBROWSTATUS rgBookmarkStatus[]);

    /* IRowsetInfo */

    HRESULT GetProperties([in] ULONG cPropertyIDSets,
                          [in, unique, size_is((ULONG)cPropertyIDSets)] const DBPROPIDSET *rgPropertyIDSets,
                          [in, out] ULONG *pcPropertySets,
                          [out, size_is(,*pcPropertySets)] DBPROPSET **prgPropertySets);

    HRESULT GetReferencedRowset([in] DBORDINAL iOrdinal,
                                [in] REFIID riid,
                                [out, iid_is(riid)] IUnknown **ppReferencedRowset);

    HRESULT GetSpecification([in] REFIID riid,
                             [out, iid_is(riid)] IUnknown **ppSpecification);

    /* IAccessor */

    HRESULT AddRefAccessor([in] HACCESSOR hAccessor,
                           [in, out, unique, annotation("__out_opt")] DBREFCOUNT *pcRefCount);

    HRESULT CreateAccessor([in] DBACCESSORFLAGS dwAccessorFlags,
                           [in] DBCOUNTITEM cBindings,
                           [in, unique, size_is((ULONG)cBindings)] const DBBINDING *rgBindings,
                           [in] DBLENGTH cbRowSize,
                           [out] HACCESSOR *phAccessor,
                           [in, out, unique, size_is((ULONG)cBindings)] DBBINDSTATUS *rgStatus);

    HRESULT GetBindings([in] HACCESSOR hAccessor,
                        [out] DBACCESSORFLAGS *pdwAccessorFlags,
                        [in, out] DBCOUNTITEM *pcBindings,
                        [out, size_is(,(ULONG)*pcBindings)] DBBINDING **prgBindings);

    HRESULT ReleaseAccessor([in] HACCESSOR hAccessor,
                            [in, out, unique] DBREFCOUNT *pcRefCount);
}

[
    helpstring("Wine OLE DB Row Server"),
    threading(both),
    progid("WINEDBROWPRX.AsServer.1"),
    vi_progid("WINEDBROWPRX.AsServer"),
    uuid(38248178-cf6d-11de-abe5-000c2916d865)
]
coclass wine_row_server
{

}

[
    helpstring("Wine OLE DB Row Proxy"),
    threading(both),
    progid("WINEDBROWPRX.AsProxy.1"),
    vi_progid("WINEDBROWPRX.AsProxy"),
    uuid(38248179-cf6d-11de-abe5-000c2916d865)
]
coclass wine_row_proxy
{

}

[
    helpstring("Wine OLE DB Rowset Server"),
    threading(both),
    progid("WINEDBRSTPRX.AsServer.1"),
    vi_progid("WINEDBRSTPRX.AsServer"),
    uuid(3824817a-cf6d-11de-abe5-000c2916d865)
]
coclass wine_rowset_server
{

}

[
    helpstring("Wine OLE DB Rowset Proxy"),
    threading(both),
    progid("WINEDBRSTPRX.AsProxy.1"),
    vi_progid("WINEDBRSTPRX.AsProxy"),
    uuid(3824817b-cf6d-11de-abe5-000c2916d865)
]
coclass wine_rowset_proxy
{

}

cpp_quote("extern HRESULT create_row_server( IUnknown*, LPVOID* );")
cpp_quote("extern HRESULT create_row_marshal( IUnknown*, LPVOID* );")
cpp_quote("extern HRESULT create_rowset_server( IUnknown*, LPVOID* );")
cpp_quote("extern HRESULT create_rowset_marshal( IUnknown*, LPVOID* );")
