array.h revision f2a38a61f58a9252205f92a1b17f1e3eba4a91a1
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync/** @file
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * MS COM / XPCOM Abstraction Layer:
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * Safe array helper class declaration
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync */
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync/*
c7814cf6e1240a519cbec0441e033d0e2470ed00vboxsync * Copyright (C) 2006-2007 Sun Microsystems, Inc.
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync *
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * This file is part of VirtualBox Open Source Edition (OSE), as
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * available from http://www.virtualbox.org. This file is free software;
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * you can redistribute it and/or modify it under the terms of the GNU
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * General Public License (GPL) as published by the Free Software
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * Foundation, in version 2 as it comes in the "COPYING" file of the
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync *
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * The contents of this file may alternatively be used under the terms
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * of the Common Development and Distribution License Version 1.0
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * VirtualBox OSE distribution, in which case the provisions of the
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * CDDL are applicable instead of those of the GPL.
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync *
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * You may elect to license modified versions of this file under the
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * terms and conditions of either the GPL or the CDDL or both.
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync *
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * Clara, CA 95054 USA or visit http://www.sun.com if you need
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * additional information or have any questions.
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync */
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync
5a5b5956f8b592c807c94785d58c25e717d430c4vboxsync#ifndef ___VBox_com_array_h
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync#define ___VBox_com_array_h
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync/** @defgroup grp_COM_arrays COM/XPCOM Arrays
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * @{
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync *
5a5b5956f8b592c807c94785d58c25e717d430c4vboxsync * The COM/XPCOM array support layer provides a cross-platform way to pass
e4bf6817370e1a71833a02285515694afcda7599vboxsync * arrays to and from COM interface methods and consists of the com::SafeArray
5a5b5956f8b592c807c94785d58c25e717d430c4vboxsync * template and a set of ComSafeArray* macros part of which is defined in
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * VBox/com/defs.h.
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync *
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * This layer works with interface attributes and method parameters that have
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * the 'safearray="yes"' attribute in the XIDL definition:
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync * @code
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync <interface name="ISomething" ...>
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync <method name="testArrays">
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync <param name="inArr" type="long" dir="in" safearray="yes"/>
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync <param name="outArr" type="long" dir="out" safearray="yes"/>
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync <param name="retArr" type="long" dir="return" safearray="yes"/>
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync </method>
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync </interface>
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * @endcode
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync *
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * Methods generated from this and similar definitions are implemented in
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * component classes using the following declarations:
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * @code
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync STDMETHOD(TestArrays) (ComSafeArrayIn (LONG, aIn),
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync ComSafeArrayOut (LONG, aOut),
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync ComSafeArrayOut (LONG, aRet));
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * @endcode
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync *
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * And the following function bodies:
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * @code
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync STDMETHODIMP Component::TestArrays (ComSafeArrayIn (LONG, aIn),
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync ComSafeArrayOut (LONG, aOut),
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync ComSafeArrayOut (LONG, aRet))
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync {
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync if (ComSafeArrayInIsNull (aIn))
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync return E_INVALIDARG;
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync if (ComSafeArrayOutIsNull (aOut))
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync return E_POINTER;
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync if (ComSafeArrayOutIsNull (aRet))
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync return E_POINTER;
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync // Use SafeArray to access the input array parameter
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync com::SafeArray <LONG> in (ComSafeArrayInArg (aIn));
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync for (size_t i = 0; i < in.size(); ++ i)
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync LogFlow (("*** in[%u]=%d\n", i, in [i]));
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync // Use SafeArray to create the return array (the same technique is used
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync // for output array paramters)
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync SafeArray <LONG> ret (in.size() * 2);
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync for (size_t i = 0; i < in.size(); ++ i)
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync {
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync ret [i] = in [i];
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync ret [i + in.size()] = in [i] * 10;
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync }
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync ret.detachTo (ComSafeArrayOutArg (aRet));
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync return S_OK;
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync }
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync * @endcode
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync *
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync * Such methods can be called from the client code using the following pattern:
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync * @code
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync ComPtr <ISomething> component;
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync // ...
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync com::SafeArray <LONG> in (3);
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync in [0] = -1;
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync in [1] = -2;
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync in [2] = -3;
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync com::SafeArray <LONG> out;
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync com::SafeArray <LONG> ret;
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync HRESULT rc = component->TestArrays (ComSafeArrayAsInParam (in),
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync ComSafeArrayAsOutParam (out),
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync ComSafeArrayAsOutParam (ret));
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync if (SUCCEEDED (rc))
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync for (size_t i = 0; i < ret.size(); ++ i)
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync printf ("*** ret[%u]=%d\n", i, ret [i]);
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync * @endcode
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync *
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync * For interoperability with standard C++ containers, there is a template
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync * constructor that takes such a container as argument and performs a deep copy
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync * of its contents. This can be used in method implementations like this:
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync * @code
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync STDMETHODIMP Component::COMGETTER(Values) (ComSafeArrayOut (int, aValues))
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync {
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync // ... assume there is a |std::list <int> mValues| data member
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync com::SafeArray <int> values (mValues);
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync values.detachTo (ComSafeArrayOutArg (aValues));
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync return S_OK;
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync }
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * @endcode
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync *
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * The current implementation of the SafeArray layer supports all types normally
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * allowed in XIDL as array element types (including 'wstring' and 'uuid').
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * However, 'pointer-to-...' types (e.g. 'long *', 'wstring *') are not
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * supported and therefore cannot be used as element types.
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync *
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * Note that for GUID arrays you should use SafeGUIDArray and
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * SafeConstGUIDArray, customized SafeArray<> specializations.
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync *
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * Also note that in order to pass input BSTR array parameters declared
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * using the ComSafeArrayIn (INPTR BSTR, aParam) macro to the SafeArray<>
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * constructor using the ComSafeArrayInArg() macro, you should use INPTR BSTR
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * as the SafeArray<> template argument, not just BSTR.
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync *
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * Arrays of interface pointers are also supported but they require to use a
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * special SafeArray implementation, com::SafeIfacePointer, which takes the
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * interface class name as a template argument (e.g. com::SafeIfacePointer
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * <IUnknown>). This implementation functions identically to com::SafeArray.
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync */
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#if defined (VBOX_WITH_XPCOM)
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync# include <nsMemory.h>
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#endif
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#include "VBox/com/defs.h"
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#include "VBox/com/ptr.h"
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#include "VBox/com/assert.h"
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#include "iprt/cpputils.h"
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#if defined (VBOX_WITH_XPCOM)
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync/**
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * Wraps the given com::SafeArray instance to generate an expression that is
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * suitable for passing it to functions that take input safearray parameters
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * declared using the ComSafeArrayIn macro.
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync *
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * @param aArray com::SafeArray instance to pass as an input parameter.
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync */
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#define ComSafeArrayAsInParam(aArray) \
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync (aArray).size(), (aArray).__asInParam_Arr ((aArray).raw())
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync/**
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * Wraps the given com::SafeArray instance to generate an expression that is
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * suitable for passing it to functions that take output safearray parameters
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * declared using the ComSafeArrayOut macro.
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync *
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * @param aArray com::SafeArray instance to pass as an output parameter.
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync */
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#define ComSafeArrayAsOutParam(aArray) \
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync (aArray).__asOutParam_Size(), (aArray).__asOutParam_Arr()
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#else /* defined (VBOX_WITH_XPCOM) */
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#define ComSafeArrayAsInParam(aArray) (aArray).__asInParam()
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#define ComSafeArrayAsOutParam(aArray) (aArray).__asOutParam()
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#endif /* defined (VBOX_WITH_XPCOM) */
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync/**
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync *
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync */
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsyncnamespace com
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync{
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync#if defined (VBOX_WITH_XPCOM)
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync////////////////////////////////////////////////////////////////////////////////
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync/**
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * Provides various helpers for SafeArray.
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync *
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * @param T Type of array elements.
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync */
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsynctemplate <typename T>
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsyncstruct SafeArrayTraits
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync{
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsyncprotected:
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync /** Initializes memory for aElem. */
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync static void Init (T &aElem) { aElem = 0; }
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync /** Initializes memory occupied by aElem. */
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync static void Uninit (T &aElem) { aElem = 0; }
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync /** Creates a deep copy of aFrom and stores it in aTo. */
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync static void Copy (const T &aFrom, T &aTo) { aTo = aFrom; }
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsyncpublic:
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync /* Magic to workaround strict rules of par. 4.4.4 of the C++ standard (that
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * in particular forbid casts of 'char **' to 'const char **'). Then initial
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * reason for this magic is that XPIDL declares input strings
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * (char/PRUnichar pointers) as const but doesn't do so for pointers to
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync * arrays. */
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync static T *__asInParam_Arr (T *aArr) { return aArr; }
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync static T *__asInParam_Arr (const T *aArr) { return const_cast <T *> (aArr); }
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync};
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsynctemplate <typename T>
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsyncstruct SafeArrayTraits <T *>
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync{
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync // Arbitrary pointers are not supported
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync};
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsynctemplate<>
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsyncstruct SafeArrayTraits <PRUnichar *>
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync{
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsyncprotected:
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync static void Init (PRUnichar * &aElem) { aElem = NULL; }
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync static void Uninit (PRUnichar * &aElem)
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync {
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync if (aElem)
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync {
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync ::SysFreeString (aElem);
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync aElem = NULL;
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync }
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync }
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync static void Copy (const PRUnichar * aFrom, PRUnichar * &aTo)
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync {
e4bf6817370e1a71833a02285515694afcda7599vboxsync AssertCompile (sizeof (PRUnichar) == sizeof (OLECHAR));
e4bf6817370e1a71833a02285515694afcda7599vboxsync aTo = aFrom ? ::SysAllocString ((const OLECHAR *) aFrom) : NULL;
e4bf6817370e1a71833a02285515694afcda7599vboxsync }
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsyncpublic:
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /* Magic to workaround strict rules of par. 4.4.4 of the C++ standard */
e4bf6817370e1a71833a02285515694afcda7599vboxsync static const PRUnichar **__asInParam_Arr (PRUnichar **aArr)
e4bf6817370e1a71833a02285515694afcda7599vboxsync {
e4bf6817370e1a71833a02285515694afcda7599vboxsync return const_cast <const PRUnichar **> (aArr);
1025ef7261a6961d07d390e85a095d806ccb88d9vboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync static const PRUnichar **__asInParam_Arr (const PRUnichar **aArr) { return aArr; }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync};
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsynctemplate<>
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsyncstruct SafeArrayTraits <const PRUnichar *>
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync{
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsyncprotected:
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync static void Init (const PRUnichar * &aElem) { aElem = NULL; }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync static void Uninit (const PRUnichar * &aElem)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (aElem)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync ::SysFreeString (const_cast <PRUnichar *> (aElem));
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync aElem = NULL;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync static void Copy (const PRUnichar * aFrom, const PRUnichar * &aTo)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync AssertCompile (sizeof (PRUnichar) == sizeof (OLECHAR));
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync aTo = aFrom ? ::SysAllocString ((const OLECHAR *) aFrom) : NULL;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsyncpublic:
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /* Magic to workaround strict rules of par. 4.4.4 of the C++ standard */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync static const PRUnichar **__asInParam_Arr (const PRUnichar **aArr) { return aArr; }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync};
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsynctemplate<>
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsyncstruct SafeArrayTraits <nsID *>
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync{
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsyncprotected:
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync static void Init (nsID * &aElem) { aElem = NULL; }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync static void Uninit (nsID * &aElem)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (aElem)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync ::nsMemory::Free (aElem);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync aElem = NULL;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync static void Copy (const nsID * aFrom, nsID * &aTo)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (aFrom)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync aTo = (nsID *) ::nsMemory::Alloc (sizeof (nsID));
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (aTo)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync *aTo = *aFrom;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync else
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync aTo = NULL;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /* This specification is also reused for SafeConstGUIDArray, so provide a
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * no-op Init() and Uninit() which are necessary for SafeArray<> but should
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * be never called in context of SafeConstGUIDArray. */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync static void Init (const nsID * &aElem) { NOREF (aElem); AssertFailed(); }
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync static void Uninit (const nsID * &aElem) { NOREF (aElem); AssertFailed(); }
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsyncpublic:
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /** Magic to workaround strict rules of par. 4.4.4 of the C++ standard. */
e4bf6817370e1a71833a02285515694afcda7599vboxsync static const nsID **__asInParam_Arr (nsID **aArr)
e4bf6817370e1a71833a02285515694afcda7599vboxsync {
e4bf6817370e1a71833a02285515694afcda7599vboxsync return const_cast <const nsID **> (aArr);
e4bf6817370e1a71833a02285515694afcda7599vboxsync }
e4bf6817370e1a71833a02285515694afcda7599vboxsync static const nsID **__asInParam_Arr (const nsID **aArr) { return aArr; }
e4bf6817370e1a71833a02285515694afcda7599vboxsync};
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync#else /* defined (VBOX_WITH_XPCOM) */
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync////////////////////////////////////////////////////////////////////////////////
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsyncstruct SafeArrayTraitsBase
5b0a093ca572a855886faa6747ad46df859dd041vboxsync{
5b0a093ca572a855886faa6747ad46df859dd041vboxsyncprotected:
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync static SAFEARRAY *CreateSafeArray (VARTYPE aVarType, SAFEARRAYBOUND *aBound)
5b0a093ca572a855886faa6747ad46df859dd041vboxsync { return SafeArrayCreate (aVarType, 1, aBound); }
5b0a093ca572a855886faa6747ad46df859dd041vboxsync};
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync/**
5b0a093ca572a855886faa6747ad46df859dd041vboxsync * Provides various helpers for SafeArray.
5b0a093ca572a855886faa6747ad46df859dd041vboxsync *
5b0a093ca572a855886faa6747ad46df859dd041vboxsync * @param T Type of array elements.
5b0a093ca572a855886faa6747ad46df859dd041vboxsync *
5b0a093ca572a855886faa6747ad46df859dd041vboxsync * Specializations of this template must provide the following methods:
5b0a093ca572a855886faa6747ad46df859dd041vboxsync *
5b0a093ca572a855886faa6747ad46df859dd041vboxsync // Returns the VARTYPE of COM SafeArray elements to be used for T
5b0a093ca572a855886faa6747ad46df859dd041vboxsync static VARTYPE VarType();
ad66a27959d7085aa31760f63ce082943be60e89vboxsync
ad66a27959d7085aa31760f63ce082943be60e89vboxsync // Returns the number of VarType() elements necessary for aSize
ad66a27959d7085aa31760f63ce082943be60e89vboxsync // elements of T
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync static ULONG VarCount (size_t aSize);
ad66a27959d7085aa31760f63ce082943be60e89vboxsync
ad66a27959d7085aa31760f63ce082943be60e89vboxsync // Returns the number of elements of T that fit into the given number of
ad66a27959d7085aa31760f63ce082943be60e89vboxsync // VarType() elements (opposite to VarCount (size_t aSize)).
ad66a27959d7085aa31760f63ce082943be60e89vboxsync static size_t Size (ULONG aVarCount);
ad66a27959d7085aa31760f63ce082943be60e89vboxsync
ad66a27959d7085aa31760f63ce082943be60e89vboxsync // Creates a deep copy of aFrom and stores it in aTo
ad66a27959d7085aa31760f63ce082943be60e89vboxsync static void Copy (ULONG aFrom, ULONG &aTo);
ad66a27959d7085aa31760f63ce082943be60e89vboxsync */
ad66a27959d7085aa31760f63ce082943be60e89vboxsynctemplate <typename T>
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsyncstruct SafeArrayTraits : public SafeArrayTraitsBase
ad66a27959d7085aa31760f63ce082943be60e89vboxsync{
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsyncprotected:
ad66a27959d7085aa31760f63ce082943be60e89vboxsync
c553cea6bfe2ce63ff5517ca4ec288502a890e99vboxsync // Arbitrary types are treated as passed by value and each value is
ad66a27959d7085aa31760f63ce082943be60e89vboxsync // represented by a number of VT_Ix type elements where VT_Ix has the
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync // biggest possible bitness necessary to represent T w/o a gap. COM enums
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync // fall into this category.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static VARTYPE VarType()
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync if (sizeof (T) % 8 == 0) return VT_I8;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync if (sizeof (T) % 4 == 0) return VT_I4;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync if (sizeof (T) % 2 == 0) return VT_I2;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync return VT_I1;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static ULONG VarCount (size_t aSize)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync if (sizeof (T) % 8 == 0) return (ULONG) ((sizeof (T) / 8) * aSize);
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync if (sizeof (T) % 4 == 0) return (ULONG) ((sizeof (T) / 4) * aSize);
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync if (sizeof (T) % 2 == 0) return (ULONG) ((sizeof (T) / 2) * aSize);
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync return (ULONG) (sizeof (T) * aSize);
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync }
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync static size_t Size (ULONG aVarCount)
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync {
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync if (sizeof (T) % 8 == 0) return (size_t) (aVarCount * 8) / sizeof (T);
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync if (sizeof (T) % 4 == 0) return (size_t) (aVarCount * 4) / sizeof (T);
5b0a093ca572a855886faa6747ad46df859dd041vboxsync if (sizeof (T) % 2 == 0) return (size_t) (aVarCount * 2) / sizeof (T);
ad66a27959d7085aa31760f63ce082943be60e89vboxsync return (size_t) aVarCount / sizeof (T);
5b0a093ca572a855886faa6747ad46df859dd041vboxsync }
ad66a27959d7085aa31760f63ce082943be60e89vboxsync
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync static void Copy (T aFrom, T &aTo) { aTo = aFrom; }
5b0a093ca572a855886faa6747ad46df859dd041vboxsync};
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsynctemplate <typename T>
5b0a093ca572a855886faa6747ad46df859dd041vboxsyncstruct SafeArrayTraits <T *>
ad66a27959d7085aa31760f63ce082943be60e89vboxsync{
5b0a093ca572a855886faa6747ad46df859dd041vboxsync // Arbitrary pointer types are not supported
ad66a27959d7085aa31760f63ce082943be60e89vboxsync};
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
ad66a27959d7085aa31760f63ce082943be60e89vboxsync/* Although the generic SafeArrayTraits template would work for all integers,
5b0a093ca572a855886faa6747ad46df859dd041vboxsync * we specialize it for some of them in order to use the correct VT_ type */
ad66a27959d7085aa31760f63ce082943be60e89vboxsync
3bb3e26b3306b9f62b18c17380bdf2ca3a98ca49vboxsynctemplate<>
3bb3e26b3306b9f62b18c17380bdf2ca3a98ca49vboxsyncstruct SafeArrayTraits <LONG> : public SafeArrayTraitsBase
5b0a093ca572a855886faa6747ad46df859dd041vboxsync{
ad66a27959d7085aa31760f63ce082943be60e89vboxsyncprotected:
ad66a27959d7085aa31760f63ce082943be60e89vboxsync
ad66a27959d7085aa31760f63ce082943be60e89vboxsync static VARTYPE VarType() { return VT_I4; }
ad66a27959d7085aa31760f63ce082943be60e89vboxsync static ULONG VarCount (size_t aSize) { return (ULONG) aSize; }
ad66a27959d7085aa31760f63ce082943be60e89vboxsync static size_t Size (ULONG aVarCount) { return (size_t) aVarCount; }
ad66a27959d7085aa31760f63ce082943be60e89vboxsync
ad66a27959d7085aa31760f63ce082943be60e89vboxsync static void Copy (LONG aFrom, LONG &aTo) { aTo = aFrom; }
ad66a27959d7085aa31760f63ce082943be60e89vboxsync};
e4bf6817370e1a71833a02285515694afcda7599vboxsync
ad66a27959d7085aa31760f63ce082943be60e89vboxsynctemplate<>
e4bf6817370e1a71833a02285515694afcda7599vboxsyncstruct SafeArrayTraits <ULONG> : public SafeArrayTraitsBase
e4bf6817370e1a71833a02285515694afcda7599vboxsync{
e4bf6817370e1a71833a02285515694afcda7599vboxsyncprotected:
e961f5bfe1727c6816d3dad3805ebe21b6ba1c64vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static VARTYPE VarType() { return VT_UI4; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static ULONG VarCount (size_t aSize) { return (ULONG) aSize; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static size_t Size (ULONG aVarCount) { return (size_t) aVarCount; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static void Copy (ULONG aFrom, ULONG &aTo) { aTo = aFrom; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync};
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsynctemplate<>
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsyncstruct SafeArrayTraits <LONG64> : public SafeArrayTraitsBase
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync{
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsyncprotected:
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static VARTYPE VarType() { return VT_I8; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static ULONG VarCount (size_t aSize) { return (ULONG) aSize; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static size_t Size (ULONG aVarCount) { return (size_t) aVarCount; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static void Copy (LONG64 aFrom, LONG64 &aTo) { aTo = aFrom; }
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync};
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsync
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsynctemplate<>
c58c758d3642ac45d3f12356c406c631fcd8f538vboxsyncstruct SafeArrayTraits <ULONG64> : public SafeArrayTraitsBase
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync{
4bf996d915405be92dc4394b2db1395e00e14d58vboxsyncprotected:
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync static VARTYPE VarType() { return VT_UI8; }
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync static ULONG VarCount (size_t aSize) { return (ULONG) aSize; }
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync static size_t Size (ULONG aVarCount) { return (size_t) aVarCount; }
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync static void Copy (ULONG64 aFrom, ULONG64 &aTo) { aTo = aFrom; }
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync};
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsynctemplate<>
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsyncstruct SafeArrayTraits <BSTR> : public SafeArrayTraitsBase
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync{
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsyncprotected:
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync static VARTYPE VarType() { return VT_BSTR; }
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync static ULONG VarCount (size_t aSize) { return (ULONG) aSize; }
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync static size_t Size (ULONG aVarCount) { return (size_t) aVarCount; }
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync static void Copy (BSTR aFrom, BSTR &aTo)
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync {
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync aTo = aFrom ? ::SysAllocString ((const OLECHAR *) aFrom) : NULL;
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync};
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsynctemplate<>
ad66a27959d7085aa31760f63ce082943be60e89vboxsyncstruct SafeArrayTraits <GUID> : public SafeArrayTraitsBase
ad66a27959d7085aa31760f63ce082943be60e89vboxsync{
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsyncprotected:
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync /* Use the 64-bit unsigned integer type for GUID */
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync static VARTYPE VarType() { return VT_UI8; }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync /* GUID is 128 bit, so we need two VT_UI8 */
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync static ULONG VarCount (size_t aSize)
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync {
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync AssertCompileSize (GUID, 16);
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync return (ULONG) (aSize * 2);
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync static size_t Size (ULONG aVarCount) { return (size_t) aVarCount / 2; }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync static void Copy (GUID aFrom, GUID &aTo) { aTo = aFrom; }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync};
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync/**
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * Helper for SafeArray::__asOutParam() that automatically updates m.raw after a
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * non-NULL m.arr assignment.
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync */
4bf996d915405be92dc4394b2db1395e00e14d58vboxsyncclass OutSafeArrayDipper
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync{
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync OutSafeArrayDipper (SAFEARRAY **aArr, void **aRaw)
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync : arr (aArr), raw (aRaw) { Assert (*aArr == NULL && *aRaw == NULL); }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync SAFEARRAY **arr;
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync void **raw;
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync template <class, class> friend class SafeArray;
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsyncpublic:
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync ~OutSafeArrayDipper()
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync {
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync if (*arr != NULL)
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync {
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync HRESULT rc = SafeArrayAccessData (*arr, raw);
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync AssertComRC (rc);
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync operator SAFEARRAY **() { return arr; }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync};
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync#endif /* defined (VBOX_WITH_XPCOM) */
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync////////////////////////////////////////////////////////////////////////////////
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync/**
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * The SafeArray class represents the safe array type used in COM to pass arrays
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * to/from interface methods.
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync *
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * This helper class hides all MSCOM/XPCOM specific implementation details and,
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * together with ComSafeArrayIn, ComSafeArrayOut and ComSafeArrayRet macros,
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * provides a platform-neutral way to handle safe arrays in the method
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * implementation.
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync *
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * When an instance of this class is destroyed, it automatically frees all
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * resources occupied by individual elements of the array as well as by the
e4bf6817370e1a71833a02285515694afcda7599vboxsync * array itself. However, when the value of an element is manually changed
e4bf6817370e1a71833a02285515694afcda7599vboxsync * using #operator[] or by accessing array data through the #raw() pointer, it is
e4bf6817370e1a71833a02285515694afcda7599vboxsync * the caller's responsibility to free resources occupied by the previous
e4bf6817370e1a71833a02285515694afcda7599vboxsync * element's value.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Also, objects of this class do not support copy and assignment operations and
e4bf6817370e1a71833a02285515694afcda7599vboxsync * therefore cannot be returned from functions by value. In other words, this
e4bf6817370e1a71833a02285515694afcda7599vboxsync * class is just a temporary storage for handling interface method calls and not
e4bf6817370e1a71833a02285515694afcda7599vboxsync * intended to be used to store arrays as data members and such -- you should
e4bf6817370e1a71833a02285515694afcda7599vboxsync * use normal list/vector classes for that.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @note The current implementation supports only one-dimensional arrays.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @note This class is not thread-safe.
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
e4bf6817370e1a71833a02285515694afcda7599vboxsynctemplate <typename T, class Traits = SafeArrayTraits <T> >
e4bf6817370e1a71833a02285515694afcda7599vboxsyncclass SafeArray : public Traits
e4bf6817370e1a71833a02285515694afcda7599vboxsync{
e4bf6817370e1a71833a02285515694afcda7599vboxsyncpublic:
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /**
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Creates a null array.
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
e4bf6817370e1a71833a02285515694afcda7599vboxsync SafeArray() {}
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /**
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Creates a new array of the given size. All elements of the newly created
e4bf6817370e1a71833a02285515694afcda7599vboxsync * array initialized with null values.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @param aSize Initial number of elements in the array.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @note If this object remains null after construction it means that there
e4bf6817370e1a71833a02285515694afcda7599vboxsync * was not enough memory for creating an array of the requested size.
e4bf6817370e1a71833a02285515694afcda7599vboxsync * The constructor will also assert in this case.
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
e4bf6817370e1a71833a02285515694afcda7599vboxsync SafeArray (size_t aSize) { resize (aSize); }
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /**
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Weakly attaches this instance to the existing array passed in a method
e4bf6817370e1a71833a02285515694afcda7599vboxsync * parameter declared using the ComSafeArrayIn macro. When using this call,
e4bf6817370e1a71833a02285515694afcda7599vboxsync * always wrap the parameter name in the ComSafeArrayInArg macro call like
e4bf6817370e1a71833a02285515694afcda7599vboxsync * this:
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * <pre>
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * SafeArray safeArray (ComSafeArrayInArg (aArg));
e4bf6817370e1a71833a02285515694afcda7599vboxsync * </pre>
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Note that this constructor doesn't take the ownership of the array. In
e4bf6817370e1a71833a02285515694afcda7599vboxsync * particular, it means that operations that operate on the ownership (e.g.
e4bf6817370e1a71833a02285515694afcda7599vboxsync * #detachTo()) are forbidden and will assert.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @param aArg Input method parameter to attach to.
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
e4bf6817370e1a71833a02285515694afcda7599vboxsync SafeArray (ComSafeArrayIn (T, aArg))
e4bf6817370e1a71833a02285515694afcda7599vboxsync {
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#if defined (VBOX_WITH_XPCOM)
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync AssertReturnVoid (aArg != NULL);
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync m.size = aArgSize;
e4bf6817370e1a71833a02285515694afcda7599vboxsync m.arr = aArg;
e4bf6817370e1a71833a02285515694afcda7599vboxsync m.isWeak = true;
e4bf6817370e1a71833a02285515694afcda7599vboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#else /* defined (VBOX_WITH_XPCOM) */
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync AssertReturnVoid (aArg != NULL);
e4bf6817370e1a71833a02285515694afcda7599vboxsync SAFEARRAY *arg = *aArg;
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync if (arg)
e4bf6817370e1a71833a02285515694afcda7599vboxsync {
e4bf6817370e1a71833a02285515694afcda7599vboxsync AssertReturnVoid (arg->cDims == 1);
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync VARTYPE vt;
e4bf6817370e1a71833a02285515694afcda7599vboxsync HRESULT rc = SafeArrayGetVartype (arg, &vt);
e4bf6817370e1a71833a02285515694afcda7599vboxsync AssertComRCReturnVoid (rc);
e4bf6817370e1a71833a02285515694afcda7599vboxsync AssertMsgReturnVoid (vt == VarType(),
e4bf6817370e1a71833a02285515694afcda7599vboxsync ("Expected vartype %d, got %d.\n",
e4bf6817370e1a71833a02285515694afcda7599vboxsync VarType(), vt));
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync rc = SafeArrayAccessData (arg, (void HUGEP **) &m.raw);
e4bf6817370e1a71833a02285515694afcda7599vboxsync AssertComRCReturnVoid (rc);
e4bf6817370e1a71833a02285515694afcda7599vboxsync }
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync m.arr = arg;
e4bf6817370e1a71833a02285515694afcda7599vboxsync m.isWeak = true;
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync#endif /* defined (VBOX_WITH_XPCOM) */
e4bf6817370e1a71833a02285515694afcda7599vboxsync }
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /**
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Creates a deep copy of the given standard C++ container.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @param aCntr Container object to copy.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @param C Standard C++ container template class (normally deduced from
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @c aCntr).
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync template <template <typename, typename> class C, class A>
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync SafeArray (const C <T, A> & aCntr)
e4bf6817370e1a71833a02285515694afcda7599vboxsync {
e4bf6817370e1a71833a02285515694afcda7599vboxsync resize (aCntr.size());
e4bf6817370e1a71833a02285515694afcda7599vboxsync AssertReturnVoid (!isNull());
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync size_t i = 0;
e4bf6817370e1a71833a02285515694afcda7599vboxsync for (typename C <T, A>::const_iterator it = aCntr.begin();
e4bf6817370e1a71833a02285515694afcda7599vboxsync it != aCntr.end(); ++ it, ++ i)
e4bf6817370e1a71833a02285515694afcda7599vboxsync#if defined (VBOX_WITH_XPCOM)
e4bf6817370e1a71833a02285515694afcda7599vboxsync Copy (*it, m.arr [i]);
e4bf6817370e1a71833a02285515694afcda7599vboxsync#else
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync Copy (*it, m.raw [i]);
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#endif
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync }
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /**
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Destroys this instance after calling #setNull() to release allocated
e4bf6817370e1a71833a02285515694afcda7599vboxsync * resources. See #setNull() for more details.
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
e4bf6817370e1a71833a02285515694afcda7599vboxsync virtual ~SafeArray() { setNull(); }
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /**
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Returns @c true if this instance represents a null array.
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
e4bf6817370e1a71833a02285515694afcda7599vboxsync bool isNull() const { return m.arr == NULL; }
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /**
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Resets this instance to null and, if this instance is not a weak one,
e4bf6817370e1a71833a02285515694afcda7599vboxsync * releases any resources occupied by the array data.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @note This method destroys (cleans up) all elements of the array using
e4bf6817370e1a71833a02285515694afcda7599vboxsync * the corresponding cleanup routine for the element type before the
e4bf6817370e1a71833a02285515694afcda7599vboxsync * array itself is destroyed.
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
e4bf6817370e1a71833a02285515694afcda7599vboxsync virtual void setNull() { m.uninit(); }
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /**
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Returns @c true if this instance is weak. A weak instance doesn't own the
e4bf6817370e1a71833a02285515694afcda7599vboxsync * array data and therefore operations manipulating the ownership (e.g.
e4bf6817370e1a71833a02285515694afcda7599vboxsync * #detachTo()) are forbidden and will assert.
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
e4bf6817370e1a71833a02285515694afcda7599vboxsync bool isWeak() const { return m.isWeak; }
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /** Number of elements in the array. */
e4bf6817370e1a71833a02285515694afcda7599vboxsync size_t size() const
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#if defined (VBOX_WITH_XPCOM)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (m.arr)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync return m.size;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync return 0;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#else
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (m.arr)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync return Size (m.arr->rgsabound [0].cElements);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync return 0;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#endif
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /**
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * Appends a copy of the given element at the end of the array.
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync *
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * The array size is increased by one by this method and the additional
e4bf6817370e1a71833a02285515694afcda7599vboxsync * space is allocated as needed.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * This method is handy in cases where you want to assign a copy of the
e4bf6817370e1a71833a02285515694afcda7599vboxsync * existing value to the array element, for example:
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * <tt>Bstr string; array.push_back (string);</tt>. If you create a string
e4bf6817370e1a71833a02285515694afcda7599vboxsync * just to put it to the array, you may find #appendedRaw() more useful.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @param aElement Element to append.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @return @c true on success and false if there is not enough
e4bf6817370e1a71833a02285515694afcda7599vboxsync * memory for resizing.
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync bool push_back (const T &aElement)
e4bf6817370e1a71833a02285515694afcda7599vboxsync {
e4bf6817370e1a71833a02285515694afcda7599vboxsync if (!ensureCapacity (size() + 1))
e4bf6817370e1a71833a02285515694afcda7599vboxsync return false;
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync#if defined (VBOX_WITH_XPCOM)
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync Copy (aElement, m.arr [m.size]);
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync ++ m.size;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#else
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync Copy (aElement, m.raw [size() - 1]);
e4bf6817370e1a71833a02285515694afcda7599vboxsync#endif
e4bf6817370e1a71833a02285515694afcda7599vboxsync return true;
e4bf6817370e1a71833a02285515694afcda7599vboxsync }
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /**
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Appends an empty element at the end of the array and returns a raw
e4bf6817370e1a71833a02285515694afcda7599vboxsync * pointer to it suitable for assigning a raw value (w/o constructing a
e4bf6817370e1a71833a02285515694afcda7599vboxsync * copy).
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * The array size is increased by one by this method and the additional
e4bf6817370e1a71833a02285515694afcda7599vboxsync * space is allocated as needed.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
3bb3e26b3306b9f62b18c17380bdf2ca3a98ca49vboxsync * Note that in case of raw assignment, value ownership (for types with
e4bf6817370e1a71833a02285515694afcda7599vboxsync * dynamically allocated data and for interface pointers) is transferred to
e4bf6817370e1a71833a02285515694afcda7599vboxsync * the safe array object.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * This method is handy for operations like
e4bf6817370e1a71833a02285515694afcda7599vboxsync * <tt>Bstr ("foo").detacTo (array.appendedRaw());</tt>. Don't use it as
e4bf6817370e1a71833a02285515694afcda7599vboxsync * l-value (<tt>array.appendedRaw() = SysAllocString (L"tralala");</tt>)
e4bf6817370e1a71833a02285515694afcda7599vboxsync * since this doesn't check for a NULL condition; use #resize() and
e4bf6817370e1a71833a02285515694afcda7599vboxsync * #setRawAt() instead. If you need to assign a copy of the existing value
e4bf6817370e1a71833a02285515694afcda7599vboxsync * instead of transferring the ownership, look at #push_back().
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @return Raw pointer to the added element or NULL if no memory.
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
e4bf6817370e1a71833a02285515694afcda7599vboxsync T *appendedRaw()
e4bf6817370e1a71833a02285515694afcda7599vboxsync {
e4bf6817370e1a71833a02285515694afcda7599vboxsync if (!ensureCapacity (size() + 1))
e4bf6817370e1a71833a02285515694afcda7599vboxsync return NULL;
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync#if defined (VBOX_WITH_XPCOM)
e4bf6817370e1a71833a02285515694afcda7599vboxsync Init (m.arr [m.size]);
e4bf6817370e1a71833a02285515694afcda7599vboxsync ++ m.size;
e4bf6817370e1a71833a02285515694afcda7599vboxsync return &m.arr [m.size - 1];
e4bf6817370e1a71833a02285515694afcda7599vboxsync#else
e4bf6817370e1a71833a02285515694afcda7599vboxsync /* nothing to do here, SafeArrayCreate() has performed element
e4bf6817370e1a71833a02285515694afcda7599vboxsync * initialization */
e4bf6817370e1a71833a02285515694afcda7599vboxsync return &m.raw [size() - 1];
e4bf6817370e1a71833a02285515694afcda7599vboxsync#endif
e4bf6817370e1a71833a02285515694afcda7599vboxsync }
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync /**
e4bf6817370e1a71833a02285515694afcda7599vboxsync * Resizes the array preserving its contents when possible. If the new size
e4bf6817370e1a71833a02285515694afcda7599vboxsync * is larget than the old size, new elements are initialized with null
e4bf6817370e1a71833a02285515694afcda7599vboxsync * values. If the new size is less than the old size, the contents of the
e4bf6817370e1a71833a02285515694afcda7599vboxsync * array beyond the new size is lost.
e4bf6817370e1a71833a02285515694afcda7599vboxsync *
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @param aNewSize New number of elements in the array.
e4bf6817370e1a71833a02285515694afcda7599vboxsync * @return @c true on success and false if there is not enough
e4bf6817370e1a71833a02285515694afcda7599vboxsync * memory for resizing.
e4bf6817370e1a71833a02285515694afcda7599vboxsync */
e4bf6817370e1a71833a02285515694afcda7599vboxsync bool resize (size_t aNewSize)
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync {
e4bf6817370e1a71833a02285515694afcda7599vboxsync if (!ensureCapacity (aNewSize))
e4bf6817370e1a71833a02285515694afcda7599vboxsync return false;
e4bf6817370e1a71833a02285515694afcda7599vboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#if defined (VBOX_WITH_XPCOM)
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync if (m.size < aNewSize)
e4bf6817370e1a71833a02285515694afcda7599vboxsync {
e4bf6817370e1a71833a02285515694afcda7599vboxsync /* initialize the new elements */
e4bf6817370e1a71833a02285515694afcda7599vboxsync for (size_t i = m.size; i < aNewSize; ++ i)
e4bf6817370e1a71833a02285515694afcda7599vboxsync Init (m.arr [i]);
e4bf6817370e1a71833a02285515694afcda7599vboxsync }
e4bf6817370e1a71833a02285515694afcda7599vboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync m.size = aNewSize;
e4bf6817370e1a71833a02285515694afcda7599vboxsync#else
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync /* nothing to do here, SafeArrayCreate() has performed element
e4bf6817370e1a71833a02285515694afcda7599vboxsync * initialization */
e4bf6817370e1a71833a02285515694afcda7599vboxsync#endif
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync return true;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync }
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync /**
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * Reinitializes this instance by preallocating space for the given number
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * of elements. The previous array contents is lost.
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync *
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * @param aNewSize New number of elements in the array.
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * @return @c true on success and false if there is not enough
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * memory for resizing.
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync */
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync bool reset (size_t aNewSize)
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync {
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync m.uninit();
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync return resize (aNewSize);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync /**
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * Returns a pointer to the raw array data. Use this raw pointer with care
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * as no type or bound checking is done for you in this case.
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync *
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * @note This method returns @c NULL when this instance is null.
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * @see #operator[]
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync */
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync T *raw()
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync {
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#if defined (VBOX_WITH_XPCOM)
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync return m.arr;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#else
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync return m.raw;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#endif
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync }
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /**
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * Const version of #raw().
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync */
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync const T *raw() const
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync {
e4bf6817370e1a71833a02285515694afcda7599vboxsync#if defined (VBOX_WITH_XPCOM)
e4bf6817370e1a71833a02285515694afcda7599vboxsync return m.arr;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#else
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync return m.raw;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#endif
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync /**
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * Array access operator that returns an array element by reference. A bit
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * safer than #raw(): asserts and returns an invalid reference if this
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * instance is null or if the index is out of bounds.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync *
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * @note For weak instances, this call will succeed but the behavior of
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * changing the contents of an element of the weak array instance is
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * undefined and may lead to a program crash on some platforms.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync T &operator[] (size_t aIdx)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync AssertReturn (m.arr != NULL, *((T *) NULL));
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync AssertReturn (aIdx < size(), *((T *) NULL));
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#if defined (VBOX_WITH_XPCOM)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync return m.arr [aIdx];
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#else
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync AssertReturn (m.raw != NULL, *((T *) NULL));
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync return m.raw [aIdx];
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#endif
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync /**
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * Const version of #operator[] that returns an array element by value.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync const T operator[] (size_t aIdx) const
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync AssertReturn (m.arr != NULL, *((T *) NULL));
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync AssertReturn (aIdx < size(), *((T *) NULL));
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#if defined (VBOX_WITH_XPCOM)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync return m.arr [aIdx];
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#else
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync AssertReturn (m.raw != NULL, *((T *) NULL));
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync return m.raw [aIdx];
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#endif
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync }
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync /**
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * Creates a copy of this array and stores it in a method parameter declared
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * using the ComSafeArrayOut macro. When using this call, always wrap the
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * parameter name in the ComSafeArrayOutArg macro call like this:
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * <pre>
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * safeArray.cloneTo (ComSafeArrayOutArg (aArg));
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * </pre>
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync *
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * @note It is assumed that the ownership of the returned copy is
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * transferred to the caller of the method and he is responsible to free the
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * array data when it is no more necessary.
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync *
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * @param aArg Output method parameter to clone to.
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync */
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync virtual const SafeArray &cloneTo (ComSafeArrayOut (T, aArg)) const
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync {
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync /// @todo Implement me!
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#if defined (VBOX_WITH_XPCOM)
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync NOREF (aArgSize);
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync NOREF (aArg);
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#else
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync NOREF (aArg);
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#endif
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync AssertFailedReturn (*this);
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync }
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync /**
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * Transfers the ownership of this array's data to the specified location
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * declared using the ComSafeArrayOut macro and makes this array a null
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * array. When using this call, always wrap the parameter name in the
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * ComSafeArrayOutArg macro call like this:
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * <pre>
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * safeArray.detachTo (ComSafeArrayOutArg (aArg));
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * </pre>
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync *
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * Detaching the null array is also possible in which case the location will
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * receive NULL.
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync *
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * @note Since the ownership of the array data is transferred to the
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * caller of the method, he is responsible to free the array data when it is
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * no more necessary.
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync *
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync * @param aArg Location to detach to.
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync */
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync virtual SafeArray &detachTo (ComSafeArrayOut (T, aArg))
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync {
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync AssertReturn (m.isWeak == false, *this);
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#if defined (VBOX_WITH_XPCOM)
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync AssertReturn (aArgSize != NULL, *this);
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync AssertReturn (aArg != NULL, *this);
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync *aArgSize = m.size;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync *aArg = m.arr;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync m.isWeak = false;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync m.size = 0;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync m.arr = NULL;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#else /* defined (VBOX_WITH_XPCOM) */
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync AssertReturn (aArg != NULL, *this);
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync *aArg = m.arr;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync if (m.raw)
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync {
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync HRESULT rc = SafeArrayUnaccessData (m.arr);
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync AssertComRCReturn (rc, *this);
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync m.raw = NULL;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync }
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync m.isWeak = false;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync m.arr = NULL;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync#endif /* defined (VBOX_WITH_XPCOM) */
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync return *this;
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync }
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync // public methods for internal purposes only
725fba5c64717677ac66072bae37e5b3686f3e6dvboxsync
e4bf6817370e1a71833a02285515694afcda7599vboxsync#if defined (VBOX_WITH_XPCOM)
e4bf6817370e1a71833a02285515694afcda7599vboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /** Internal function. Never call it directly. */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync PRUint32 *__asOutParam_Size() { setNull(); return &m.size; }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /** Internal function Never call it directly. */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync T **__asOutParam_Arr() { Assert (isNull()); return &m.arr; }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#else /* defined (VBOX_WITH_XPCOM) */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /** Internal function Never call it directly. */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync SAFEARRAY ** __asInParam() { return &m.arr; }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /** Internal function Never call it directly. */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync OutSafeArrayDipper __asOutParam()
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync { setNull(); return OutSafeArrayDipper (&m.arr, (void **) &m.raw); }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#endif /* defined (VBOX_WITH_XPCOM) */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync static const SafeArray Null;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsyncprotected:
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync DECLARE_CLS_COPY_CTOR_ASSIGN_NOOP(SafeArray)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /**
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * Ensures that the array is big enough to contaon aNewSize elements.
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync *
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * If the new size is greater than the current capacity, a new array is
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * allocated and elements from the old array are copied over. The size of
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * the array doesn't change, only the capacity increases (which is always
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * greater than the size). Note that the additionally allocated elements are
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * left uninitialized by this method.
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync *
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * If the new size is less than the current size, the existing array is
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * truncated to the specified size and the elements outside the new array
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * boundary are freed.
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync *
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * If the new size is the same as the current size, nothing happens.
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync *
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * @param aNewSize New size of the array.
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync *
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * @return @c true on success and @c false if not enough memory.
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync bool ensureCapacity (size_t aNewSize)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync AssertReturn (!m.isWeak, false);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#if defined (VBOX_WITH_XPCOM)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /* Note: we distinguish between a null array and an empty (zero
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * elements) array. Therefore we never use zero in malloc (even if
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * aNewSize is zero) to make sure we get a non-null pointer. */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (m.size == aNewSize && m.arr != NULL)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync return true;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /* allocate in 16-byte pieces */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync size_t newCapacity = RT_MAX ((aNewSize + 15) / 16 * 16, 16);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (m.capacity != newCapacity)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync T *newArr = (T *) nsMemory::Alloc (RT_MAX (newCapacity, 1) * sizeof (T));
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync AssertReturn (newArr != NULL, false);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (m.arr != NULL)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (m.size > aNewSize)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /* truncation takes place, uninit exceeding elements and
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * shrink the size */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync for (size_t i = aNewSize; i < m.size; ++ i)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync Uninit (m.arr [i]);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync m.size = aNewSize;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /* copy the old contents */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync memcpy (newArr, m.arr, m.size * sizeof (T));
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync nsMemory::Free ((void *) m.arr);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync m.arr = newArr;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync else
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (m.size > aNewSize)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync /* truncation takes place, uninit exceeding elements and
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * shrink the size */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync for (size_t i = aNewSize; i < m.size; ++ i)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync Uninit (m.arr [i]);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync m.size = aNewSize;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync m.capacity = newCapacity;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#else
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync SAFEARRAYBOUND bound = { VarCount (aNewSize), 0 };
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync HRESULT rc;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (m.arr == NULL)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync m.arr = CreateSafeArray (VarType(), &bound);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync AssertReturn (m.arr != NULL, false);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync else
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync SafeArrayUnaccessData (m.arr);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync rc = SafeArrayRedim (m.arr, &bound);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync AssertComRCReturn (rc == S_OK, false);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync rc = SafeArrayAccessData (m.arr, (void HUGEP **) &m.raw);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync AssertComRCReturn (rc, false);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#endif
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync return true;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync struct Data
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync Data()
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync : isWeak (false)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#if defined (VBOX_WITH_XPCOM)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync , capacity (0), size (0), arr (NULL)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#else
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync , arr (NULL), raw (NULL)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#endif
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {}
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync ~Data() { uninit(); }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync void uninit()
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#if defined (VBOX_WITH_XPCOM)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (arr)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (!isWeak)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync for (size_t i = 0; i < size; ++ i)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync Uninit (arr [i]);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync nsMemory::Free ((void *) arr);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync else
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync isWeak = false;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync arr = NULL;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync size = capacity = 0;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync#else /* defined (VBOX_WITH_XPCOM) */
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (arr)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (raw)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync SafeArrayUnaccessData (arr);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync raw = NULL;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync if (!isWeak)
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync {
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync HRESULT rc = SafeArrayDestroy (arr);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync AssertComRCReturnVoid (rc);
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync else
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync isWeak = false;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync arr = NULL;
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#endif /* defined (VBOX_WITH_XPCOM) */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync bool isWeak : 1;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#if defined (VBOX_WITH_XPCOM)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync PRUint32 capacity;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync PRUint32 size;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync T *arr;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#else
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync SAFEARRAY *arr;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync T *raw;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#endif
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync };
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync Data m;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync};
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync////////////////////////////////////////////////////////////////////////////////
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync#if defined (VBOX_WITH_XPCOM)
4e47bb772df0d04d1ded3e06354de547d52e2d06vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync/**
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * Version of com::SafeArray for arrays of GUID.
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync *
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * In MS COM, GUID arrays store GUIDs by value and therefore input arrays are
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * represented using |GUID *| and out arrays -- using |GUID **|. In XPCOM,
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * GUID arrays store pointers to nsID so that input arrays are |const nsID **|
113a43aca041000560f93f9a8ee23dfcf01a9e7cvboxsync * and out arrays are |nsID ***|. Due to this difference, it is impossible to
3bb3e26b3306b9f62b18c17380bdf2ca3a98ca49vboxsync * work with arrays of GUID on both platforms by simply using com::SafeArray
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * <GUID>. This class is intended to provide some level of cross-platform
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * behavior.
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync *
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * The basic usage pattern is basically similar to com::SafeArray<> except that
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * you use ComSafeGUIDArrayIn* and ComSafeGUIDArrayOut* macros instead of
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * ComSafeArrayIn* and ComSafeArrayOut*. Another important nuance is that the
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * raw() array type is different (nsID **, or GUID ** on XPCOM and GUID * on MS
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * COM) so it is recommended to use operator[] instead that always returns a
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * GUID by value.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync *
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * Note that due to const modifiers, you cannot use SafeGUIDArray for input GUID
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * arrays. Please use SafeConstGUIDArray for this instead.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync *
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * Other than mentioned above, the functionality of this class is equivalent to
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * com::SafeArray<>. See the description of that template and its methods for
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * more information.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync *
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * Output GUID arrays are handled by a separate class, SafeGUIDArrayOut, since
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * this class cannot handle them because of const modifiers.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsyncclass SafeGUIDArray : public SafeArray <nsID *>
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync{
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsyncpublic:
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync typedef SafeArray <nsID *> Base;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync class nsIDRef
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync public:
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync nsIDRef (nsID * &aVal) : mVal (aVal) {}
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync operator const nsID &() const { return mVal ? *mVal : *Empty; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync operator nsID() const { return mVal ? *mVal : *Empty; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync const nsID *operator&() const { return mVal ? mVal : Empty; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync nsIDRef &operator= (const nsID &aThat)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync if (mVal == NULL)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync Copy (&aThat, mVal);
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync else
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync *mVal = aThat;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync return *this;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync private:
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync nsID * &mVal;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static const nsID *Empty;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync friend class SafeGUIDArray;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync };
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync /** See SafeArray<>::SafeArray(). */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync SafeGUIDArray() {}
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync /** See SafeArray<>::SafeArray (size_t). */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync SafeGUIDArray (size_t aSize) : Base (aSize) {}
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync /**
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * Array access operator that returns an array element by reference. As a
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * special case, the return value of this operator on XPCOM is a nsID (GUID)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * reference, instead of a nsID pointer (the actual SafeArray template
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * argument), for compatibility with the MS COM version.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync *
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * The rest is equivalent to SafeArray<>::operator[].
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync nsIDRef operator[] (size_t aIdx)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync Assert (m.arr != NULL);
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync Assert (aIdx < size());
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync return nsIDRef (m.arr [aIdx]);
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync /**
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * Const version of #operator[] that returns an array element by value.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync const nsID &operator[] (size_t aIdx) const
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync Assert (m.arr != NULL);
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync Assert (aIdx < size());
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync return m.arr [aIdx] ? *m.arr [aIdx] : *nsIDRef::Empty;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync};
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync/**
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * Version of com::SafeArray for const arrays of GUID.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync *
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * This class is used to work with input GUID array parameters in method
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * implementations. See SafeGUIDArray for more details.
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsyncclass SafeConstGUIDArray : public SafeArray <const nsID *,
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync SafeArrayTraits <nsID *> >
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync{
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsyncpublic:
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync typedef SafeArray <const nsID *, SafeArrayTraits <nsID *> > Base;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync /** See SafeArray<>::SafeArray(). */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync SafeConstGUIDArray() {}
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync /* See SafeArray<>::SafeArray (ComSafeArrayIn (T, aArg)). */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync SafeConstGUIDArray (ComSafeGUIDArrayIn (aArg))
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync : Base (ComSafeGUIDArrayInArg (aArg)) {}
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync /**
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * Array access operator that returns an array element by reference. As a
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * special case, the return value of this operator on XPCOM is nsID (GUID)
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync * instead of nsID *, for compatibility with the MS COM version.
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync *
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * The rest is equivalent to SafeArray<>::operator[].
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync const nsID &operator[] (size_t aIdx) const
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync AssertReturn (m.arr != NULL, **((const nsID * *) NULL));
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync AssertReturn (aIdx < size(), **((const nsID * *) NULL));
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync return *m.arr [aIdx];
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsyncprivate:
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync /* These are disabled because of const */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync bool reset (size_t aNewSize) { NOREF (aNewSize); return false; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync};
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#else /* defined (VBOX_WITH_XPCOM) */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsynctypedef SafeArray <GUID> SafeGUIDArray;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsynctypedef SafeArray <const GUID, SafeArrayTraits <GUID> > SafeConstGUIDArray;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#endif /* defined (VBOX_WITH_XPCOM) */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync////////////////////////////////////////////////////////////////////////////////
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#if defined (VBOX_WITH_XPCOM)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsynctemplate <class I>
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsyncstruct SafeIfaceArrayTraits
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync{
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsyncprotected:
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static void Init (I * &aElem) { aElem = NULL; }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static void Uninit (I * &aElem)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync if (aElem)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync aElem->Release();
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync aElem = NULL;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync static void Copy (I * aFrom, I * &aTo)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync if (aFrom != NULL)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync aTo = aFrom;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync aTo->AddRef();
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync }
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync else
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync aTo = NULL;
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsyncpublic:
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync /* Magic to workaround strict rules of par. 4.4.4 of the C++ standard. */
5b0a093ca572a855886faa6747ad46df859dd041vboxsync static I **__asInParam_Arr (I **aArr) { return aArr; }
5b0a093ca572a855886faa6747ad46df859dd041vboxsync static I **__asInParam_Arr (const I **aArr) { return const_cast <I **> (aArr); }
5b0a093ca572a855886faa6747ad46df859dd041vboxsync};
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync#else /* defined (VBOX_WITH_XPCOM) */
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsynctemplate <class I>
5b0a093ca572a855886faa6747ad46df859dd041vboxsyncstruct SafeIfaceArrayTraits
5b0a093ca572a855886faa6747ad46df859dd041vboxsync{
5b0a093ca572a855886faa6747ad46df859dd041vboxsyncprotected:
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync static VARTYPE VarType() { return VT_UNKNOWN; }
5b0a093ca572a855886faa6747ad46df859dd041vboxsync static ULONG VarCount (size_t aSize) { return (ULONG) aSize; }
5b0a093ca572a855886faa6747ad46df859dd041vboxsync static size_t Size (ULONG aVarCount) { return (size_t) aVarCount; }
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync static void Copy (I * aFrom, I * &aTo)
5b0a093ca572a855886faa6747ad46df859dd041vboxsync {
5b0a093ca572a855886faa6747ad46df859dd041vboxsync if (aFrom != NULL)
5b0a093ca572a855886faa6747ad46df859dd041vboxsync {
5b0a093ca572a855886faa6747ad46df859dd041vboxsync aTo = aFrom;
5b0a093ca572a855886faa6747ad46df859dd041vboxsync aTo->AddRef();
5b0a093ca572a855886faa6747ad46df859dd041vboxsync }
5b0a093ca572a855886faa6747ad46df859dd041vboxsync else
5b0a093ca572a855886faa6747ad46df859dd041vboxsync aTo = NULL;
5b0a093ca572a855886faa6747ad46df859dd041vboxsync }
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync static SAFEARRAY *CreateSafeArray (VARTYPE aVarType, SAFEARRAYBOUND *aBound)
5b0a093ca572a855886faa6747ad46df859dd041vboxsync {
5b0a093ca572a855886faa6747ad46df859dd041vboxsync NOREF (aVarType);
5b0a093ca572a855886faa6747ad46df859dd041vboxsync return SafeArrayCreateEx (VT_UNKNOWN, 1, aBound, (PVOID) &_ATL_IIDOF (I));
5b0a093ca572a855886faa6747ad46df859dd041vboxsync }
5b0a093ca572a855886faa6747ad46df859dd041vboxsync};
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
3bb3e26b3306b9f62b18c17380bdf2ca3a98ca49vboxsync#endif /* defined (VBOX_WITH_XPCOM) */
3bb3e26b3306b9f62b18c17380bdf2ca3a98ca49vboxsync
3bb3e26b3306b9f62b18c17380bdf2ca3a98ca49vboxsync////////////////////////////////////////////////////////////////////////////////
3bb3e26b3306b9f62b18c17380bdf2ca3a98ca49vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync/**
5b0a093ca572a855886faa6747ad46df859dd041vboxsync * Version of com::SafeArray for arrays of interface pointers.
5b0a093ca572a855886faa6747ad46df859dd041vboxsync *
5b0a093ca572a855886faa6747ad46df859dd041vboxsync * Except that it manages arrays of interface pointers, the usage of this class
70aa086e9e9d2f85d2e997d0e69169018a001e54vboxsync * is identical to com::SafeArray.
5b0a093ca572a855886faa6747ad46df859dd041vboxsync *
5b0a093ca572a855886faa6747ad46df859dd041vboxsync * @param I Interface class (no asterisk).
5b0a093ca572a855886faa6747ad46df859dd041vboxsync */
5b0a093ca572a855886faa6747ad46df859dd041vboxsynctemplate <class I>
5b0a093ca572a855886faa6747ad46df859dd041vboxsyncclass SafeIfaceArray : public SafeArray <I *, SafeIfaceArrayTraits <I> >
5b0a093ca572a855886faa6747ad46df859dd041vboxsync{
5b0a093ca572a855886faa6747ad46df859dd041vboxsyncpublic:
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync typedef SafeArray <I *, SafeIfaceArrayTraits <I> > Base;
5b0a093ca572a855886faa6747ad46df859dd041vboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync /**
5b0a093ca572a855886faa6747ad46df859dd041vboxsync * Creates a null array.
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync */
d3dea25ec07f6546715fe3af943ea863294b392evboxsync SafeIfaceArray() {}
d3dea25ec07f6546715fe3af943ea863294b392evboxsync
5b0a093ca572a855886faa6747ad46df859dd041vboxsync /**
70aa086e9e9d2f85d2e997d0e69169018a001e54vboxsync * Creates a new array of the given size. All elements of the newly created
5b0a093ca572a855886faa6747ad46df859dd041vboxsync * array initialized with null values.
5b0a093ca572a855886faa6747ad46df859dd041vboxsync *
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * @param aSize Initial number of elements in the array. Must be greater
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * than 0.
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync *
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * @note If this object remains null after construction it means that there
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * was not enough memory for creating an array of the requested size.
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * The constructor will also assert in this case.
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync */
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync SafeIfaceArray (size_t aSize) { resize (aSize); }
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync /**
4e47bb772df0d04d1ded3e06354de547d52e2d06vboxsync * Weakly attaches this instance to the existing array passed in a method
4e47bb772df0d04d1ded3e06354de547d52e2d06vboxsync * parameter declared using the ComSafeArrayIn macro. When using this call,
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * always wrap the parameter name in the ComSafeArrayOutArg macro call like
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * this:
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * <pre>
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * SafeArray safeArray (ComSafeArrayInArg (aArg));
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * </pre>
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync *
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * Note that this constructor doesn't take the ownership of the array. In
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * particular, it means that operations that operate on the ownership (e.g.
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * #detachTo()) are forbidden and will assert.
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync *
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync * @param aArg Input method parameter to attach to.
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync */
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync SafeIfaceArray (ComSafeArrayIn (I *, aArg))
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync {
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync#if defined (VBOX_WITH_XPCOM)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync AssertReturnVoid (aArg != NULL);
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync Base::m.size = aArgSize;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync Base::m.arr = aArg;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync Base::m.isWeak = true;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync#else /* defined (VBOX_WITH_XPCOM) */
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync AssertReturnVoid (aArg != NULL);
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync SAFEARRAY *arg = *aArg;
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync if (arg)
4b8c66482cbc69a01ac399b8588b8bc80b310523vboxsync {
3bb3e26b3306b9f62b18c17380bdf2ca3a98ca49vboxsync AssertReturnVoid (arg->cDims == 1);
3bb3e26b3306b9f62b18c17380bdf2ca3a98ca49vboxsync
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync VARTYPE vt;
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync HRESULT rc = SafeArrayGetVartype (arg, &vt);
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync AssertComRCReturnVoid (rc);
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync AssertMsgReturnVoid (vt == VT_UNKNOWN,
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync ("Expected vartype VT_UNKNOWN, got %d.\n",
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync VarType(), vt));
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync GUID guid;
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync rc = SafeArrayGetIID (arg, &guid);
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync AssertComRCReturnVoid (rc);
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync AssertMsgReturnVoid (InlineIsEqualGUID (_ATL_IIDOF (I), guid),
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync ("Expected IID {%Vuuid}, got {%Vuuid}.\n",
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync &_ATL_IIDOF (I), &guid));
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync rc = SafeArrayAccessData (arg, (void HUGEP **) &m.raw);
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync AssertComRCReturnVoid (rc);
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync }
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync m.arr = arg;
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync m.isWeak = true;
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync#endif /* defined (VBOX_WITH_XPCOM) */
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync }
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync /**
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * Creates a deep copy of the given standard C++ container that stores
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * interface pointers as objects of the ComPtr <I> class.
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync *
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * @param aCntr Container object to copy.
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync *
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * @param C Standard C++ container template class (normally deduced from
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * @c aCntr).
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * @param A Standard C++ allocator class (deduced from @c aCntr).
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * @param OI Argument to the ComPtr template (deduced from @c aCntr).
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync */
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync template <template <typename, typename> class C, class A, class OI>
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync SafeIfaceArray (const C <ComPtr <OI>, A> & aCntr)
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync {
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync typedef C <ComPtr <OI>, A> List;
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync resize (aCntr.size());
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync AssertReturnVoid (!Base::isNull());
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync int i = 0;
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync for (typename List::const_iterator it = aCntr.begin();
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync it != aCntr.end(); ++ it, ++ i)
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync#if defined (VBOX_WITH_XPCOM)
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync Copy (*it, Base::m.arr [i]);
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync#else
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync Copy (*it, Base::m.raw [i]);
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync#endif
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync }
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync /**
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * Creates a deep copy of the given standard C++ container that stores
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * interface pointers as objects of the ComObjPtr <I> class.
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync *
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * @param aCntr Container object to copy.
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync *
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * @param C Standard C++ container template class (normally deduced from
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync * @c aCntr).
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * @param A Standard C++ allocator class (deduced from @c aCntr).
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync * @param OI Argument to the ComObjPtr template (deduced from @c aCntr).
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync */
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync template <template <typename, typename> class C, class A, class OI>
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync SafeIfaceArray (const C <ComObjPtr <OI>, A> & aCntr)
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync {
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync typedef C <ComObjPtr <OI>, A> List;
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync resize (aCntr.size());
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync AssertReturnVoid (!Base::isNull());
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync int i = 0;
4bf996d915405be92dc4394b2db1395e00e14d58vboxsync for (typename List::const_iterator it = aCntr.begin();
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync it != aCntr.end(); ++ it, ++ i)
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync#if defined (VBOX_WITH_XPCOM)
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync Copy (*it, Base::m.arr [i]);
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync#else
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync Copy (*it, Base::m.raw [i]);
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync#endif
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync }
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync};
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync} /* namespace com */
b26e5b503baa3dffc58048982eaf17ad1b53f207vboxsync
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync/** @} */
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync#endif /* ___VBox_com_array_h */
71e045383a3316b27563b2f44b0e0e1231968bdcvboxsync