summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorNoel Grandin <noelgrandin@gmail.com>2024-05-01 13:33:41 +0200
committerNoel Grandin <noel.grandin@collabora.co.uk>2024-05-02 14:37:56 +0200
commitd4c0e39d93f3038a18cba975c25bb42aa125166c (patch)
treebc09721381615ec94bff792f5ede1e7319dbd970
parentuse [[noreturn]] instead of asserts that badUsage exits (diff)
downloadcore-d4c0e39d93f3038a18cba975c25bb42aa125166c.tar.gz
core-d4c0e39d93f3038a18cba975c25bb42aa125166c.zip
make the slot data constinit
because it takes a surprising amount of time to initialise it at runtime during startup (*) have to convert the std::function in SfxType to a function pointer, because the std::function constructor is not constinit compatible. (*) the SfxType0..SfxTypeN types need some reinterpret_cast to work around the lack of zero-sized trailing arrays in c++ (*) Sadly MSVC does not support taking the address of symbols in constinit structures, so we cannot make the SfxSlot array constinit. Change-Id: I300ee770cc115d30bc25c819f2ad34b29633876c Reviewed-on: https://gerrit.libreoffice.org/c/core/+/166963 Tested-by: Jenkins Reviewed-by: Noel Grandin <noel.grandin@collabora.co.uk>
-rw-r--r--idl/source/objects/object.cxx5
-rw-r--r--idl/source/objects/types.cxx4
-rw-r--r--include/sfx2/msg.hxx25
-rw-r--r--sfx2/source/appl/appuno.cxx86
-rw-r--r--sfx2/source/control/objface.cxx39
5 files changed, 66 insertions, 93 deletions
diff --git a/idl/source/objects/object.cxx b/idl/source/objects/object.cxx
index 0b2fadec2d77..9138ab075a2d 100644
--- a/idl/source/objects/object.cxx
+++ b/idl/source/objects/object.cxx
@@ -269,7 +269,7 @@ void SvMetaClass::WriteSfx( SvIdlDataBase & rBase, SvStream & rOutStm )
return;
}
// write parameter array
- rOutStm.WriteOString("static SfxFormalArgument a").WriteOString(GetName()).WriteOString("Args_Impl[] =") << endl;
+ rOutStm.WriteOString("static const SfxFormalArgument a").WriteOString(GetName()).WriteOString("Args_Impl[] =") << endl;
rOutStm.WriteChar('{') << endl;
std::vector<sal_uInt32> aSuperList;
@@ -304,7 +304,8 @@ void SvMetaClass::WriteSfx( SvIdlDataBase & rBase, SvStream & rOutStm )
rOutStm << endl;
// write slotmap
- rOutStm.WriteOString("static SfxSlot a").WriteOString(GetName()).WriteOString("Slots_Impl[] =") << endl;
+ rOutStm.WriteOString("static SfxSlot a").WriteOString(GetName())
+ .WriteOString("Slots_Impl[").WriteOString(OString::number(nSlotCount == 0 ? 1 : nSlotCount)).WriteOString("] =") << endl;
rOutStm.WriteChar( '{' ) << endl;
// write all attributes
diff --git a/idl/source/objects/types.cxx b/idl/source/objects/types.cxx
index b98d90c93d85..08fa843d6f96 100644
--- a/idl/source/objects/types.cxx
+++ b/idl/source/objects/types.cxx
@@ -242,7 +242,7 @@ void SvMetaType::WriteSfxItem(
rOutStm.WriteOString( "extern " );
if (bExport)
rOutStm.WriteOString( "SFX2_DLLPUBLIC " );
- rOutStm.WriteOString( aTypeName )
+ rOutStm.WriteOString( "constinit const " ).WriteOString( aTypeName )
.WriteOString( aVarName ).WriteChar( ';' ) << endl;
if (bReturn)
return;
@@ -252,7 +252,7 @@ void SvMetaType::WriteSfxItem(
rOutStm.WriteOString( "#if !defined(_WIN32) && (defined(DISABLE_DYNLOADING) && (defined(ANDROID) || defined(IOS) || defined(EMSCRIPTEN) || defined(LINUX)))" ) << endl;
rOutStm.WriteOString( "__attribute__((__weak__))" ) << endl;
rOutStm.WriteOString( "#endif" ) << endl;
- rOutStm.WriteOString( aTypeName ).WriteOString( aVarName )
+ rOutStm.WriteOString( "constinit const " ).WriteOString( aTypeName ).WriteOString( aVarName )
.WriteOString( " = " ) << endl;
rOutStm.WriteChar( '{' ) << endl;
diff --git a/include/sfx2/msg.hxx b/include/sfx2/msg.hxx
index 8023f0846f60..88d9f68cf6ca 100644
--- a/include/sfx2/msg.hxx
+++ b/include/sfx2/msg.hxx
@@ -98,30 +98,33 @@ template<class T> SfxPoolItem* createSfxPoolItem()
{
return T::CreateDefault();
}
+
struct SfxType
{
- std::function<SfxPoolItem* ()> createSfxPoolItemFunc;
+ SfxPoolItem* (*createSfxPoolItemFunc)();
const std::type_info* pType;
sal_uInt16 nAttribs;
- SfxTypeAttrib aAttrib[1]; // variable length
const std::type_info* Type() const{return pType;}
std::unique_ptr<SfxPoolItem> CreateItem() const
{ return std::unique_ptr<SfxPoolItem>(createSfxPoolItemFunc()); }
+ inline const SfxTypeAttrib& getAttrib(sal_uInt16 idx) const;
};
-struct SfxType0
+struct SfxTypeImpl : public SfxType
+{
+ SfxTypeAttrib aAttrib[1]; // variable length
+};
+
+// Some casting to work around the lack of zero-sized trailing arrays in c++
+inline const SfxTypeAttrib& SfxType::getAttrib(sal_uInt16 idx) const
+{ return reinterpret_cast<const SfxTypeImpl*>(this)->aAttrib[idx]; }
+
+struct SfxType0 : public SfxType
{
- std::function<SfxPoolItem* ()> createSfxPoolItemFunc;
- const std::type_info* pType;
- sal_uInt16 nAttribs;
- const std::type_info* Type() const { return pType;}
};
-#define SFX_DECL_TYPE(n) struct SfxType##n \
+#define SFX_DECL_TYPE(n) struct SfxType##n : public SfxType \
{ \
- std::function<SfxPoolItem* ()> createSfxPoolItemFunc; \
- const std::type_info* pType; \
- sal_uInt16 nAttribs; \
SfxTypeAttrib aAttrib[n]; \
}
diff --git a/sfx2/source/appl/appuno.cxx b/sfx2/source/appl/appuno.cxx
index 7aa37e031143..948b8d7abb4d 100644
--- a/sfx2/source/appl/appuno.cxx
+++ b/sfx2/source/appl/appuno.cxx
@@ -60,37 +60,37 @@ using namespace ::com::sun::star::io;
// needs to be converted to a better data structure
SfxFormalArgument const aFormalArgs[] = {
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "SuggestedSaveAsName", SID_DEFAULTFILENAME },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "SuggestedSaveAsDir", SID_DEFAULTFILEPATH },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "VersionAuthor", SID_DOCINFO_AUTHOR },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "VersionComment", SID_DOCINFO_COMMENTS },
- { reinterpret_cast<SfxType*>(&aSfxBoolItem_Impl), "DontTerminateEdit", FN_PARAM_1 },
- { reinterpret_cast<SfxType*>(&aSfxBoolItem_Impl), "VersionMajor", SID_DOCINFO_MAJOR },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "FilterOptions", SID_FILE_FILTEROPTIONS },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "FilterName", SID_FILTER_NAME },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "Margin1", SID_RULER_MARGIN1 },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "Margin2", SID_RULER_MARGIN2 },
-// { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "FileName", SID_FILE_NAME },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "URL", SID_FILE_NAME },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "OpenFlags", SID_OPTIONS },
- { reinterpret_cast<SfxType*>(&aSfxBoolItem_Impl), "Overwrite", SID_OVERWRITE },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "Password", SID_PASSWORD },
- { reinterpret_cast<SfxType*>(&aSfxBoolItem_Impl), "PasswordInteraction", SID_PASSWORDINTERACTION },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "Referer", SID_REFERER },
- { reinterpret_cast<SfxType*>(&aSfxBoolItem_Impl), "SaveTo", SID_SAVETO },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "TemplateName", SID_TEMPLATE_NAME },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "TemplateRegion", SID_TEMPLATE_REGIONNAME },
-// { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "Region", SID_TEMPLATE_REGIONNAME },
-// { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "Name", SID_TEMPLATE_NAME },
- { reinterpret_cast<SfxType*>(&aSfxBoolItem_Impl), "Unpacked", SID_UNPACK },
- { reinterpret_cast<SfxType*>(&aSfxInt16Item_Impl), "Version", SID_VERSION },
- { reinterpret_cast<SfxType*>(&aSfxBoolItem_Impl), "SaveACopy", SID_SAVEACOPYITEM },
- { reinterpret_cast<SfxType*>(&aSfxBoolItem_Impl), "NoFileSync", SID_NO_FILE_SYNC },
- { reinterpret_cast<SfxType*>(&aSfxBoolItem_Impl), "NoThumbnail", SID_NO_THUMBNAIL },
- { reinterpret_cast<SfxType*>(&aSfxBoolItem_Impl), "NoEmbDataSet", SID_NO_EMBEDDED_DS },
- { reinterpret_cast<SfxType*>(&aSfxBoolItem_Impl), "IsRedactMode", SID_IS_REDACT_MODE },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "RedactionStyle", SID_REDACTION_STYLE },
- { reinterpret_cast<SfxType*>(&aSfxStringItem_Impl), "AdditionsTag", FN_PARAM_ADDITIONS_TAG },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "SuggestedSaveAsName", SID_DEFAULTFILENAME },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "SuggestedSaveAsDir", SID_DEFAULTFILEPATH },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "VersionAuthor", SID_DOCINFO_AUTHOR },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "VersionComment", SID_DOCINFO_COMMENTS },
+ { static_cast<const SfxType*>(&aSfxBoolItem_Impl), "DontTerminateEdit", FN_PARAM_1 },
+ { static_cast<const SfxType*>(&aSfxBoolItem_Impl), "VersionMajor", SID_DOCINFO_MAJOR },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "FilterOptions", SID_FILE_FILTEROPTIONS },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "FilterName", SID_FILTER_NAME },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "Margin1", SID_RULER_MARGIN1 },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "Margin2", SID_RULER_MARGIN2 },
+// { static_cast<const SfxType*>(&aSfxStringItem_Impl), "FileName", SID_FILE_NAME },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "URL", SID_FILE_NAME },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "OpenFlags", SID_OPTIONS },
+ { static_cast<const SfxType*>(&aSfxBoolItem_Impl), "Overwrite", SID_OVERWRITE },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "Password", SID_PASSWORD },
+ { static_cast<const SfxType*>(&aSfxBoolItem_Impl), "PasswordInteraction", SID_PASSWORDINTERACTION },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "Referer", SID_REFERER },
+ { static_cast<const SfxType*>(&aSfxBoolItem_Impl), "SaveTo", SID_SAVETO },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "TemplateName", SID_TEMPLATE_NAME },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "TemplateRegion", SID_TEMPLATE_REGIONNAME },
+// { static_cast<const SfxType*>(&aSfxStringItem_Impl), "Region", SID_TEMPLATE_REGIONNAME },
+// { static_cast<const SfxType*>(&aSfxStringItem_Impl), "Name", SID_TEMPLATE_NAME },
+ { static_cast<const SfxType*>(&aSfxBoolItem_Impl), "Unpacked", SID_UNPACK },
+ { static_cast<const SfxType*>(&aSfxInt16Item_Impl), "Version", SID_VERSION },
+ { static_cast<const SfxType*>(&aSfxBoolItem_Impl), "SaveACopy", SID_SAVEACOPYITEM },
+ { static_cast<const SfxType*>(&aSfxBoolItem_Impl), "NoFileSync", SID_NO_FILE_SYNC },
+ { static_cast<const SfxType*>(&aSfxBoolItem_Impl), "NoThumbnail", SID_NO_THUMBNAIL },
+ { static_cast<const SfxType*>(&aSfxBoolItem_Impl), "NoEmbDataSet", SID_NO_EMBEDDED_DS },
+ { static_cast<const SfxType*>(&aSfxBoolItem_Impl), "IsRedactMode", SID_IS_REDACT_MODE },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "RedactionStyle", SID_REDACTION_STYLE },
+ { static_cast<const SfxType*>(&aSfxStringItem_Impl), "AdditionsTag", FN_PARAM_ADDITIONS_TAG },
};
sal_uInt16 const nMediaArgsCount = SAL_N_ELEMENTS(aFormalArgs);
@@ -242,9 +242,9 @@ void TransformParameters( sal_uInt16 nSlotId, const uno::Sequence<beans::Propert
for ( nSub=0; nSub<nSubCount; nSub++ )
{
// search sub item by name
- if ( rPropValue.Name == (pSlot->aUnoName + "." + pType->aAttrib[nSub].aName) )
+ if ( rPropValue.Name == (pSlot->aUnoName + "." + pType->getAttrib(nSub).aName) )
{
- sal_uInt8 nSubId = static_cast<sal_uInt8>(static_cast<sal_Int8>(pType->aAttrib[nSub].nAID));
+ sal_uInt8 nSubId = static_cast<sal_uInt8>(static_cast<sal_Int8>(pType->getAttrib(nSub).nAID));
if ( bConvertTwips )
nSubId |= CONVERT_TWIPS;
if ( pItem->PutValue( rPropValue.Value, nSubId ) )
@@ -344,14 +344,14 @@ void TransformParameters( sal_uInt16 nSlotId, const uno::Sequence<beans::Propert
for ( sal_uInt16 nSub=0; nSub<nSubCount; nSub++ )
{
// search sub item by name
- if ( rProp.Name == (rArg.aName + "." + pType->aAttrib[nSub].aName) )
+ if ( rProp.Name == (rArg.aName + "." + pType->getAttrib(nSub).aName) )
{
// at least one member found ...
bRet = true;
#ifdef DBG_UTIL
++nFoundArgs;
#endif
- sal_uInt8 nSubId = static_cast<sal_uInt8>(static_cast<sal_Int8>(pType->aAttrib[nSub].nAID));
+ sal_uInt8 nSubId = static_cast<sal_uInt8>(static_cast<sal_Int8>(pType->getAttrib(nSub).nAID));
if ( bConvertTwips )
nSubId |= CONVERT_TWIPS;
if (!pItem->PutValue( rProp.Value, nSubId ) )
@@ -1311,17 +1311,17 @@ void TransformItems( sal_uInt16 nSlotId, const SfxItemSet& rSet, uno::Sequence<b
// complex type, add a property value for every member of the struct
for ( sal_uInt16 n=1; n<=nSubCount; ++n )
{
- sal_uInt8 nSubId = static_cast<sal_uInt8>(static_cast<sal_Int8>(pType->aAttrib[n-1].nAID));
+ sal_uInt8 nSubId = static_cast<sal_uInt8>(static_cast<sal_Int8>(pType->getAttrib(n-1).nAID));
if ( bConvertTwips )
nSubId |= CONVERT_TWIPS;
- DBG_ASSERT(( pType->aAttrib[n-1].nAID ) <= 127, "Member ID out of range" );
+ DBG_ASSERT(( pType->getAttrib(n-1).nAID ) <= 127, "Member ID out of range" );
pValue[nActProp].Name = pSlot->aUnoName +
"." +
- pType->aAttrib[n-1].aName;
+ pType->getAttrib(n-1).aName;
if ( !pItem->QueryValue( pValue[nActProp++].Value, nSubId ) )
{
- SAL_WARN( "sfx", "Sub item " << pType->aAttrib[n-1].nAID
+ SAL_WARN( "sfx", "Sub item " << pType->getAttrib(n-1).nAID
<< " not convertible in slot: " << nSlotId );
}
}
@@ -1356,18 +1356,18 @@ void TransformItems( sal_uInt16 nSlotId, const SfxItemSet& rSet, uno::Sequence<b
// complex type, add a property value for every member of the struct
for ( sal_uInt16 n = 1; n <= nSubCount; ++n )
{
- sal_uInt8 nSubId = static_cast<sal_uInt8>(static_cast<sal_Int8>(rArg.pType->aAttrib[n-1].nAID));
+ sal_uInt8 nSubId = static_cast<sal_uInt8>(static_cast<sal_Int8>(rArg.pType->getAttrib(n-1).nAID));
if ( bConvertTwips )
nSubId |= CONVERT_TWIPS;
- DBG_ASSERT((rArg.pType->aAttrib[n-1].nAID) <= 127, "Member ID out of range" );
+ DBG_ASSERT((rArg.pType->getAttrib(n-1).nAID) <= 127, "Member ID out of range" );
pValue[nActProp].Name = rArg.aName +
"." +
- rArg.pType->aAttrib[n-1].aName ;
+ rArg.pType->getAttrib(n-1).aName ;
if ( !pItem->QueryValue( pValue[nActProp++].Value, nSubId ) )
{
SAL_WARN( "sfx", "Sub item "
- << rArg.pType->aAttrib[n-1].nAID
+ << rArg.pType->getAttrib(n-1).nAID
<< " not convertible in slot: "
<< rArg.nSlotId );
}
diff --git a/sfx2/source/control/objface.cxx b/sfx2/source/control/objface.cxx
index ed4393fa45d3..96afa430ac4e 100644
--- a/sfx2/source/control/objface.cxx
+++ b/sfx2/source/control/objface.cxx
@@ -30,12 +30,6 @@
extern "C" {
-static int
-SfxCompareSlots_qsort( const void* pSmaller, const void* pBigger )
-{
- return static_cast<int>(static_cast<SfxSlot const *>(pSmaller)->GetSlotId()) -
- static_cast<int>(static_cast<SfxSlot const *>(pBigger)->GetSlotId());
-}
static int
SfxCompareSlots_bsearch( const void* pSmaller, const void* pBigger )
@@ -113,39 +107,14 @@ void SfxInterface::SetSlotMap( SfxSlot& rSlotMap, sal_uInt16 nSlotCount )
pSlots = &rSlotMap;
nCount = nSlotCount;
SfxSlot* pIter = pSlots;
- if ( 1 == nCount && !pIter->pNextSlot )
- pIter->pNextSlot = pIter;
if ( !pIter->pNextSlot )
{
- // sort the SfxSlots by id
- qsort( pSlots, nCount, sizeof(SfxSlot), SfxCompareSlots_qsort );
-
- // link masters and slaves
- sal_uInt16 nIter = 1;
- for ( pIter = pSlots; nIter <= nCount; ++pIter, ++nIter )
- {
-
- assert( nIter == nCount ||
- pIter->GetSlotId() != (pIter+1)->GetSlotId() );
-
- if ( nullptr == pIter->GetNextSlot() )
+ assert(std::is_sorted(pSlots, pSlots + nCount,
+ [](const SfxSlot& rLHS, const SfxSlot& rRHS)
{
- // Slots referring in circle to the next with the same
- // Status method.
- SfxSlot *pLastSlot = pIter;
- for ( sal_uInt16 n = nIter; n < Count(); ++n )
- {
- SfxSlot *pCurSlot = pSlots+n;
- if ( pCurSlot->GetStateFnc() == pIter->GetStateFnc() )
- {
- pLastSlot->pNextSlot = pCurSlot;
- pLastSlot = pCurSlot;
- }
- }
- pLastSlot->pNextSlot = pIter;
- }
- }
+ return rLHS.GetSlotId() < rRHS.GetSlotId();
+ }));
}
#ifdef DBG_UTIL
else