canvas/source/cairo/cairo_textlayout.cxx                |    6 +-
 canvas/source/directx/dx_textlayout_drawhelper.cxx      |    2 
 canvas/source/opengl/ogl_canvashelper.cxx               |    6 +-
 canvas/source/vcl/textlayout.cxx                        |   12 ++---
 cppcanvas/source/inc/implrenderer.hxx                   |    2 
 cppcanvas/source/mtfrenderer/implrenderer.cxx           |   16 +++---
 cppcanvas/source/mtfrenderer/textaction.cxx             |   15 +++---
 cppcanvas/source/mtfrenderer/textaction.hxx             |    2 
 drawinglayer/source/primitive2d/textlayoutdevice.cxx    |    2 
 drawinglayer/source/processor2d/vclprocessor2d.cxx      |   12 ++---
 drawinglayer/source/tools/wmfemfhelper.cxx              |    6 +-
 editeng/source/editeng/editeng.cxx                      |    2 
 editeng/source/editeng/impedit3.cxx                     |   15 +++---
 editeng/source/items/svxfont.cxx                        |    6 +-
 editeng/source/outliner/outleeng.cxx                    |    2 
 editeng/source/outliner/outleeng.hxx                    |    2 
 editeng/source/outliner/outliner.cxx                    |    6 +-
 emfio/inc/mtftools.hxx                                  |    2 
 emfio/source/reader/emfreader.cxx                       |   13 ++---
 emfio/source/reader/mtftools.cxx                        |   23 +++++----
 emfio/source/reader/wmfreader.cxx                       |   19 ++++----
 filter/source/svg/svgwriter.cxx                         |   16 +++---
 filter/source/svg/svgwriter.hxx                         |    4 -
 include/editeng/editeng.hxx                             |    3 -
 include/editeng/outliner.hxx                            |    6 +-
 include/editeng/svxfont.hxx                             |    3 -
 include/o3tl/span.hxx                                   |    5 ++
 include/vcl/metaact.hxx                                 |   13 +++--
 include/vcl/outdev.hxx                                  |   11 ++--
 include/vcl/pdfwriter.hxx                               |    2 
 sc/source/ui/view/output2.cxx                           |    4 -
 sfx2/source/doc/SfxRedactionHelper.cxx                  |    6 +-
 svtools/source/control/ruler.cxx                        |    4 -
 svx/source/customshapes/EnhancedCustomShapeFontWork.cxx |    4 -
 svx/source/svdraw/svdotextdecomposition.cxx             |    2 
 svx/source/svdraw/svdotextpathdecomposition.cxx         |    2 
 sw/source/core/txtnode/fntcache.cxx                     |   28 +++++------
 toolkit/source/awt/vclxgraphics.cxx                     |    6 +-
 vcl/inc/pdf/pdfwriter_impl.hxx                          |    2 
 vcl/qa/cppunit/complextext.cxx                          |    8 +--
 vcl/qa/cppunit/text.cxx                                 |    2 
 vcl/source/control/calendar.cxx                         |    5 +-
 vcl/source/control/imp_listbox.cxx                      |    2 
 vcl/source/filter/eps/eps.cxx                           |   18 +++----
 vcl/source/filter/svm/SvmConverter.cxx                  |   12 ++---
 vcl/source/filter/svm/SvmReader.cxx                     |   14 +++--
 vcl/source/filter/svm/SvmWriter.cxx                     |    6 +-
 vcl/source/filter/wmf/emfwr.cxx                         |   25 ++++++----
 vcl/source/filter/wmf/emfwr.hxx                         |    2 
 vcl/source/filter/wmf/wmfwr.cxx                         |   22 ++++-----
 vcl/source/filter/wmf/wmfwr.hxx                         |    6 +-
 vcl/source/gdi/gdimtf.cxx                               |    4 -
 vcl/source/gdi/metaact.cxx                              |   38 ++++++++--------
 vcl/source/gdi/mtfxmldump.cxx                           |    2 
 vcl/source/gdi/pdfwriter.cxx                            |    2 
 vcl/source/gdi/pdfwriter_impl.cxx                       |    2 
 vcl/source/gdi/pdfwriter_impl2.cxx                      |    2 
 vcl/source/gdi/textlayout.cxx                           |    2 
 vcl/source/outdev/text.cxx                              |   31 ++++++-------
 vcl/source/outdev/transparent.cxx                       |    2 
 vcl/source/window/menuitemlist.cxx                      |    2 
 61 files changed, 267 insertions(+), 234 deletions(-)

New commits:
commit 894b4911ffb96ff667fdeb3aec7922316ab7230a
Author:     Noel Grandin <noel.gran...@collabora.co.uk>
AuthorDate: Thu Oct 28 09:27:29 2021 +0200
Commit:     Noel Grandin <noel.gran...@collabora.co.uk>
CommitDate: Fri Oct 29 12:38:51 2021 +0200

    pass DX array around using o3tl::span instead of pointer
    
    so we get bounds checking in debug mode
    
    Note that I cannot just pass around the std::vectors
    involved because there is a place in editeng which
    calls with a subset of a vector.
    
    Change-Id: I5088a139593c27bf9cbe5d843ab4b0048ac6d508
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/124330
    Tested-by: Jenkins
    Reviewed-by: Noel Grandin <noel.gran...@collabora.co.uk>

diff --git a/canvas/source/cairo/cairo_textlayout.cxx 
b/canvas/source/cairo/cairo_textlayout.cxx
index 9952d33d343c..acf2672be51d 100644
--- a/canvas/source/cairo/cairo_textlayout.cxx
+++ b/canvas/source/cairo/cairo_textlayout.cxx
@@ -263,14 +263,14 @@ namespace cairocanvas
         ::osl::MutexGuard aGuard( m_aMutex );
         setupLayoutMode( rOutDev, mnTextDirection );
 
-        std::unique_ptr< tools::Long []> aOffsets(new 
tools::Long[maLogicalAdvancements.getLength()]);
+        std::vector<tools::Long> aOffsets(maLogicalAdvancements.getLength());
 
         if( maLogicalAdvancements.hasElements() )
-            setupTextOffsets( aOffsets.get(), maLogicalAdvancements, 
viewState, renderState );
+            setupTextOffsets( aOffsets.data(), maLogicalAdvancements, 
viewState, renderState );
 
         if (maLogicalAdvancements.hasElements())
         {
-            rOutDev.DrawTextArray( rOutpos, maText.Text, aOffsets.get(),
+            rOutDev.DrawTextArray( rOutpos, maText.Text, { aOffsets.data(), 
aOffsets.size() },
                                    
::canvas::tools::numeric_cast<sal_uInt16>(maText.StartPosition),
                                    
::canvas::tools::numeric_cast<sal_uInt16>(maText.Length) );
         }
diff --git a/canvas/source/directx/dx_textlayout_drawhelper.cxx 
b/canvas/source/directx/dx_textlayout_drawhelper.cxx
index 1ffeb612de3d..6b5a389f77ae 100644
--- a/canvas/source/directx/dx_textlayout_drawhelper.cxx
+++ b/canvas/source/directx/dx_textlayout_drawhelper.cxx
@@ -213,7 +213,7 @@ namespace dxcanvas
                 // draw the String
                 xVirtualDevice->DrawTextArray( aEmptyPoint,
                                               aText,
-                                              pDXArray.get(),
+                                              o3tl::span<const ::tools::Long>( 
pDXArray.get(), nLen ),
                                               rText.StartPosition,
                                               rText.Length,
                                               bIsRTL ? SalLayoutFlags::BiDiRtl 
: SalLayoutFlags::NONE);
diff --git a/canvas/source/opengl/ogl_canvashelper.cxx 
b/canvas/source/opengl/ogl_canvashelper.cxx
index b0264d8d1d31..fdd4a7ac541b 100644
--- a/canvas/source/opengl/ogl_canvashelper.cxx
+++ b/canvas/source/opengl/ogl_canvashelper.cxx
@@ -729,9 +729,9 @@ namespace oglcanvas
                 {
                     // create the DXArray
                     const sal_Int32 nLen( aLogicalAdvancements.getLength() );
-                    std::unique_ptr<tools::Long[]> pDXArray( new 
tools::Long[nLen] );
+                    std::vector<tools::Long> aDXArray(nLen);
                     for( sal_Int32 i=0; i<nLen; ++i )
-                        pDXArray[i] = basegfx::fround( aLogicalAdvancements[i] 
);
+                        aDXArray[i] = basegfx::fround( aLogicalAdvancements[i] 
);
 
                     // get the glyphs
                     pVDev->GetTextOutlines(rAct.maPolyPolys,
@@ -740,7 +740,7 @@ namespace oglcanvas
                                           rTxt.StartPosition,
                                           rTxt.Length,
                                           0,
-                                          pDXArray.get() );
+                                          { aDXArray.data(), aDXArray.size() } 
);
                 }
                 else
                 {
diff --git a/canvas/source/vcl/textlayout.cxx b/canvas/source/vcl/textlayout.cxx
index 42e96e420233..1c1f1317b865 100644
--- a/canvas/source/vcl/textlayout.cxx
+++ b/canvas/source/vcl/textlayout.cxx
@@ -117,8 +117,8 @@ namespace vclcanvas
             uno::Sequence<double>(4),
             rendering::CompositeOperation::SOURCE);
 
-        std::unique_ptr< ::tools::Long []> aOffsets(new 
::tools::Long[maLogicalAdvancements.getLength()]);
-        setupTextOffsets(aOffsets.get(), maLogicalAdvancements, aViewState, 
aRenderState);
+        std::vector<::tools::Long> aOffsets(maLogicalAdvancements.getLength());
+        setupTextOffsets(aOffsets.data(), maLogicalAdvancements, aViewState, 
aRenderState);
 
         std::vector< uno::Reference< rendering::XPolyPolygon2D> > 
aOutlineSequence;
         ::basegfx::B2DPolyPolygonVector aOutlines;
@@ -129,7 +129,7 @@ namespace vclcanvas
             maText.StartPosition,
             maText.Length,
             0,
-            aOffsets.get()))
+            {aOffsets.data(), aOffsets.size()}))
         {
             aOutlineSequence.reserve(aOutlines.size());
             sal_Int32 nIndex (0);
@@ -335,15 +335,15 @@ namespace vclcanvas
         if( maLogicalAdvancements.hasElements() )
         {
             // TODO(P2): cache that
-            std::unique_ptr< ::tools::Long []> aOffsets(new 
::tools::Long[maLogicalAdvancements.getLength()]);
-            setupTextOffsets( aOffsets.get(), maLogicalAdvancements, 
viewState, renderState );
+            std::vector<::tools::Long> 
aOffsets(maLogicalAdvancements.getLength());
+            setupTextOffsets( aOffsets.data(), maLogicalAdvancements, 
viewState, renderState );
 
             // TODO(F3): ensure correct length and termination for DX
             // array (last entry _must_ contain the overall width)
 
             rOutDev.DrawTextArray( rOutpos,
                                    maText.Text,
-                                   aOffsets.get(),
+                                   { aOffsets.data(), aOffsets.size() },
                                    
::canvas::tools::numeric_cast<sal_uInt16>(maText.StartPosition),
                                    
::canvas::tools::numeric_cast<sal_uInt16>(maText.Length) );
         }
diff --git a/cppcanvas/source/inc/implrenderer.hxx 
b/cppcanvas/source/inc/implrenderer.hxx
index 93b68f9410ad..2a77639e4ae8 100644
--- a/cppcanvas/source/inc/implrenderer.hxx
+++ b/cppcanvas/source/inc/implrenderer.hxx
@@ -192,7 +192,7 @@ namespace cppcanvas::internal
                                    const OUString&                rString,
                                    int                            nIndex,
                                    int                            nLength,
-                                   const tools::Long*                    
pCharWidths,
+                                   o3tl::span<const tools::Long>  pCharWidths,
                                    const ActionFactoryParameters& rParms,
                                    bool                           bSubsettable 
);
 
diff --git a/cppcanvas/source/mtfrenderer/implrenderer.cxx 
b/cppcanvas/source/mtfrenderer/implrenderer.cxx
index 308e4be259dc..8c530c193cb4 100644
--- a/cppcanvas/source/mtfrenderer/implrenderer.cxx
+++ b/cppcanvas/source/mtfrenderer/implrenderer.cxx
@@ -858,7 +858,7 @@ namespace cppcanvas::internal
                                              const OUString&                
rString,
                                              int                            
nIndex,
                                              int                            
nLength,
-                                             const ::tools::Long*              
      pCharWidths,
+                                             o3tl::span<const ::tools::Long> 
pCharWidths,
                                              const ActionFactoryParameters& 
rParms,
                                              bool                           
bSubsettableActions )
         {
@@ -996,16 +996,16 @@ namespace cppcanvas::internal
                 {
                     ::tools::Long nInterval = ( nWidth - nStrikeoutWidth * 
nLen ) / nLen;
                     nStrikeoutWidth += nInterval;
-                    ::tools::Long* pStrikeoutCharWidths = new 
::tools::Long[nLen];
+                    std::vector<::tools::Long> aStrikeoutCharWidths(nLen);
 
                     for ( int i = 0;i<nLen; i++)
                     {
-                        pStrikeoutCharWidths[i] = nStrikeoutWidth;
+                        aStrikeoutCharWidths[i] = nStrikeoutWidth;
                     }
 
                     for ( int i = 1;i< nLen; i++ )
                     {
-                        pStrikeoutCharWidths[ i ] += pStrikeoutCharWidths[ i-1 
];
+                        aStrikeoutCharWidths[ i ] += aStrikeoutCharWidths[ i-1 
];
                     }
 
                     pStrikeoutTextAction =
@@ -1019,7 +1019,7 @@ namespace cppcanvas::internal
                             aStrikeoutText.makeStringAndClear(),
                             0/*nStartPos*/,
                             nLen,
-                            pStrikeoutCharWidths,
+                            { aStrikeoutCharWidths.data(), 
aStrikeoutCharWidths.size() },
                             rParms.mrVDev,
                             rParms.mrCanvas,
                             rState,
@@ -2464,7 +2464,7 @@ namespace cppcanvas::internal
                             sText,
                             pAct->GetIndex(),
                             nLen,
-                            nullptr,
+                            {},
                             rFactoryParms,
                             bSubsettableActions );
                     }
@@ -2485,7 +2485,7 @@ namespace cppcanvas::internal
                             sText,
                             pAct->GetIndex(),
                             nLen,
-                            pAct->GetDXArray(),
+                            { pAct->GetDXArray().data(), 
pAct->GetDXArray().size() },
                             rFactoryParms,
                             bSubsettableActions );
                     }
@@ -2593,7 +2593,7 @@ namespace cppcanvas::internal
                             sText,
                             pAct->GetIndex(),
                             nLen,
-                            aDXArray.data(),
+                            { aDXArray.data(), aDXArray.size() },
                             rFactoryParms,
                             bSubsettableActions );
                     }
diff --git a/cppcanvas/source/mtfrenderer/textaction.cxx 
b/cppcanvas/source/mtfrenderer/textaction.cxx
index 6af8984534e0..735bcb685555 100644
--- a/cppcanvas/source/mtfrenderer/textaction.cxx
+++ b/cppcanvas/source/mtfrenderer/textaction.cxx
@@ -157,7 +157,7 @@ namespace cppcanvas::internal
                 rLayoutWidth = *(std::max_element(rOffsets.begin(), 
rOffsets.end()));
             }
 
-            uno::Sequence< double > setupDXArray( const ::tools::Long*   
pCharWidths,
+            uno::Sequence< double > setupDXArray( o3tl::span<const 
::tools::Long> rCharWidths,
                                                   sal_Int32          nLen,
                                                   const OutDevState& rState )
             {
@@ -169,6 +169,7 @@ namespace cppcanvas::internal
                 // array, by circumventing integer-based
                 // OutDev-mapping
                 const double nScale( rState.mapModeTransform.get(0,0) );
+                ::tools::Long const * pCharWidths = rCharWidths.data();
                 for( int i = 0; i < nLen; ++i )
                 {
                     // TODO(F2): use correct scale direction
@@ -190,7 +191,7 @@ namespace cppcanvas::internal
 
                 rVDev.GetTextArray( rText, &aCharWidths, nStartPos, nLen );
 
-                return setupDXArray( aCharWidths.data(), nLen, rState );
+                return setupDXArray( { aCharWidths.data(), aCharWidths.size() 
}, nLen, rState );
             }
 
             ::basegfx::B2DPoint adaptStartPoint( const ::basegfx::B2DPoint&    
 rStartPoint,
@@ -1965,7 +1966,7 @@ namespace cppcanvas::internal
                                            const OUString&                  
rText,
                                            sal_Int32                        
nStartPos,
                                            sal_Int32                        
nLen,
-                                           const ::tools::Long*                
      pDXArray,
+                                           o3tl::span<const ::tools::Long>  
pDXArray,
                                            VirtualDevice&                   
rVDev,
                                            const CanvasSharedPtr&           
rCanvas,
                                            const OutDevState&               
rState,
@@ -2038,7 +2039,7 @@ namespace cppcanvas::internal
                 }
 
                 const uno::Sequence< double > aCharWidthSeq(
-                    pDXArray ?
+                    !pDXArray.empty() ?
                     setupDXArray( pDXArray, nLen, rState ) :
                     setupDXArray( rText,
                                   nStartPos,
@@ -2095,7 +2096,7 @@ namespace cppcanvas::internal
                                                              const OUString&   
             rText,
                                                              sal_Int32         
             nStartPos,
                                                              sal_Int32         
             nLen,
-                                                             const 
::tools::Long*                    pDXArray,
+                                                             o3tl::span<const 
::tools::Long> pDXArray,
                                                              VirtualDevice&    
             rVDev,
                                                              const 
CanvasSharedPtr&         rCanvas,
                                                              const 
OutDevState&             rState,
@@ -2137,7 +2138,7 @@ namespace cppcanvas::internal
             // convert DX array to device coordinate system (and
             // create it in the first place, if pDXArray is NULL)
             const uno::Sequence< double > aCharWidths(
-                pDXArray ?
+                !pDXArray.empty() ?
                 setupDXArray( pDXArray, nLen, rState ) :
                 setupDXArray( rText,
                               nStartPos,
@@ -2154,7 +2155,7 @@ namespace cppcanvas::internal
 
             // no DX array, and no need to subset - no need to store
             // DX array, then.
-            if( !pDXArray && !bSubsettable )
+            if( pDXArray.empty() && !bSubsettable )
             {
                 // effects, or not?
                 if( !rState.textOverlineStyle &&
diff --git a/cppcanvas/source/mtfrenderer/textaction.hxx 
b/cppcanvas/source/mtfrenderer/textaction.hxx
index aabad2245727..4cbdd46284bf 100644
--- a/cppcanvas/source/mtfrenderer/textaction.hxx
+++ b/cppcanvas/source/mtfrenderer/textaction.hxx
@@ -67,7 +67,7 @@ namespace cppcanvas::internal
                                                      const OUString&           
     rText,
                                                      sal_Int32                 
     nStartPos,
                                                      sal_Int32                 
     nLen,
-                                                     const ::tools::Long*      
              pDXArray,
+                                                     o3tl::span<const 
::tools::Long> pDXArray,
                                                      VirtualDevice&            
     rVDev,
                                                      const CanvasSharedPtr&    
     rCanvas,
                                                      const OutDevState&        
     rState,
diff --git a/drawinglayer/source/primitive2d/textlayoutdevice.cxx 
b/drawinglayer/source/primitive2d/textlayoutdevice.cxx
index c36c73658a08..11e903027122 100644
--- a/drawinglayer/source/primitive2d/textlayoutdevice.cxx
+++ b/drawinglayer/source/primitive2d/textlayoutdevice.cxx
@@ -239,7 +239,7 @@ void 
TextLayouterDevice::getTextOutlines(basegfx::B2DPolyPolygonVector& rB2DPoly
         }
 
         mrDevice.GetTextOutlines(rB2DPolyPolyVector, rText, nIndex, nIndex, 
nLength, 0,
-                                 aIntegerDXArray.data());
+                                 { aIntegerDXArray.data(), 
aIntegerDXArray.size() });
     }
     else
     {
diff --git a/drawinglayer/source/processor2d/vclprocessor2d.cxx 
b/drawinglayer/source/processor2d/vclprocessor2d.cxx
index 16bf6a78b878..034e82e1f50e 100644
--- a/drawinglayer/source/processor2d/vclprocessor2d.cxx
+++ b/drawinglayer/source/processor2d/vclprocessor2d.cxx
@@ -286,9 +286,6 @@ void 
VclProcessor2D::RenderTextSimpleOrDecoratedPortionPrimitive2D(
             sal_Int32 nPos = rTextCandidate.getTextPosition();
             sal_Int32 nLen = rTextCandidate.getTextLength();
 
-            std::vector<tools::Long>* pDXArray
-                = !aTransformedDXArray.empty() ? &aTransformedDXArray : 
nullptr;
-
             if (rTextCandidate.isFilled())
             {
                 basegfx::B2DVector aOldFontScaling, aOldTranslate;
@@ -299,8 +296,8 @@ void 
VclProcessor2D::RenderTextSimpleOrDecoratedPortionPrimitive2D(
                 tools::Long nWidthToFill = static_cast<tools::Long>(
                     rTextCandidate.getWidthToFill() * aFontScaling.getX() / 
aOldFontScaling.getX());
 
-                tools::Long nWidth
-                    = mpOutputDevice->GetTextArray(rTextCandidate.getText(), 
pDXArray, 0, 1);
+                tools::Long nWidth = 
mpOutputDevice->GetTextArray(rTextCandidate.getText(),
+                                                                  
&aTransformedDXArray, 0, 1);
                 tools::Long nChars = 2;
                 if (nWidth)
                     nChars = nWidthToFill / nWidth;
@@ -314,8 +311,9 @@ void 
VclProcessor2D::RenderTextSimpleOrDecoratedPortionPrimitive2D(
 
             if (!aTransformedDXArray.empty())
             {
-                mpOutputDevice->DrawTextArray(aStartPoint, aText,
-                                              pDXArray ? pDXArray->data() : 
nullptr, nPos, nLen);
+                mpOutputDevice->DrawTextArray(
+                    aStartPoint, aText, { aTransformedDXArray.data(), 
aTransformedDXArray.size() },
+                    nPos, nLen);
             }
             else
             {
diff --git a/drawinglayer/source/tools/wmfemfhelper.cxx 
b/drawinglayer/source/tools/wmfemfhelper.cxx
index 042bd8a77037..78b178355fbd 100644
--- a/drawinglayer/source/tools/wmfemfhelper.cxx
+++ b/drawinglayer/source/tools/wmfemfhelper.cxx
@@ -1828,15 +1828,15 @@ namespace wmfemfhelper
                     {
                         // prepare DXArray (if used)
                         std::vector< double > aDXArray;
-                        tools::Long* pDXArray = pA->GetDXArray();
+                        const std::vector<tools::Long> & rDXArray = 
pA->GetDXArray();
 
-                        if(pDXArray)
+                        if(!rDXArray.empty())
                         {
                             aDXArray.reserve(nTextLength);
 
                             for(sal_uInt32 a(0); a < nTextLength; a++)
                             {
-                                
aDXArray.push_back(static_cast<double>(*(pDXArray + a)));
+                                
aDXArray.push_back(static_cast<double>(rDXArray[a]));
                             }
                         }
 
diff --git a/editeng/source/editeng/editeng.cxx 
b/editeng/source/editeng/editeng.cxx
index f7c125cc2bca..5301de9513e0 100644
--- a/editeng/source/editeng/editeng.cxx
+++ b/editeng/source/editeng/editeng.cxx
@@ -2464,7 +2464,7 @@ css::uno::Reference< css::datatransfer::XTransferable >
 // ======================    Virtual Methods    ========================
 
 void EditEngine::DrawingText( const Point&, const OUString&, sal_Int32, 
sal_Int32,
-                              const tools::Long*, const SvxFont&, sal_Int32 
/*nPara*/, sal_uInt8 /*nRightToLeft*/,
+                              o3tl::span<const tools::Long>, const SvxFont&, 
sal_Int32 /*nPara*/, sal_uInt8 /*nRightToLeft*/,
                               const EEngineData::WrongSpellVector*, const 
SvxFieldData*, bool, bool,
                               const css::lang::Locale*, const Color&, const 
Color&)
 
diff --git a/editeng/source/editeng/impedit3.cxx 
b/editeng/source/editeng/impedit3.cxx
index 9281f4d7dcf2..98736f11cb85 100644
--- a/editeng/source/editeng/impedit3.cxx
+++ b/editeng/source/editeng/impedit3.cxx
@@ -156,7 +156,7 @@ static void lcl_DrawRedLines( OutputDevice& rOutDev,
                               const Point& rPoint,
                               size_t nIndex,
                               size_t nMaxEnd,
-                              const tools::Long* pDXArray,
+                              o3tl::span<const tools::Long> pDXArray,
                               WrongList const * pWrongs,
                               Degree10 nOrientation,
                               const Point& rOrigin,
@@ -3258,7 +3258,7 @@ void ImpEditEngine::Paint( OutputDevice& rOutDev, 
tools::Rectangle aClipRect, Po
                                 OUString aText;
                                 sal_Int32 nTextStart = 0;
                                 sal_Int32 nTextLen = 0;
-                                const tools::Long* pDXArray = nullptr;
+                                o3tl::span<const tools::Long> pDXArray;
                                 std::vector<tools::Long> aTmpDXArray;
 
                                 if ( rTextPortion.GetKind() == 
PortionKind::TEXT )
@@ -3266,7 +3266,8 @@ void ImpEditEngine::Paint( OutputDevice& rOutDev, 
tools::Rectangle aClipRect, Po
                                     aText = rPortion.GetNode()->GetString();
                                     nTextStart = nIndex;
                                     nTextLen = rTextPortion.GetLen();
-                                    pDXArray = pLine->GetCharPosArray().data() 
+ (nIndex - pLine->GetStart());
+                                    pDXArray = 
o3tl::span(pLine->GetCharPosArray().data() + (nIndex - pLine->GetStart()),
+                                                    
pLine->GetCharPosArray().size() - (nIndex - pLine->GetStart()));
 
                                     // Paint control characters (#i55716#)
                                     /* XXX: Given that there's special handling
@@ -3391,7 +3392,7 @@ void ImpEditEngine::Paint( OutputDevice& rOutDev, 
tools::Rectangle aClipRect, Po
 
                                     aTmpFont.SetPhysFont(*GetRefDevice());
                                     aTmpFont.QuickGetTextSize( GetRefDevice(), 
aText, nTextStart, nTextLen, &aTmpDXArray );
-                                    pDXArray = aTmpDXArray.data();
+                                    pDXArray = o3tl::span(aTmpDXArray.data(), 
aTmpDXArray.size());
 
                                     // add a meta file comment if we record to 
a metafile
                                     if( bMetafileValid )
@@ -3417,7 +3418,7 @@ void ImpEditEngine::Paint( OutputDevice& rOutDev, 
tools::Rectangle aClipRect, Po
                                     // crash when accessing 0 pointer in 
pDXArray
                                     aTmpFont.SetPhysFont(*GetRefDevice());
                                     aTmpFont.QuickGetTextSize( GetRefDevice(), 
aText, 0, aText.getLength(), &aTmpDXArray );
-                                    pDXArray = aTmpDXArray.data();
+                                    pDXArray = o3tl::span(aTmpDXArray.data(), 
aTmpDXArray.size());
                                 }
 
                                 tools::Long nTxtWidth = 
rTextPortion.GetSize().Width();
@@ -3753,7 +3754,7 @@ void ImpEditEngine::Paint( OutputDevice& rOutDev, 
tools::Rectangle aClipRect, Po
                                     const Color 
aTextLineColor(rOutDev.GetTextLineColor());
 
                                     GetEditEnginePtr()->DrawingText(
-                                        aTmpPos, OUString(), 0, 0, nullptr,
+                                        aTmpPos, OUString(), 0, 0, {},
                                         aTmpFont, n, 0,
                                         nullptr,
                                         nullptr,
@@ -3802,7 +3803,7 @@ void ImpEditEngine::Paint( OutputDevice& rOutDev, 
tools::Rectangle aClipRect, Po
                 const Color aTextLineColor(rOutDev.GetTextLineColor());
 
                 GetEditEnginePtr()->DrawingText(
-                    aTmpPos, OUString(), 0, 0, nullptr,
+                    aTmpPos, OUString(), 0, 0, {},
                     aTmpFont, n, 0,
                     nullptr,
                     nullptr,
diff --git a/editeng/source/items/svxfont.cxx b/editeng/source/items/svxfont.cxx
index 691ef6cb037a..e5b6a6df4fbf 100644
--- a/editeng/source/items/svxfont.cxx
+++ b/editeng/source/items/svxfont.cxx
@@ -500,7 +500,7 @@ Size SvxFont::GetTextSize(const OutputDevice& rOut, const 
OUString &rTxt,
 
 void SvxFont::QuickDrawText( OutputDevice *pOut,
     const Point &rPos, const OUString &rTxt,
-    const sal_Int32 nIdx, const sal_Int32 nLen, const tools::Long* pDXArray ) 
const
+    const sal_Int32 nIdx, const sal_Int32 nLen, o3tl::span<const tools::Long> 
pDXArray ) const
 {
 
     // Font has to be selected in OutputDevice...
@@ -526,12 +526,12 @@ void SvxFont::QuickDrawText( OutputDevice *pOut,
 
     if( IsCapital() )
     {
-        DBG_ASSERT( !pDXArray, "DrawCapital not for TextArray!" );
+        DBG_ASSERT( pDXArray.empty(), "DrawCapital not for TextArray!" );
         DrawCapital( pOut, aPos, rTxt, nIdx, nLen );
     }
     else
     {
-        if ( IsKern() && !pDXArray )
+        if ( IsKern() && pDXArray.empty() )
         {
             Size aSize = GetPhysTxtSize( pOut, rTxt, nIdx, nLen );
 
diff --git a/editeng/source/outliner/outleeng.cxx 
b/editeng/source/outliner/outleeng.cxx
index d9e1d0595a11..ed0099d2ac1a 100644
--- a/editeng/source/outliner/outleeng.cxx
+++ b/editeng/source/outliner/outleeng.cxx
@@ -141,7 +141,7 @@ OUString OutlinerEditEng::GetUndoComment( sal_uInt16 
nUndoId ) const
 }
 
 void OutlinerEditEng::DrawingText( const Point& rStartPos, const OUString& 
rText, sal_Int32 nTextStart, sal_Int32 nTextLen,
-                                   const tools::Long* pDXArray, const SvxFont& 
rFont, sal_Int32 nPara, sal_uInt8 nRightToLeft,
+                                   o3tl::span<const tools::Long> pDXArray, 
const SvxFont& rFont, sal_Int32 nPara, sal_uInt8 nRightToLeft,
                                    const EEngineData::WrongSpellVector* 
pWrongSpellVector,
                                    const SvxFieldData* pFieldData,
                                    bool bEndOfLine,
diff --git a/editeng/source/outliner/outleeng.hxx 
b/editeng/source/outliner/outleeng.hxx
index dcff4b9f8be0..ecc14d61a75c 100644
--- a/editeng/source/outliner/outleeng.hxx
+++ b/editeng/source/outliner/outleeng.hxx
@@ -44,7 +44,7 @@ public:
     virtual void        ParagraphConnected( sal_Int32 nLeftParagraph, 
sal_Int32 nRightParagraph ) override;
 
     virtual void DrawingText( const Point& rStartPos, const OUString& rText, 
sal_Int32 nTextStart,
-                              sal_Int32 nTextLen, const tools::Long* pDXArray, 
const SvxFont& rFont,
+                              sal_Int32 nTextLen, o3tl::span<const 
tools::Long> pDXArray, const SvxFont& rFont,
                               sal_Int32 nPara, sal_uInt8 nRightToLeft,
                               const EEngineData::WrongSpellVector* 
pWrongSpellVector,
                               const SvxFieldData* pFieldData,
diff --git a/editeng/source/outliner/outliner.cxx 
b/editeng/source/outliner/outliner.cxx
index c827b13a5937..48d02130135a 100644
--- a/editeng/source/outliner/outliner.cxx
+++ b/editeng/source/outliner/outliner.cxx
@@ -977,7 +977,7 @@ void Outliner::PaintBullet(sal_Int32 nPara, const Point& 
rStartPos, const Point&
                     aTextPos.AdjustY( -(aMetric.GetDescent()) );
                 }
 
-                DrawingText(aTextPos, pPara->GetText(), 0, 
pPara->GetText().getLength(), aBuf.data(),
+                DrawingText(aTextPos, pPara->GetText(), 0, 
pPara->GetText().getLength(), o3tl::span(aBuf.data(), aBuf.size()),
                     aSvxFont, nPara, bRightToLeftPara ? 1 : 0, nullptr, 
nullptr, false, false, true, nullptr, Color(), Color());
             }
             else
@@ -1653,7 +1653,7 @@ void Outliner::StripPortions()
 }
 
 void Outliner::DrawingText( const Point& rStartPos, const OUString& rText, 
sal_Int32 nTextStart,
-                            sal_Int32 nTextLen, const tools::Long* 
pDXArray,const SvxFont& rFont,
+                            sal_Int32 nTextLen, o3tl::span<const tools::Long> 
pDXArray,const SvxFont& rFont,
                             sal_Int32 nPara, sal_uInt8 nRightToLeft,
                             const EEngineData::WrongSpellVector* 
pWrongSpellVector,
                             const SvxFieldData* pFieldData,
@@ -1679,7 +1679,7 @@ void Outliner::DrawingTab( const Point& rStartPos, 
tools::Long nWidth, const OUS
 {
     if(aDrawPortionHdl.IsSet())
     {
-        DrawPortionInfo aInfo( rStartPos, rChar, 0, rChar.getLength(), rFont, 
nPara, nullptr, nullptr,
+        DrawPortionInfo aInfo( rStartPos, rChar, 0, rChar.getLength(), rFont, 
nPara, {}, nullptr,
             nullptr, nullptr, rOverlineColor, rTextLineColor, nRightToLeft, 
true, nWidth, bEndOfLine, bEndOfParagraph, false);
 
         aDrawPortionHdl.Call( &aInfo );
diff --git a/emfio/inc/mtftools.hxx b/emfio/inc/mtftools.hxx
index 527eae4a5a57..a9de54706f6d 100644
--- a/emfio/inc/mtftools.hxx
+++ b/emfio/inc/mtftools.hxx
@@ -675,7 +675,7 @@ namespace emfio
         );
         void                DrawText(Point& rPosition,
             OUString const & rString,
-            tools::Long* pDXArry = nullptr,
+            std::vector<tools::Long>* pDXArry = nullptr,
             tools::Long* pDYArry = nullptr,
             bool bRecordPath = false,
             sal_Int32 nGraphicsMode = GM_COMPATIBLE);
diff --git a/emfio/source/reader/emfreader.cxx 
b/emfio/source/reader/emfreader.cxx
index f3b114a57c01..ff258182595f 100644
--- a/emfio/source/reader/emfreader.cxx
+++ b/emfio/source/reader/emfreader.cxx
@@ -1939,14 +1939,15 @@ namespace emfio
                                 SAL_INFO("emfio", "\t\tText: " << aText);
                                 SAL_INFO("emfio", "\t\tDxBuffer:");
 
-                                std::unique_ptr<tools::Long[]> pDXAry, pDYAry;
+                                std::vector<tools::Long> aDXAry;
+                                std::unique_ptr<tools::Long[]> pDYAry;
 
                                 sal_Int32 nDxSize;
                                 bool bOverflow = 
o3tl::checked_multiply<sal_Int32>(nLen, (nOptions & ETO_PDY) ? 8 : 4, nDxSize);
                                 if (!bOverflow && offDx && ((nCurPos + offDx + 
nDxSize) <= nNextPos ) && nNextPos <= mnEndPos)
                                 {
                                     mpInputStream->Seek( nCurPos + offDx );
-                                    pDXAry.reset( new 
tools::Long[aText.getLength()] );
+                                    aDXAry.resize(aText.getLength());
                                     if (nOptions & ETO_PDY)
                                     {
                                         pDYAry.reset( new 
tools::Long[aText.getLength()] );
@@ -1965,7 +1966,7 @@ namespace emfio
                                             }
                                         }
 
-                                        pDXAry[i] = 0;
+                                        aDXAry[i] = 0;
                                         if (nOptions & ETO_PDY)
                                         {
                                             pDYAry[i] = 0;
@@ -1975,7 +1976,7 @@ namespace emfio
                                         {
                                             sal_Int32 nDxTmp = 0;
                                             mpInputStream->ReadInt32(nDxTmp);
-                                            pDXAry[i] += nDxTmp;
+                                            aDXAry[i] += nDxTmp;
                                             if (nOptions & ETO_PDY)
                                             {
                                                 sal_Int32 nDyTmp = 0;
@@ -1984,7 +1985,7 @@ namespace emfio
                                             }
                                         }
 
-                                        SAL_INFO("emfio", "\t\t\tSpacing " << 
i << ": " << pDXAry[i]);
+                                        SAL_INFO("emfio", "\t\t\tSpacing " << 
i << ": " << aDXAry[i]);
                                     }
                                 }
                                 if ( nOptions & ETO_CLIPPED )
@@ -1992,7 +1993,7 @@ namespace emfio
                                     Push(); // Save the current clip. It will 
be restored after text drawing
                                     IntersectClipRect( aRect );
                                 }
-                                DrawText(aPos, aText, pDXAry.get(), 
pDYAry.get(), mbRecordPath, nGfxMode);
+                                DrawText(aPos, aText, aDXAry.empty() ? nullptr 
: &aDXAry, pDYAry.get(), mbRecordPath, nGfxMode);
                                 if ( nOptions & ETO_CLIPPED )
                                     Pop();
                             }
diff --git a/emfio/source/reader/mtftools.cxx b/emfio/source/reader/mtftools.cxx
index f78fee7bd5d9..d43a62e665e1 100644
--- a/emfio/source/reader/mtftools.cxx
+++ b/emfio/source/reader/mtftools.cxx
@@ -1677,7 +1677,7 @@ namespace emfio
         }
     }
 
-    void MtfTools::DrawText( Point& rPosition, OUString const & rText, 
tools::Long* pDXArry, tools::Long* pDYArry, bool bRecordPath, sal_Int32 
nGfxMode )
+    void MtfTools::DrawText( Point& rPosition, OUString const & rText, 
std::vector<tools::Long>* pDXArry, tools::Long* pDYArry, bool bRecordPath, 
sal_Int32 nGfxMode )
     {
         UpdateClipRegion();
         rPosition = ImplMap( rPosition );
@@ -1689,13 +1689,13 @@ namespace emfio
             sal_Int32 nSumX = 0, nSumY = 0;
             for (sal_Int32 i = 0; i < rText.getLength(); i++ )
             {
-                nSumX += pDXArry[i];
+                nSumX += (*pDXArry)[i];
 
                 // #i121382# Map DXArray using WorldTransform
                 const Size aSizeX(ImplMap(Size(nSumX, 0)));
                 const basegfx::B2DVector aVectorX(aSizeX.Width(), 
aSizeX.Height());
-                pDXArry[i] = basegfx::fround(aVectorX.getLength());
-                pDXArry[i] *= (nSumX >= 0 ? 1 : -1);
+                (*pDXArry)[i] = basegfx::fround(aVectorX.getLength());
+                (*pDXArry)[i] *= (nSumX >= 0 ? 1 : -1);
 
                 if (pDYArry)
                 {
@@ -1796,9 +1796,9 @@ namespace emfio
             {
                 nTextWidth = pVDev->GetTextWidth( OUString(rText[ nLen - 1 ]) 
);
                 if( nLen > 1 )
-                    nTextWidth += pDXArry[ nLen - 2 ];
+                    nTextWidth += (*pDXArry)[ nLen - 2 ];
                 // tdf#39894: We should consider the distance to next 
character cell origin
-                aActPosDelta.setX( pDXArry[ nLen - 1 ] );
+                aActPosDelta.setX( (*pDXArry)[ nLen - 1 ] );
                 if ( pDYArry )
                 {
                     aActPosDelta.setY( pDYArry[ nLen - 1 ] );
@@ -1859,25 +1859,26 @@ namespace emfio
             {
                 for (sal_Int32 i = 0; i < rText.getLength(); ++i)
                 {
-                    Point aCharDisplacement( i ? pDXArry[i-1] : 0, i ? 
pDYArry[i-1] : 0 );
+                    Point aCharDisplacement( i ? (*pDXArry)[i-1] : 0, i ? 
pDYArry[i-1] : 0 );
                     Point().RotateAround(aCharDisplacement, 
maFont.GetOrientation());
-                    mpGDIMetaFile->AddAction( new MetaTextArrayAction( 
rPosition + aCharDisplacement, OUString( rText[i] ), nullptr, 0, 1 ) );
+                    mpGDIMetaFile->AddAction( new MetaTextArrayAction( 
rPosition + aCharDisplacement, OUString( rText[i] ), o3tl::span<const 
tools::Long>{}, 0, 1 ) );
                 }
             }
             else
             {
                 /* because text without dx array is badly scaled, we
                    will create such an array if necessary */
-                tools::Long* pDX = pDXArry;
+                o3tl::span<const tools::Long> pDX;
                 std::vector<tools::Long> aMyDXArray;
                 if (pDXArry)
                 {
+                    pDX = { pDXArry->data(), pDXArry->size() };
                     // only useful when we have an imported DXArray
                     if(!rText.isEmpty())
                     {
                         maScaledFontHelper.evaluateAlternativeFontScale(
                             rText,
-                            pDXArry[rText.getLength() - 1] // extract imported 
TextLength
+                            (*pDXArry)[rText.getLength() - 1] // extract 
imported TextLength
                         );
                     }
                 }
@@ -1889,7 +1890,7 @@ namespace emfio
                     pVDev->SetMapMode(MapMode(MapUnit::Map100thMM));
                     pVDev->SetFont( maLatestFont );
                     pVDev->GetTextArray( rText, &aMyDXArray, 0, 
rText.getLength());
-                    pDX = aMyDXArray.data();
+                    pDX = { aMyDXArray.data(), aMyDXArray.size() };
                 }
                 mpGDIMetaFile->AddAction( new MetaTextArrayAction( rPosition, 
rText, pDX, 0, rText.getLength() ) );
             }
diff --git a/emfio/source/reader/wmfreader.cxx 
b/emfio/source/reader/wmfreader.cxx
index 62c5168a6bf0..9a04cdeb9823 100644
--- a/emfio/source/reader/wmfreader.cxx
+++ b/emfio/source/reader/wmfreader.cxx
@@ -721,7 +721,8 @@ namespace emfio
                             IntersectClipRect( aRect );
                         }
                         SAL_INFO( "emfio", "\t\t\t Text : " << aText );
-                        std::unique_ptr<tools::Long[]> pDXAry, pDYAry;
+                        std::vector<tools::Long> aDXAry;
+                        std::unique_ptr<tools::Long[]> pDYAry;
                         auto nDxArySize =  nMaxStreamPos - 
mpInputStream->Tell();
                         auto nDxAryEntries = nDxArySize >> 1;
                         bool        bUseDXAry = false;
@@ -729,7 +730,7 @@ namespace emfio
                         if ( ( ( nDxAryEntries % nOriginalTextLen ) == 0 ) && 
( nNewTextLen <= nOriginalTextLen ) )
                         {
                             sal_Int32 i; // needed just outside the for
-                            pDXAry.reset(new tools::Long[ nNewTextLen ]);
+                            aDXAry.resize( nNewTextLen );
                             if ( nOptions & ETO_PDY )
                             {
                                 pDYAry.reset(new tools::Long[ nNewTextLen ]);
@@ -767,7 +768,7 @@ namespace emfio
                                     }
                                 }
 
-                                pDXAry[ i ] = nDx;
+                                aDXAry[ i ] = nDx;
                                 if ( nOptions & ETO_PDY )
                                 {
                                     pDYAry[i] = nDy;
@@ -776,8 +777,8 @@ namespace emfio
                             if ( i == nNewTextLen )
                                 bUseDXAry = true;
                         }
-                        if ( pDXAry && bUseDXAry )
-                            DrawText( aPosition, aText, pDXAry.get(), 
pDYAry.get() );
+                        if ( bUseDXAry )
+                            DrawText( aPosition, aText, &aDXAry, pDYAry.get() 
);
                         else
                             DrawText( aPosition, aText );
                         if ( nOptions & ETO_CLIPPED )
@@ -1256,7 +1257,7 @@ namespace emfio
                                                 {
                                                     Point  aPt;
                                                     sal_uInt32  nStringLen, 
nDXCount;
-                                                    
std::unique_ptr<tools::Long[]> pDXAry;
+                                                    std::vector<tools::Long> 
aDXAry;
                                                     SvMemoryStream 
aMemoryStream( nEscLen );
                                                     
aMemoryStream.WriteBytes(pData.get(), nEscLen);
                                                     aMemoryStream.Seek( 
STREAM_SEEK_TO_BEGIN );
@@ -1274,15 +1275,15 @@ namespace emfio
                                                         if ( ( static_cast< 
sal_uInt64 >( nDXCount ) * sizeof( sal_Int32 ) ) >= ( nEscLen - 
aMemoryStream.Tell() ) )
                                                             nDXCount = 0;
                                                         if ( nDXCount )
-                                                            pDXAry.reset(new 
tools::Long[ nDXCount ]);
+                                                            
aDXAry.resize(nDXCount);
                                                         for  (sal_uInt32 i = 
0; i < nDXCount; i++ )
                                                         {
                                                             sal_Int32 val;
                                                             
aMemoryStream.ReadInt32( val);
-                                                            pDXAry[ i ] = val;
+                                                            aDXAry[ i ] = val;
                                                         }
                                                         
aMemoryStream.ReadUInt32(mnSkipActions);
-                                                        DrawText( aPt, 
aString, pDXAry.get() );
+                                                        DrawText( aPt, 
aString, aDXAry.empty() ? nullptr : &aDXAry );
                                                     }
                                                 }
                                             }
diff --git a/filter/source/svg/svgwriter.cxx b/filter/source/svg/svgwriter.cxx
index addf2897799c..a2eb3eccf065 100644
--- a/filter/source/svg/svgwriter.cxx
+++ b/filter/source/svg/svgwriter.cxx
@@ -2536,7 +2536,7 @@ void SVGActionWriter::ImplWriteMask(GDIMetaFile& rMtf, 
const Point& rDestPt, con
 
 
 void SVGActionWriter::ImplWriteText( const Point& rPos, const OUString& rText,
-                                     const tools::Long* pDXArray, tools::Long 
nWidth )
+                                     o3tl::span<const tools::Long> pDXArray, 
tools::Long nWidth )
 {
     const FontMetric aMetric( mpVDev->GetFontMetric() );
 
@@ -2627,7 +2627,7 @@ void SVGActionWriter::ImplWriteText( const Point& rPos, 
const OUString& rText,
 
 
 void SVGActionWriter::ImplWriteText( const Point& rPos, const OUString& rText,
-                                     const tools::Long* pDXArray, tools::Long 
nWidth,
+                                     o3tl::span<const tools::Long> pDXArray, 
tools::Long nWidth,
                                      Color aTextColor )
 {
     sal_Int32                               nLen = rText.getLength();
@@ -2646,10 +2646,10 @@ void SVGActionWriter::ImplWriteText( const Point& rPos, 
const OUString& rText,
 
     std::vector<tools::Long> aTmpArray(nLen);
     // get text sizes
-    if( pDXArray )
+    if( !pDXArray.empty() )
     {
         aNormSize = Size( mpVDev->GetTextWidth( rText ), 0 );
-        memcpy(aTmpArray.data(), pDXArray, nLen * sizeof(tools::Long));
+        memcpy(aTmpArray.data(), pDXArray.data(), nLen * sizeof(tools::Long));
     }
     else
     {
@@ -3764,7 +3764,7 @@ void SVGActionWriter::ImplWriteActions( const 
GDIMetaFile& rMtf,
                         {
                             vcl::Font aFont = ImplSetCorrectFontHeight();
                             maAttributeWriter.SetFontAttr( aFont );
-                            ImplWriteText( pA->GetPoint(), aText, nullptr, 0 );
+                            ImplWriteText( pA->GetPoint(), aText, {}, 0 );
                         }
                         else
                         {
@@ -3787,7 +3787,7 @@ void SVGActionWriter::ImplWriteActions( const 
GDIMetaFile& rMtf,
                         {
                             vcl::Font aFont = ImplSetCorrectFontHeight();
                             maAttributeWriter.SetFontAttr( aFont );
-                            ImplWriteText( pA->GetRect().TopLeft(), 
pA->GetText(), nullptr, 0 );
+                            ImplWriteText( pA->GetRect().TopLeft(), 
pA->GetText(), {}, 0 );
                         }
                         maTextWriter.writeTextPortion( 
pA->GetRect().TopLeft(), pA->GetText() );
                     }
@@ -3809,7 +3809,7 @@ void SVGActionWriter::ImplWriteActions( const 
GDIMetaFile& rMtf,
                         {
                             vcl::Font aFont = ImplSetCorrectFontHeight();
                             maAttributeWriter.SetFontAttr( aFont );
-                            ImplWriteText( pA->GetPoint(), aText, 
pA->GetDXArray(), 0 );
+                            ImplWriteText( pA->GetPoint(), aText, { 
pA->GetDXArray().data(), pA->GetDXArray().size() }, 0 );
                         }
                         else
                         {
@@ -3834,7 +3834,7 @@ void SVGActionWriter::ImplWriteActions( const 
GDIMetaFile& rMtf,
                         {
                             vcl::Font aFont = ImplSetCorrectFontHeight();
                             maAttributeWriter.SetFontAttr( aFont );
-                            ImplWriteText( pA->GetPoint(), aText, nullptr, 
pA->GetWidth() );
+                            ImplWriteText( pA->GetPoint(), aText, {}, 
pA->GetWidth() );
                         }
                         else
                         {
diff --git a/filter/source/svg/svgwriter.hxx b/filter/source/svg/svgwriter.hxx
index 2dd32bacca26..81c71e5cd149 100644
--- a/filter/source/svg/svgwriter.hxx
+++ b/filter/source/svg/svgwriter.hxx
@@ -345,8 +345,8 @@ private:
     static Color            ImplGetColorWithIntensity( const Color& rColor, 
sal_uInt16 nIntensity );
     static Color            ImplGetGradientColor( const Color& rStartColor, 
const Color& rEndColor, double fOffset );
     void                    ImplWriteMask( GDIMetaFile& rMtf, const Point& 
rDestPt, const Size& rDestSize, const Gradient& rGradient, sal_uInt32 
nWriteFlags );
-    void                    ImplWriteText( const Point& rPos, const OUString& 
rText, const tools::Long* pDXArray, tools::Long nWidth );
-    void                    ImplWriteText( const Point& rPos, const OUString& 
rText, const tools::Long* pDXArray, tools::Long nWidth, Color aTextColor );
+    void                    ImplWriteText( const Point& rPos, const OUString& 
rText, o3tl::span<const tools::Long> pDXArray, tools::Long nWidth );
+    void                    ImplWriteText( const Point& rPos, const OUString& 
rText, o3tl::span<const tools::Long> pDXArray, tools::Long nWidth, Color 
aTextColor );
     void                    ImplWriteBmp( const BitmapEx& rBmpEx, const Point& 
rPt, const Size& rSz, const Point& rSrcPt, const Size& rSrcSz, const 
css::uno::Reference<css::drawing::XShape>* pShape);
 
     void                    ImplWriteActions( const GDIMetaFile& rMtf,
diff --git a/include/editeng/editeng.hxx b/include/editeng/editeng.hxx
index db50eb2ac5ec..3006e178783c 100644
--- a/include/editeng/editeng.hxx
+++ b/include/editeng/editeng.hxx
@@ -29,6 +29,7 @@
 #include <com/sun/star/i18n/WordType.hpp>
 #include <com/sun/star/i18n/CharacterIteratorMode.hpp>
 
+#include <o3tl/span.hxx>
 #include <svl/typedwhich.hxx>
 #include <editeng/editdata.hxx>
 #include <editeng/editstat.hxx>
@@ -497,7 +498,7 @@ public:
 
     virtual void DrawingText( const Point& rStartPos, const OUString& rText,
                               sal_Int32 nTextStart, sal_Int32 nTextLen,
-                              const tools::Long* pDXArray, const SvxFont& 
rFont,
+                              o3tl::span<const tools::Long> pDXArray, const 
SvxFont& rFont,
                               sal_Int32 nPara, sal_uInt8 nRightToLeft,
                               const EEngineData::WrongSpellVector* 
pWrongSpellVector,
                               const SvxFieldData* pFieldData,
diff --git a/include/editeng/outliner.hxx b/include/editeng/outliner.hxx
index 5003a671d35e..98fc4ff41667 100644
--- a/include/editeng/outliner.hxx
+++ b/include/editeng/outliner.hxx
@@ -395,7 +395,7 @@ public:
     sal_Int32           mnTextLen;
     sal_Int32           mnPara;
     const SvxFont&      mrFont;
-    const tools::Long*         mpDXArray;
+    o3tl::span<const tools::Long> mpDXArray;
 
     const EEngineData::WrongSpellVector*  mpWrongSpellVector;
     const SvxFieldData* mpFieldData;
@@ -421,7 +421,7 @@ public:
         sal_Int32 nTxtLen,
         const SvxFont& rFnt,
         sal_Int32 nPar,
-        const tools::Long* pDXArr,
+        o3tl::span<const tools::Long> pDXArr,
         const EEngineData::WrongSpellVector* pWrongSpellVector,
         const SvxFieldData* pFieldData,
         const css::lang::Locale* pLocale,
@@ -813,7 +813,7 @@ public:
 
     void DrawingText( const Point& rStartPos, const OUString& rText,
                               sal_Int32 nTextStart, sal_Int32 nTextLen,
-                              const tools::Long* pDXArray, const SvxFont& 
rFont,
+                              o3tl::span<const tools::Long> pDXArray, const 
SvxFont& rFont,
                               sal_Int32 nPara, sal_uInt8 nRightToLeft,
                               const EEngineData::WrongSpellVector* 
pWrongSpellVector,
                               const SvxFieldData* pFieldData,
diff --git a/include/editeng/svxfont.hxx b/include/editeng/svxfont.hxx
index fb0b8dbc97de..eabffc4f6301 100644
--- a/include/editeng/svxfont.hxx
+++ b/include/editeng/svxfont.hxx
@@ -20,6 +20,7 @@
 #define INCLUDED_EDITENG_SVXFONT_HXX
 
 #include <editeng/svxenum.hxx>
+#include <o3tl/span.hxx>
 #include <tools/long.hxx>
 #include <vcl/font.hxx>
 #include <editeng/editengdllapi.h>
@@ -95,7 +96,7 @@ public:
                      const sal_Int32 nIdx = 0, const sal_Int32 nLen = 
SAL_MAX_INT32) const;
 
     void QuickDrawText( OutputDevice *pOut, const Point &rPos, const OUString 
&rTxt,
-                        const sal_Int32 nIdx = 0, const sal_Int32 nLen = 
SAL_MAX_INT32, const tools::Long* pDXArray = nullptr ) const;
+                        const sal_Int32 nIdx = 0, const sal_Int32 nLen = 
SAL_MAX_INT32, o3tl::span<const tools::Long> pDXArray = {} ) const;
 
     Size QuickGetTextSize( const OutputDevice *pOut, const OUString &rTxt,
                          const sal_Int32 nIdx, const sal_Int32 nLen, 
std::vector<tools::Long>* pDXArray = nullptr ) const;
diff --git a/include/o3tl/span.hxx b/include/o3tl/span.hxx
index 8af8ba846b65..087d1f9d69c3 100644
--- a/include/o3tl/span.hxx
+++ b/include/o3tl/span.hxx
@@ -25,6 +25,7 @@ namespace o3tl { using std::span; }
 #include <cassert>
 #include <cstddef>
 #include <iterator>
+#include <type_traits>
 
 namespace o3tl {
 
@@ -57,6 +58,10 @@ public:
         assert(a != nullptr || len == 0);
     }
 
+    /** for assigning from span<T> to span<const T> */
+    constexpr span (const span<typename std::remove_const<T>::type>& other) 
noexcept
+        : data_(other.data()), size_(other.size()) {}
+
     constexpr bool empty() const noexcept { return size_ == 0; }
 
     constexpr iterator begin() const noexcept { return data_; }
diff --git a/include/vcl/metaact.hxx b/include/vcl/metaact.hxx
index ed74de84d5cd..43251d0facc2 100644
--- a/include/vcl/metaact.hxx
+++ b/include/vcl/metaact.hxx
@@ -24,6 +24,7 @@
 
 #include <config_options.h>
 
+#include <o3tl/span.hxx>
 #include <rtl/ref.hxx>
 #include <salhelper/simplereferenceobject.hxx>
 #include <tools/poly.hxx>
@@ -505,8 +506,7 @@ private:
 
     Point       maStartPt;
     OUString    maStr;
-    std::unique_ptr<tools::Long[]>
-                mpDXAry;
+    std::vector<::tools::Long> maDXAry;
     sal_Int32   mnIndex;
     sal_Int32   mnLen;
 
@@ -516,7 +516,10 @@ public:
                         MetaTextArrayAction();
                         MetaTextArrayAction( const MetaTextArrayAction& 
rAction );
     MetaTextArrayAction( const Point& rStartPt, const OUString& rStr,
-                         const tools::Long* pDXAry, sal_Int32 nIndex,
+                         const std::vector<tools::Long>& rDXAry, sal_Int32 
nIndex,
+                         sal_Int32 nLen );
+    MetaTextArrayAction( const Point& rStartPt, const OUString& rStr,
+                         o3tl::span<const tools::Long> pDXAry, sal_Int32 
nIndex,
                          sal_Int32 nLen );
 
     virtual void        Execute( OutputDevice* pOut ) override;
@@ -530,12 +533,12 @@ public:
     const OUString& GetText() const { return maStr; }
     sal_Int32       GetIndex() const { return mnIndex; }
     sal_Int32       GetLen() const { return mnLen; }
-    tools::Long*    GetDXArray() const { return mpDXAry.get(); }
+    const std::vector<tools::Long> & GetDXArray() const { return maDXAry; }
     void            SetPoint(const Point& rPt) { maStartPt = rPt; }
     void            SetText(const OUString& rStr) { maStr = rStr; }
     void            SetIndex(sal_Int32 rIndex) { mnIndex = rIndex; }
     void            SetLen(sal_Int32 rLen) { mnLen = rLen; }
-    void            SetDXArray(std::unique_ptr<tools::Long[]> aArray);
+    void            SetDXArray(std::vector<tools::Long> aArray);
 };
 
 class SAL_DLLPUBLIC_RTTI MetaStretchTextAction final : public MetaAction
diff --git a/include/vcl/outdev.hxx b/include/vcl/outdev.hxx
index ed9e38f9fdbd..0075015dee28 100644
--- a/include/vcl/outdev.hxx
+++ b/include/vcl/outdev.hxx
@@ -21,6 +21,7 @@
 
 #include <sal/config.h>
 
+#include <o3tl/span.hxx>
 #include <tools/gen.hxx>
 #include <tools/ref.hxx>
 #include <tools/solar.h>
@@ -969,7 +970,7 @@ public:
     */
     bool                        GetTextBoundRect( tools::Rectangle& rRect,
                                                   const OUString& rStr, 
sal_Int32 nBase = 0, sal_Int32 nIndex = 0, sal_Int32 nLen = -1,
-                                                  sal_uLong nLayoutWidth = 0, 
const tools::Long* pDXArray = nullptr,
+                                                  sal_uLong nLayoutWidth = 0, 
o3tl::span<const tools::Long> pDXArray = {},
                                                   const SalLayoutGlyphs* 
pGlyphs = nullptr ) const;
 
     tools::Rectangle            ImplGetTextBoundRect( const SalLayout& ) const;
@@ -980,12 +981,12 @@ public:
     bool                        GetTextOutlines( PolyPolyVector&,
                                                  const OUString& rStr, 
sal_Int32 nBase = 0, sal_Int32 nIndex = 0,
                                                  sal_Int32 nLen = -1,
-                                                 sal_uLong nLayoutWidth = 0, 
const tools::Long* pDXArray = nullptr ) const;
+                                                 sal_uLong nLayoutWidth = 0, 
o3tl::span<const tools::Long> pDXArray = {} ) const;
 
     bool                        GetTextOutlines( basegfx::B2DPolyPolygonVector 
&rVector,
                                                  const OUString& rStr, 
sal_Int32 nBase, sal_Int32 nIndex = 0,
                                                  sal_Int32 nLen = -1,
-                                                 sal_uLong nLayoutWidth = 0, 
const tools::Long* pDXArray = nullptr ) const;
+                                                 sal_uLong nLayoutWidth = 0, 
o3tl::span<const tools::Long> pDXArray = {} ) const;
 
 
     OUString                    GetEllipsisString( const OUString& rStr, 
tools::Long nMaxWidth,
@@ -1050,7 +1051,7 @@ public:
     float                       approximate_digit_width() const;
 
     void                        DrawTextArray( const Point& rStartPt, const 
OUString& rStr,
-                                               const tools::Long* pDXAry,
+                                               o3tl::span<const tools::Long> 
pDXAry,
                                                sal_Int32 nIndex = 0,
                                                sal_Int32 nLen = -1,
                                                SalLayoutFlags flags = 
SalLayoutFlags::NONE,
@@ -1236,7 +1237,7 @@ public:
     std::unique_ptr<SalLayout>
                                 ImplLayout( const OUString&, sal_Int32 nIndex, 
sal_Int32 nLen,
                                             const Point& rLogicPos = 
Point(0,0), tools::Long nLogicWidth=0,
-                                            const tools::Long* 
pLogicDXArray=nullptr, SalLayoutFlags flags = SalLayoutFlags::NONE,
+                                            o3tl::span<const tools::Long> 
pLogicDXArray={}, SalLayoutFlags flags = SalLayoutFlags::NONE,
                                             vcl::text::TextLayoutCache const* 
= nullptr,
                                             const SalLayoutGlyphs* pGlyphs = 
nullptr) const;
     SAL_DLLPRIVATE vcl::text::ImplLayoutArgs ImplPrepareLayoutArgs( OUString&, 
const sal_Int32 nIndex, const sal_Int32 nLen,
diff --git a/include/vcl/pdfwriter.hxx b/include/vcl/pdfwriter.hxx
index 3601c88501f9..5a566937e373 100644
--- a/include/vcl/pdfwriter.hxx
+++ b/include/vcl/pdfwriter.hxx
@@ -746,7 +746,7 @@ The following structure describes the permissions used in 
PDF security
                                       FontLineStyle eUnderline,
                                       FontLineStyle eOverline );
     void                DrawTextArray( const Point& rStartPt, const OUString& 
rStr,
-                                       const tools::Long* pDXAry,
+                                       o3tl::span<const tools::Long> pDXAry,
                                        sal_Int32 nIndex,
                                        sal_Int32 nLen );
     void                DrawStretchText( const Point& rStartPt, sal_uLong 
nWidth,
diff --git a/sc/source/ui/view/output2.cxx b/sc/source/ui/view/output2.cxx
index 098d66048e91..53eb899af9b9 100644
--- a/sc/source/ui/view/output2.cxx
+++ b/sc/source/ui/view/output2.cxx
@@ -811,7 +811,7 @@ const SalLayoutGlyphs* 
ScDrawStringsVars::GetLayoutGlyphs(const OUString& rStrin
     if( it != mCachedGlyphs.end() && it->second.IsValid())
         return &it->second;
     std::unique_ptr<SalLayout> layout = pOutput->pFmtDevice->ImplLayout( 
rString, 0, rString.getLength(),
-        Point( 0, 0 ), 0, nullptr, SalLayoutFlags::GlyphItemsOnly );
+        Point( 0, 0 ), 0, {}, SalLayoutFlags::GlyphItemsOnly );
     if( layout )
     {
         mCachedGlyphs.insert( std::make_pair( key, layout->GetGlyphs()));
@@ -2146,7 +2146,7 @@ tools::Rectangle ScOutputData::LayoutStrings(bool 
bPixelToLogic, bool bPaint, co
                                 }
 
                                 if (bPaint)
-                                    mpDev->DrawTextArray(aDrawTextPos, aShort, 
aDX.data());
+                                    mpDev->DrawTextArray(aDrawTextPos, aShort, 
{aDX.data(), aDX.size()});
                             }
                             else
                             {
diff --git a/sfx2/source/doc/SfxRedactionHelper.cxx 
b/sfx2/source/doc/SfxRedactionHelper.cxx
index 28cf18d94ebf..5bb43fcc422a 100644
--- a/sfx2/source/doc/SfxRedactionHelper.cxx
+++ b/sfx2/source/doc/SfxRedactionHelper.cxx
@@ -141,9 +141,11 @@ tools::Rectangle ImplCalcActionBounds(const MetaAction& 
rAct, const OutputDevice
             {
                 // #105987# ImplLayout takes everything in logical coordinates
                 std::unique_ptr<SalLayout> pSalLayout1 = rOut.ImplLayout(
-                    aString, 0, nStrStartPos, rTextAct.GetPoint(), 0, 
rTextAct.GetDXArray());
+                    aString, 0, nStrStartPos, rTextAct.GetPoint(), 0,
+                    { rTextAct.GetDXArray().data(), 
rTextAct.GetDXArray().size() });
                 std::unique_ptr<SalLayout> pSalLayout2 = rOut.ImplLayout(
-                    aString, 0, nStrEndPos, rTextAct.GetPoint(), 0, 
rTextAct.GetDXArray());
+                    aString, 0, nStrEndPos, rTextAct.GetPoint(), 0,
+                    { rTextAct.GetDXArray().data(), 
rTextAct.GetDXArray().size() });
                 if (pSalLayout2)
                 {
                     tools::Rectangle 
aBoundRect2(rOut.ImplGetTextBoundRect(*pSalLayout2));
diff --git a/svtools/source/control/ruler.cxx b/svtools/source/control/ruler.cxx
index c4af43b1d267..d3d5af0e00de 100644
--- a/svtools/source/control/ruler.cxx
+++ b/svtools/source/control/ruler.cxx
@@ -79,7 +79,7 @@ SalLayoutGlyphs* lcl_GetRulerTextGlyphs(const 
vcl::RenderContext& rRenderContext
     // Calculate glyph items.
 
     std::unique_ptr<SalLayout> pLayout = rRenderContext.ImplLayout(
-        rText, 0, rText.getLength(), Point(0, 0), 0, nullptr, 
SalLayoutFlags::GlyphItemsOnly);
+        rText, 0, rText.getLength(), Point(0, 0), 0, {}, 
SalLayoutFlags::GlyphItemsOnly);
     if (!pLayout)
         return nullptr;
 
@@ -339,7 +339,7 @@ void Ruler::ImplVDrawText(vcl::RenderContext& 
rRenderContext, tools::Long nX, to
     tools::Rectangle aRect;
     SalLayoutGlyphs* pTextLayout
         = lcl_GetRulerTextGlyphs(rRenderContext, rText, maTextGlyphs[rText]);
-    rRenderContext.GetTextBoundRect(aRect, rText, 0, 0, -1, 0, nullptr, 
pTextLayout);
+    rRenderContext.GetTextBoundRect(aRect, rText, 0, 0, -1, 0, {}, 
pTextLayout);
 
     tools::Long nShiftX = ( aRect.GetWidth() / 2 ) + aRect.Left();
     tools::Long nShiftY = ( aRect.GetHeight() / 2 ) + aRect.Top();
diff --git a/svx/source/customshapes/EnhancedCustomShapeFontWork.cxx 
b/svx/source/customshapes/EnhancedCustomShapeFontWork.cxx
index 32fd10661433..38a4c441f53c 100644
--- a/svx/source/customshapes/EnhancedCustomShapeFontWork.cxx
+++ b/svx/source/customshapes/EnhancedCustomShapeFontWork.cxx
@@ -326,7 +326,7 @@ static void GetTextAreaOutline(
                 {
                     FWCharacterData aCharacterData;
                     OUString aCharText( rText[ i ] );
-                    if ( pVirDev->GetTextOutlines( aCharacterData.vOutlines, 
aCharText, 0, 0, -1, nWidth, nullptr ) )
+                    if ( pVirDev->GetTextOutlines( aCharacterData.vOutlines, 
aCharText, 0, 0, -1, nWidth, {} ) )
                     {
                         sal_Int32 nTextWidth = pVirDev->GetTextWidth( 
aCharText);
                         if ( aCharacterData.vOutlines.empty() )
@@ -372,7 +372,7 @@ static void GetTextAreaOutline(
                     pVirDev->SetFont( aFont );
                 }
                 FWCharacterData aCharacterData;
-                if ( pVirDev->GetTextOutlines( aCharacterData.vOutlines, 
rText, 0, 0, -1, nWidth, aDXArry.empty() ? nullptr : aDXArry.data() ) )
+                if ( pVirDev->GetTextOutlines( aCharacterData.vOutlines, 
rText, 0, 0, -1, nWidth, { aDXArry.data(), aDXArry.size() } ) )
                 {
                     rParagraph.vCharacters.push_back( aCharacterData );
                 }
diff --git a/svx/source/svdraw/svdotextdecomposition.cxx 
b/svx/source/svdraw/svdotextdecomposition.cxx
index 5c225cf7948b..ce6fa2206326 100644
--- a/svx/source/svdraw/svdotextdecomposition.cxx
+++ b/svx/source/svdraw/svdotextdecomposition.cxx
@@ -223,7 +223,7 @@ namespace
         // the text transformation), scale it to unit coordinates
         ::std::vector< double > aDXArray;
 
-        if(rInfo.mpDXArray && rInfo.mnTextLen)
+        if(!rInfo.mpDXArray.empty() && rInfo.mnTextLen)
         {
             aDXArray.reserve(rInfo.mnTextLen);
 
diff --git a/svx/source/svdraw/svdotextpathdecomposition.cxx 
b/svx/source/svdraw/svdotextpathdecomposition.cxx
index 65f7ac1eb505..4f3144d25851 100644
--- a/svx/source/svdraw/svdotextpathdecomposition.cxx
+++ b/svx/source/svdraw/svdotextpathdecomposition.cxx
@@ -79,7 +79,7 @@ namespace
             maLocale(rInfo.mpLocale ? *rInfo.mpLocale : css::lang::Locale()),
             mbRTL(!rInfo.mrFont.IsVertical() && rInfo.IsRTL())
         {
-            if(mnTextLength && rInfo.mpDXArray)
+            if(mnTextLength && !rInfo.mpDXArray.empty())
             {
                 maDblDXArray.reserve(mnTextLength);
 
diff --git a/sw/source/core/txtnode/fntcache.cxx 
b/sw/source/core/txtnode/fntcache.cxx
index bfca43e92147..9db05f74ff0b 100644
--- a/sw/source/core/txtnode/fntcache.cxx
+++ b/sw/source/core/txtnode/fntcache.cxx
@@ -211,7 +211,7 @@ static SalLayoutGlyphs* lcl_CreateLayout(const 
SwTextGlyphsKey& rKey, SwTextGlyp
     // Calculate glyph items.
     std::unique_ptr<SalLayout> pLayout
         = rKey.m_pOutputDevice->ImplLayout(rKey.m_aText, rKey.m_nIndex, 
rKey.m_nLength, Point(0, 0), 0,
-                                           nullptr, eGlyphItemsOnlyLayout);
+                                           {}, eGlyphItemsOnlyLayout);
     if (!pLayout)
         return nullptr;
 
@@ -1114,7 +1114,7 @@ void SwFntObj::DrawText( SwDrawTextInfo &rInf )
                 rInf.GetFrame()->SwitchHorizontalToVertical( aTextOriginPos );
 
             rInf.GetOut().DrawTextArray( aTextOriginPos, rInf.GetText(),
-                aKernArray.data(), sal_Int32(rInf.GetIdx()), 
sal_Int32(rInf.GetLen()));
+                { aKernArray.data(), aKernArray.size() }, 
sal_Int32(rInf.GetIdx()), sal_Int32(rInf.GetLen()));
 
             return;
         }
@@ -1200,20 +1200,20 @@ void SwFntObj::DrawText( SwDrawTextInfo &rInf )
                             {
                                 aKernArray[0] = rInf.GetWidth() + nSpaceAdd;
                                 rInf.GetOut().DrawTextArray( aTextOriginPos, 
rInf.GetText(),
-                                    aKernArray.data(), 
sal_Int32(rInf.GetIdx()), 1);
+                                    { aKernArray.data(), aKernArray.size() }, 
sal_Int32(rInf.GetIdx()), 1);
                             }
                             else
                             {
                                 aKernArray[sal_Int32(rInf.GetLen()) - 2] += 
nSpaceAdd;
                                 rInf.GetOut().DrawTextArray( aTextOriginPos, 
rInf.GetText(),
-                                    aKernArray.data(), 
sal_Int32(rInf.GetIdx()),
+                                    { aKernArray.data(), aKernArray.size() }, 
sal_Int32(rInf.GetIdx()),
                                     sal_Int32(rInf.GetLen()));
                             }
                         }
                         else
                         {
                             rInf.GetOut().DrawTextArray( aTextOriginPos, 
rInf.GetText(),
-                                aKernArray.data(), sal_Int32(rInf.GetIdx()),
+                                { aKernArray.data(), aKernArray.size() }, 
sal_Int32(rInf.GetIdx()),
                                 sal_Int32(rInf.GetLen()));
                         }
                     }
@@ -1230,7 +1230,7 @@ void SwFntObj::DrawText( SwDrawTextInfo &rInf )
                         }
 
                         rInf.GetOut().DrawTextArray(aTextOriginPos,
-                                rInf.GetText(), aKernArray.data(),
+                                rInf.GetText(), { aKernArray.data(), 
aKernArray.size() },
                                 sal_Int32(rInf.GetIdx()),
                                 sal_Int32(rInf.GetLen()));
                     }
@@ -1247,7 +1247,7 @@ void SwFntObj::DrawText( SwDrawTextInfo &rInf )
                     aKernArray[i] += nGridAddSum;
                 }
                 rInf.GetOut().DrawTextArray( aTextOriginPos, rInf.GetText(),
-                    aKernArray.data(), sal_Int32(rInf.GetIdx()), 
sal_Int32(rInf.GetLen()));
+                    { aKernArray.data(), aKernArray.size() }, 
sal_Int32(rInf.GetIdx()), sal_Int32(rInf.GetLen()));
             }
             return;
         }
@@ -1401,18 +1401,18 @@ void SwFntObj::DrawText( SwDrawTextInfo &rInf )
                         aKernArray[0] = rInf.GetWidth() + nSpaceAdd;
 
                         rInf.GetOut().DrawTextArray( aTextOriginPos, 
rInf.GetText(),
-                             aKernArray.data(), sal_Int32(rInf.GetIdx()), 1 );
+                             { aKernArray.data(), aKernArray.size() }, 
sal_Int32(rInf.GetIdx()), 1 );
                     }
                     else
                     {
                         aKernArray[ sal_Int32(rInf.GetLen()) - 2 ] += 
nSpaceAdd;
                         rInf.GetOut().DrawTextArray( aTextOriginPos, 
rInf.GetText(),
-                            aKernArray.data(), sal_Int32(rInf.GetIdx()), 
sal_Int32(rInf.GetLen()));
+                            { aKernArray.data(), aKernArray.size() }, 
sal_Int32(rInf.GetIdx()), sal_Int32(rInf.GetLen()));
                     }
                 }
                 else
                     rInf.GetOut().DrawTextArray( aTextOriginPos, 
rInf.GetText(),
-                            aKernArray.data(), sal_Int32(rInf.GetIdx()), 
sal_Int32(rInf.GetLen()));
+                            { aKernArray.data(), aKernArray.size() }, 
sal_Int32(rInf.GetIdx()), sal_Int32(rInf.GetLen()));
             }
             else
             {
@@ -1651,9 +1651,9 @@ void SwFntObj::DrawText( SwDrawTextInfo &rInf )
                 rInf.GetFrame()->SwitchHorizontalToVertical( aTextOriginPos );
 
             rInf.GetOut().DrawTextArray( aTextOriginPos, rInf.GetText(),
-                         aKernArray.data(), sal_Int32(rInf.GetIdx()), 1 );
+                         { aKernArray.data(), aKernArray.size() }, 
sal_Int32(rInf.GetIdx()), 1 );
             if( bBullet )
-                rInf.GetOut().DrawTextArray( aTextOriginPos, *pStr, 
aKernArray.data(),
+                rInf.GetOut().DrawTextArray( aTextOriginPos, *pStr, { 
aKernArray.data(), aKernArray.size() },
                                              rInf.GetIdx() ? 1 : 0, 1 );
         }
         else
@@ -1842,7 +1842,7 @@ void SwFntObj::DrawText( SwDrawTextInfo &rInf )
                             : sal_Int32(rInf.GetIdx());
                 aGlyphsKey = SwTextGlyphsKey{ &rInf.GetOut(), *pStr, nTmpIdx, 
nLen };
                 pGlyphs = GetCachedSalLayoutGlyphs(aGlyphsKey);
-                rInf.GetOut().DrawTextArray( aTextOriginPos, *pStr, 
aKernArray.data(),
+                rInf.GetOut().DrawTextArray( aTextOriginPos, *pStr, { 
aKernArray.data(), aKernArray.size() },
                                              nTmpIdx , nLen, 
SalLayoutFlags::NONE, pGlyphs );
                 if (bBullet)
                 {
@@ -1880,7 +1880,7 @@ void SwFntObj::DrawText( SwDrawTextInfo &rInf )
                                 aKernArray [ i - 1 ] -= nAdd;
                         }
                     }
-                    rInf.GetOut().DrawTextArray( aTextOriginPos, 
aBulletOverlay, aKernArray.data(),
+                    rInf.GetOut().DrawTextArray( aTextOriginPos, 
aBulletOverlay, { aKernArray.data(), aKernArray.size() },
                                                  nTmpIdx , nLen );
                     pTmpFont->SetColor( aPreviousColor );
 
diff --git a/toolkit/source/awt/vclxgraphics.cxx 
b/toolkit/source/awt/vclxgraphics.cxx
index c644afded55f..e735a2eedcfd 100644
--- a/toolkit/source/awt/vclxgraphics.cxx
+++ b/toolkit/source/awt/vclxgraphics.cxx
@@ -465,12 +465,12 @@ void VCLXGraphics::drawTextArray( sal_Int32 x, sal_Int32 
y, const OUString& rTex
     if( mpOutputDevice )
     {
         InitOutputDevice( InitOutDevFlags::COLORS|InitOutDevFlags::FONT );
-        std::unique_ptr<tools::Long []> pDXA(new 
tools::Long[rText.getLength()]);
+        std::vector<tools::Long> aDXA(rText.getLength());
         for(int i = 0; i < rText.getLength(); i++)
         {
-            pDXA[i] = rLongs[i];
+            aDXA[i] = rLongs[i];
         }
-        mpOutputDevice->DrawTextArray( Point( x, y ), rText, pDXA.get() );
+        mpOutputDevice->DrawTextArray( Point( x, y ), rText, 
o3tl::span(aDXA.data(), aDXA.size()) );
     }
 }
 
diff --git a/vcl/inc/pdf/pdfwriter_impl.hxx b/vcl/inc/pdf/pdfwriter_impl.hxx
index c3f63be2693d..b07b7d7bbfce 100644
--- a/vcl/inc/pdf/pdfwriter_impl.hxx
+++ b/vcl/inc/pdf/pdfwriter_impl.hxx
@@ -1176,7 +1176,7 @@ public:
 
     /* actual drawing functions */
     void drawText( const Point& rPos, const OUString& rText, sal_Int32 nIndex, 
sal_Int32 nLen, bool bTextLines = true );
-    void drawTextArray( const Point& rPos, const OUString& rText, const 
tools::Long* pDXArray, sal_Int32 nIndex, sal_Int32 nLen );
+    void drawTextArray( const Point& rPos, const OUString& rText, 
o3tl::span<const tools::Long> pDXArray, sal_Int32 nIndex, sal_Int32 nLen );
     void drawStretchText( const Point& rPos, sal_uLong nWidth, const OUString& 
rText,
                           sal_Int32 nIndex, sal_Int32 nLen  );
     void drawText( const tools::Rectangle& rRect, const OUString& rOrigStr, 
DrawTextFlags nStyle );
diff --git a/vcl/qa/cppunit/complextext.cxx b/vcl/qa/cppunit/complextext.cxx
index 5b16b4d06e74..76570ed579bf 100644
--- a/vcl/qa/cppunit/complextext.cxx
+++ b/vcl/qa/cppunit/complextext.cxx
@@ -126,7 +126,7 @@ void VclComplexTextTest::testKashida()
     auto aText
         = OUString(u"عنصر الفوسفور عنصر فلزي صلب. تتكون الدورة الرابعة من 15 
عنصرا.");
     std::unique_ptr<SalLayout> pLayout = pOutputDevice->ImplLayout(
-        aText, 0, aText.getLength(), Point(0, 0), 0, nullptr, 
SalLayoutFlags::GlyphItemsOnly);
+        aText, 0, aText.getLength(), Point(0, 0), 0, {}, 
SalLayoutFlags::GlyphItemsOnly);
     SalLayoutGlyphs aGlyphs = pLayout->GetGlyphs();
     CPPUNIT_ASSERT(aGlyphs.IsValid());
     CPPUNIT_ASSERT(aGlyphs.Impl(0) != nullptr);
@@ -156,7 +156,7 @@ void VclComplexTextTest::testTdf95650()
 
     OutputDevice *pOutDev = pWin->GetOutDev();
     // Check that the following executes without failing assertion
-    pOutDev->ImplLayout(aTxt, 9, 1, Point(), 0, nullptr, 
SalLayoutFlags::BiDiRtl);
+    pOutDev->ImplLayout(aTxt, 9, 1, Point(), 0, {}, SalLayoutFlags::BiDiRtl);
 }
 
 static void testCachedGlyphs( const OUString& aText, const OUString& aFontName 
= OUString())
@@ -170,13 +170,13 @@ static void testCachedGlyphs( const OUString& aText, 
const OUString& aFontName =
     }
     // Get the glyphs for the text.
     std::unique_ptr<SalLayout> pLayout1 = pOutputDevice->ImplLayout(
-        aText, 0, aText.getLength(), Point(0, 0), 0, nullptr, 
SalLayoutFlags::GlyphItemsOnly);
+        aText, 0, aText.getLength(), Point(0, 0), 0, {}, 
SalLayoutFlags::GlyphItemsOnly);
     SalLayoutGlyphs aGlyphs1 = pLayout1->GetGlyphs();
     CPPUNIT_ASSERT_MESSAGE(message, aGlyphs1.IsValid());
     CPPUNIT_ASSERT_MESSAGE(message, aGlyphs1.Impl(0) != nullptr);
     // Reuse the cached glyphs to get glyphs again.
     std::unique_ptr<SalLayout> pLayout2 = pOutputDevice->ImplLayout(
-        aText, 0, aText.getLength(), Point(0, 0), 0, nullptr, 
SalLayoutFlags::GlyphItemsOnly, nullptr, &aGlyphs1);
+        aText, 0, aText.getLength(), Point(0, 0), 0, {}, 
SalLayoutFlags::GlyphItemsOnly, nullptr, &aGlyphs1);
     SalLayoutGlyphs aGlyphs2 = pLayout2->GetGlyphs();
     CPPUNIT_ASSERT_MESSAGE(message, aGlyphs2.IsValid());
     // And check it's the same.
diff --git a/vcl/qa/cppunit/text.cxx b/vcl/qa/cppunit/text.cxx
index e56d1f27823e..eef1478286d5 100644
--- a/vcl/qa/cppunit/text.cxx
+++ b/vcl/qa/cppunit/text.cxx
@@ -692,7 +692,7 @@ void 
VclTextTest::testImplLayoutArgs_PrepareFallback_precalculatedglyphs()
 
     const OUString sTestString = "The quick\n jumped over";
     std::unique_ptr<SalLayout> pLayout
-        = pVirDev->ImplLayout(sTestString, 0, sTestString.getLength(), 
Point(0, 0), 0, nullptr,
+        = pVirDev->ImplLayout(sTestString, 0, sTestString.getLength(), 
Point(0, 0), 0, {},
                               SalLayoutFlags::GlyphItemsOnly);
     SalLayoutGlyphs aGlyphs = pLayout->GetGlyphs();
     SalLayoutGlyphsImpl* pGlyphsImpl = aGlyphs.Impl(1);
diff --git a/vcl/source/control/calendar.cxx b/vcl/source/control/calendar.cxx
index 4beea72b5e83..2d5910a920f0 100644
--- a/vcl/source/control/calendar.cxx
+++ b/vcl/source/control/calendar.cxx
@@ -704,7 +704,10 @@ void Calendar::ImplDraw(vcl::RenderContext& rRenderContext)
             rRenderContext.SetLineColor(rStyleSettings.GetWindowTextColor());
             Point aStartPos(nDayX, nDeltaY);
             rRenderContext.DrawLine(aStartPos, Point(nDayX + (7 * mnDayWidth), 
nDeltaY));
-            rRenderContext.DrawTextArray(Point(nDayX + mnDayOfWeekAry[0], 
nDayY), maDayOfWeekText, &(mnDayOfWeekAry[1]));
+            std::vector<tools::Long> aTmp;
+            for (int k=0; k<6; ++k)
+                aTmp.push_back(mnDayOfWeekAry[k+1]);
+            rRenderContext.DrawTextArray(Point(nDayX + mnDayOfWeekAry[0], 
nDayY), maDayOfWeekText, {aTmp.data(), aTmp.size()});
 
             // display days
             sal_uInt16 nDaysInMonth = aDate.GetDaysInMonth();
diff --git a/vcl/source/control/imp_listbox.cxx 
b/vcl/source/control/imp_listbox.cxx
index b613a533fb44..2d405e542775 100644
--- a/vcl/source/control/imp_listbox.cxx
+++ b/vcl/source/control/imp_listbox.cxx
@@ -589,7 +589,7 @@ SalLayoutGlyphs* ImplEntryType::GetTextGlyphs(const 
OutputDevice* pOutputDevice)
         return &maStrGlyphs;
 
     std::unique_ptr<SalLayout> pLayout = pOutputDevice->ImplLayout(
-        maStr, 0, maStr.getLength(), Point(0, 0), 0, nullptr, 
SalLayoutFlags::GlyphItemsOnly);
+        maStr, 0, maStr.getLength(), Point(0, 0), 0, {}, 
SalLayoutFlags::GlyphItemsOnly);
     if (!pLayout)
         return nullptr;
 
diff --git a/vcl/source/filter/eps/eps.cxx b/vcl/source/filter/eps/eps.cxx
index 74a746154397..6da05bb24fb7 100644
--- a/vcl/source/filter/eps/eps.cxx
+++ b/vcl/source/filter/eps/eps.cxx
@@ -200,10 +200,10 @@ private:
 
     void                ImplSetClipRegion( vcl::Region const & rRegion );
     void                ImplBmp( Bitmap const *, Bitmap const *, const Point 
&, double nWidth, double nHeight );
-    void                ImplText( const OUString& rUniString, const Point& 
rPos, const tools::Long* pDXArry, sal_Int32 nWidth, VirtualDevice const & rVDev 
);
+    void                ImplText( const OUString& rUniString, const Point& 
rPos, o3tl::span<const tools::Long> pDXArry, sal_Int32 nWidth, VirtualDevice 
const & rVDev );
     void                ImplSetAttrForText( const Point & rPoint );
     void                ImplWriteCharacter( char );
-    void                ImplWriteString( const OString&, VirtualDevice const & 
rVDev, const tools::Long* pDXArry, bool bStretch );
+    void                ImplWriteString( const OString&, VirtualDevice const & 
rVDev, o3tl::span<const tools::Long> pDXArry, bool bStretch );
     void                ImplDefineFont( const char*, const char* );
 
     void                ImplClosePathDraw();
@@ -742,7 +742,7 @@ void PSWriter::ImplWriteActions( const GDIMetaFile& rMtf, 
VirtualDevice& rVDev )
                 OUString  aUniStr = pA->GetText().copy( pA->GetIndex(), 
pA->GetLen() );
                 Point     aPoint( pA->GetPoint() );
 
-                ImplText( aUniStr, aPoint, nullptr, 0, rVDev );
+                ImplText( aUniStr, aPoint, {}, 0, rVDev );
             }
             break;
 
@@ -758,7 +758,7 @@ void PSWriter::ImplWriteActions( const GDIMetaFile& rMtf, 
VirtualDevice& rVDev )
                 OUString  aUniStr = pA->GetText().copy( pA->GetIndex(), 
pA->GetLen() );
                 Point     aPoint( pA->GetPoint() );
 
-                ImplText( aUniStr, aPoint, nullptr, pA->GetWidth(), rVDev );
+                ImplText( aUniStr, aPoint, {}, pA->GetWidth(), rVDev );
             }
             break;
 
@@ -768,7 +768,7 @@ void PSWriter::ImplWriteActions( const GDIMetaFile& rMtf, 
VirtualDevice& rVDev )
                 OUString  aUniStr = pA->GetText().copy( pA->GetIndex(), 
pA->GetLen() );
                 Point     aPoint( pA->GetPoint() );
 
-                ImplText( aUniStr, aPoint, pA->GetDXArray(), 0, rVDev );
+                ImplText( aUniStr, aPoint, { pA->GetDXArray().data(), 
pA->GetDXArray().size() }, 0, rVDev );
             }
             break;
 
@@ -1951,13 +1951,13 @@ void PSWriter::ImplWriteCharacter( char nChar )
     ImplWriteByte( static_cast<sal_uInt8>(nChar), PS_NONE );
 }
 
-void PSWriter::ImplWriteString( const OString& rString, VirtualDevice const & 
rVDev, const tools::Long* pDXArry, bool bStretch )
+void PSWriter::ImplWriteString( const OString& rString, VirtualDevice const & 
rVDev, o3tl::span<const tools::Long> pDXArry, bool bStretch )
 {
     sal_Int32 nLen = rString.getLength();
     if ( !nLen )
         return;
 
-    if ( pDXArry )
+    if ( !pDXArry.empty() )
     {
         double nx = 0;
 
@@ -1981,7 +1981,7 @@ void PSWriter::ImplWriteString( const OString& rString, 
VirtualDevice const & rV
     }
 }
 
-void PSWriter::ImplText( const OUString& rUniString, const Point& rPos, const 
tools::Long* pDXArry, sal_Int32 nWidth, VirtualDevice const & rVDev )
+void PSWriter::ImplText( const OUString& rUniString, const Point& rPos, 
o3tl::span<const tools::Long> pDXArry, sal_Int32 nWidth, VirtualDevice const & 
rVDev )
 {
     if ( rUniString.isEmpty() )
         return;
@@ -2029,7 +2029,7 @@ void PSWriter::ImplText( const OUString& rUniString, 
const Point& rPos, const to
     else if ( ( mnTextMode == 1 ) || ( mnTextMode == 2 ) )  // normal text 
output
     {
         if ( mnTextMode == 2 )  // forcing output one complete text packet, by
-            pDXArry = nullptr;     // ignoring the kerning array
+            pDXArry = {};     // ignoring the kerning array
         ImplSetAttrForText( rPos );
         OString aStr(OUStringToOString(rUniString,
             maFont.GetCharSet()));
diff --git a/vcl/source/filter/svm/SvmConverter.cxx 
b/vcl/source/filter/svm/SvmConverter.cxx
index 40ed636dd011..71c400fb37f3 100644
--- a/vcl/source/filter/svm/SvmConverter.cxx
+++ b/vcl/source/filter/svm/SvmConverter.cxx
@@ -715,7 +715,7 @@ void SVMConverter::ImplConvertFromSVM1( SvStream& rIStm, 
GDIMetaFile& rMtf )
 
                     OUString aStr(OStringToOUString(aByteStr, eActualCharSet));
 
-                    std::unique_ptr<tools::Long[]> pDXAry;
+                    std::vector<tools::Long> aDXAry;
                     if (nAryLen > 0)
                     {
                         const size_t nMinRecordSize = sizeof(sal_Int32);
@@ -742,12 +742,12 @@ void SVMConverter::ImplConvertFromSVM1( SvStream& rIStm, 
GDIMetaFile& rMtf )
                         }
                         else
                         {
-                            pDXAry.reset(new tools::Long[nDXAryLen]);
+                            aDXAry.resize(nDXAryLen);
 
                             for (sal_Int32 j = 0; j < nAryLen; ++j)
                             {
                                 rIStm.ReadInt32( nTmp );
-                                pDXAry[ j ] = nTmp;
+                                aDXAry[ j ] = nTmp;
                             }
 
                             // #106172# Add last DX array elem, if missing
@@ -767,9 +767,9 @@ void SVMConverter::ImplConvertFromSVM1( SvStream& rIStm, 
GDIMetaFile& rMtf )
                                     // difference to last elem and store
                                     // in very last.
                                     if( nStrLen > 1 )
-                                        pDXAry[ nStrLen-1 ] = pDXAry[ 
nStrLen-2 ] + aTmpAry[ nStrLen-1 ] - aTmpAry[ nStrLen-2 ];
+                                        aDXAry[ nStrLen-1 ] = aDXAry[ 
nStrLen-2 ] + aTmpAry[ nStrLen-1 ] - aTmpAry[ nStrLen-2 ];
                                     else
-                                        pDXAry[ nStrLen-1 ] = aTmpAry[ 
nStrLen-1 ]; // len=1: 0th position taken to be 0
+                                        aDXAry[ nStrLen-1 ] = aTmpAry[ 
nStrLen-1 ]; // len=1: 0th position taken to be 0
                                 }
 #ifdef DBG_UTIL
                                 else
@@ -780,7 +780,7 @@ void SVMConverter::ImplConvertFromSVM1( SvStream& rIStm, 
GDIMetaFile& rMtf )
                     }
                     if ( nUnicodeCommentActionNumber == i )
                         ImplReadUnicodeComment( nUnicodeCommentStreamPos, 
rIStm, aStr );
-                    rMtf.AddAction( new MetaTextArrayAction( aPt, aStr, 
pDXAry.get(), nIndex, nLen ) );
+                    rMtf.AddAction( new MetaTextArrayAction( aPt, aStr, 
aDXAry, nIndex, nLen ) );
                 }
 
                 if (nActionSize < 24)
diff --git a/vcl/source/filter/svm/SvmReader.cxx 
b/vcl/source/filter/svm/SvmReader.cxx
index 31636fa23362..0f6c19ed0a31 100644
--- a/vcl/source/filter/svm/SvmReader.cxx
+++ b/vcl/source/filter/svm/SvmReader.cxx
@@ -683,7 +683,7 @@ rtl::Reference<MetaAction> 
SvmReader::TextArrayHandler(const ImplMetaReadData* p
 {
     rtl::Reference<MetaTextArrayAction> pAction(new MetaTextArrayAction);
 
-    std::unique_ptr<tools::Long[]> aArray;
+    std::vector<tools::Long> aArray;
 
     VersionCompatRead aCompat(mrStream);
     TypeSerializer aSerializer(mrStream);
@@ -720,9 +720,9 @@ rtl::Reference<MetaAction> 
SvmReader::TextArrayHandler(const ImplMetaReadData* p
         // #i9762#, #106172# Ensure that DX array is at least mnLen entries 
long
         if (nTmpLen >= nAryLen)
         {
-            aArray.reset(new (std::nothrow) tools::Long[nTmpLen]);
-            if (aArray)
+            try
             {
+                aArray.resize(nTmpLen);
                 sal_Int32 i;
                 sal_Int32 val(0);
                 for (i = 0; i < nAryLen; i++)
@@ -734,6 +734,9 @@ rtl::Reference<MetaAction> 
SvmReader::TextArrayHandler(const ImplMetaReadData* p
                 for (; i < nTmpLen; i++)
                     aArray[i] = 0;
             }
+            catch (std::bad_alloc&)
+            {
+            }
         }
         else
         {
@@ -751,11 +754,12 @@ rtl::Reference<MetaAction> 
SvmReader::TextArrayHandler(const ImplMetaReadData* p
             SAL_WARN("vcl.gdi", "inconsistent offset and len");
             pAction->SetIndex(0);
             pAction->SetLen(aStr.getLength());
-            aArray.reset();
+            aArray.clear();
         }
     }
 
-    pAction->SetDXArray(std::move(aArray));
+    if (!aArray.empty())
+        pAction->SetDXArray(std::move(aArray));
     return pAction;
 }
 
diff --git a/vcl/source/filter/svm/SvmWriter.cxx 
b/vcl/source/filter/svm/SvmWriter.cxx
index f18fc7d624a4..bcc15c5806e4 100644
--- a/vcl/source/filter/svm/SvmWriter.cxx
+++ b/vcl/source/filter/svm/SvmWriter.cxx
@@ -984,9 +984,9 @@ void SvmWriter::TextArrayHandler(const MetaTextArrayAction* 
pAction, const ImplM
 {
     mrStream.WriteUInt16(static_cast<sal_uInt16>(pAction->GetType()));
 
-    tools::Long* aArray = pAction->GetDXArray();
+    const std::vector<tools::Long>& rDXArray = pAction->GetDXArray();
 
-    const sal_Int32 nAryLen = aArray ? pAction->GetLen() : 0;
+    const sal_Int32 nAryLen = !rDXArray.empty() ? pAction->GetLen() : 0;
 
     VersionCompatWrite aCompat(mrStream, 2);
     TypeSerializer aSerializer(mrStream);
@@ -997,7 +997,7 @@ void SvmWriter::TextArrayHandler(const MetaTextArrayAction* 
pAction, const ImplM
     mrStream.WriteInt32(nAryLen);
 
     for (sal_Int32 i = 0; i < nAryLen; ++i)
-        mrStream.WriteInt32(aArray[i]);
+        mrStream.WriteInt32(rDXArray[i]);
 
     write_uInt16_lenPrefixed_uInt16s_FromOUString(mrStream, 
pAction->GetText()); // version 2
 }
diff --git a/vcl/source/filter/wmf/emfwr.cxx b/vcl/source/filter/wmf/emfwr.cxx
index 33d41da4ad0d..d9f41fd81fed 100644
--- a/vcl/source/filter/wmf/emfwr.cxx
+++ b/vcl/source/filter/wmf/emfwr.cxx
@@ -861,7 +861,7 @@ void EMFWriter::ImplWriteBmpRecord( const Bitmap& rBmp, 
const Point& rPt,
 
 }
 
-void EMFWriter::ImplWriteTextRecord( const Point& rPos, const OUString& rText, 
const tools::Long* pDXArray, sal_uInt32 nWidth )
+void EMFWriter::ImplWriteTextRecord( const Point& rPos, const OUString& rText, 
o3tl::span<const tools::Long> pDXArray, sal_uInt32 nWidth )
 {
     sal_Int32 nLen = rText.getLength(), i;
 
@@ -870,18 +870,18 @@ void EMFWriter::ImplWriteTextRecord( const Point& rPos, 
const OUString& rText, c
 
     sal_uInt32  nNormWidth;
     std::vector<tools::Long> aOwnArray;
-    tools::Long*  pDX;
+    o3tl::span<const tools::Long> pDX;
 
     // get text sizes
-    if( pDXArray )
+    if( !pDXArray.empty() )
     {
         nNormWidth = maVDev->GetTextWidth( rText );
-        pDX = const_cast<tools::Long*>(pDXArray);
+        pDX = pDXArray;
     }
     else
     {
         nNormWidth = maVDev->GetTextArray( rText, &aOwnArray );
-        pDX = aOwnArray.data();
+        pDX = { aOwnArray.data(), aOwnArray.size() };
     }
 
     if( nLen > 1 )
@@ -890,10 +890,15 @@ void EMFWriter::ImplWriteTextRecord( const Point& rPos, 
const OUString& rText, c
 
         if( nWidth && nNormWidth && ( nWidth != nNormWidth ) )
         {
+            if (!pDXArray.empty())
+            {
+                aOwnArray.insert(aOwnArray.begin(), pDXArray.begin(), 
pDXArray.end());
+                pDX = { aOwnArray.data(), aOwnArray.size() };
+            }
             const double fFactor = static_cast<double>(nWidth) / nNormWidth;
 
             for( i = 0; i < ( nLen - 1 ); i++ )
-                pDX[ i ] = FRound( pDX[ i ] * fFactor );
+                aOwnArray[ i ] = FRound( aOwnArray[ i ] * fFactor );
         }
     }
 
@@ -1346,7 +1351,7 @@ void EMFWriter::ImplWrite( const GDIMetaFile& rMtf )
                 const OUString          aText = pA->GetText().copy( 
pA->GetIndex(), std::min(pA->GetText().getLength() - pA->GetIndex(), 
pA->GetLen()) );
 
                 ImplCheckTextAttr();
-                ImplWriteTextRecord( pA->GetPoint(), aText, nullptr, 0 );
+                ImplWriteTextRecord( pA->GetPoint(), aText, {}, 0 );
             }
             break;
 
@@ -1356,7 +1361,7 @@ void EMFWriter::ImplWrite( const GDIMetaFile& rMtf )
                 const OUString&             aText( pA->GetText() );
 
                 ImplCheckTextAttr();
-                ImplWriteTextRecord( pA->GetRect().TopLeft(), aText, nullptr, 
0 );
+                ImplWriteTextRecord( pA->GetRect().TopLeft(), aText, {}, 0 );
             }
             break;
 
@@ -1366,7 +1371,7 @@ void EMFWriter::ImplWrite( const GDIMetaFile& rMtf )
                 const OUString              aText = pA->GetText().copy( 
pA->GetIndex(), std::min(pA->GetText().getLength() - pA->GetIndex(), 
pA->GetLen()) );
 
                 ImplCheckTextAttr();
-                ImplWriteTextRecord( pA->GetPoint(), aText, pA->GetDXArray(), 
0 );
+                ImplWriteTextRecord( pA->GetPoint(), aText, { 
pA->GetDXArray().data(), pA->GetDXArray().size() }, 0 );
             }
             break;
 
@@ -1376,7 +1381,7 @@ void EMFWriter::ImplWrite( const GDIMetaFile& rMtf )
                 const OUString                  aText = pA->GetText().copy( 
pA->GetIndex(), std::min(pA->GetText().getLength() - pA->GetIndex(), 
pA->GetLen()) );
 
                 ImplCheckTextAttr();
-                ImplWriteTextRecord( pA->GetPoint(), aText, nullptr, 
pA->GetWidth() );
+                ImplWriteTextRecord( pA->GetPoint(), aText, {}, pA->GetWidth() 
);
             }
             break;
 
diff --git a/vcl/source/filter/wmf/emfwr.hxx b/vcl/source/filter/wmf/emfwr.hxx
index 31149b976db1..d2d3d9845931 100644
--- a/vcl/source/filter/wmf/emfwr.hxx
+++ b/vcl/source/filter/wmf/emfwr.hxx
@@ -75,7 +75,7 @@ private:
     void                ImplWritePolygonRecord( const tools::Polygon& rPoly, 
bool bClose );
     void                ImplWritePolyPolygonRecord( const tools::PolyPolygon& 
rPolyPoly );
     void                ImplWriteBmpRecord( const Bitmap& rBmp, const Point& 
rPt, const Size& rSz, sal_uInt32 nROP );
-    void                ImplWriteTextRecord( const Point& rPos, const 
OUString& rText, const tools::Long* pDXArray, sal_uInt32 nWidth );
+    void                ImplWriteTextRecord( const Point& rPos, const 
OUString& rText, o3tl::span<const tools::Long> pDXArray, sal_uInt32 nWidth );
 
     void                Impl_handleLineInfoPolyPolygons(const LineInfo& rInfo, 
const basegfx::B2DPolygon& rLinePolygon);
     void                ImplWrite( const GDIMetaFile& rMtf );
diff --git a/vcl/source/filter/wmf/wmfwr.cxx b/vcl/source/filter/wmf/wmfwr.cxx
index 93bc6e29ee07..b58a25408523 100644
--- a/vcl/source/filter/wmf/wmfwr.cxx
+++ b/vcl/source/filter/wmf/wmfwr.cxx
@@ -442,7 +442,7 @@ void WMFWriter::WMFRecord_Escape( sal_uInt32 nEsc, 
sal_uInt32 nLen, const sal_In
 /* if return value is true, then a complete unicode string and also a polygon 
replacement has been written,
     so there is no more action necessary
 */
-bool WMFWriter::WMFRecord_Escape_Unicode( const Point& rPoint, const OUString& 
rUniStr, const tools::Long* pDXAry )
+bool WMFWriter::WMFRecord_Escape_Unicode( const Point& rPoint, const OUString& 
rUniStr, o3tl::span<const tools::Long> pDXAry )
 {
     bool bEscapeUsed = false;
 
@@ -509,7 +509,7 @@ bool WMFWriter::WMFRecord_Escape_Unicode( const Point& 
rPoint, const OUString& r
                 std::vector<tools::PolyPolygon> aPolyPolyVec;
                 if ( pVirDev->GetTextOutlines( aPolyPolyVec, rUniStr ) )
                 {
-                    sal_uInt32 nDXCount = pDXAry ? nStringLen : 0;
+                    sal_uInt32 nDXCount = !pDXAry.empty() ? nStringLen : 0;
                     sal_uInt32 nSkipActions = aPolyPolyVec.size();
                     sal_Int32 nStrmLen = 8 +
                                            + sizeof( nStringLen ) + ( 
nStringLen * 2 )
@@ -547,11 +547,11 @@ bool WMFWriter::WMFRecord_Escape_Unicode( const Point& 
rPoint, const OUString& r
 
 void WMFWriter::WMFRecord_ExtTextOut( const Point& rPoint,
                                       const OUString& rString,
-                                      const tools::Long* pDXAry )
+                                      o3tl::span<const tools::Long> pDXAry )
 {
     sal_Int32 nOriginalTextLen = rString.getLength();
 
-    if ( (nOriginalTextLen <= 1) || (pDXAry == nullptr) )
+    if ( (nOriginalTextLen <= 1) || pDXAry.empty() )
     {
         WMFRecord_TextOut(rPoint, rString);
         return;
@@ -562,7 +562,7 @@ void WMFWriter::WMFRecord_ExtTextOut( const Point& rPoint,
 }
 
 void WMFWriter::TrueExtTextOut( const Point& rPoint, const OUString& rString,
-                                const OString& rByteString, const tools::Long* 
pDXAry )
+                                const OString& rByteString, o3tl::span<const 
tools::Long> pDXAry )
 {
     WriteRecordHeader( 0, W_META_EXTTEXTOUT );
     WritePointYX( rPoint );
@@ -1162,7 +1162,7 @@ void WMFWriter::WriteRecords( const GDIMetaFile & rMTF )
                 SetAllAttr();
 
                 Point aPos( pA->GetRect().TopLeft() );
-                if ( !WMFRecord_Escape_Unicode( aPos, aTemp, nullptr ) )
+                if ( !WMFRecord_Escape_Unicode( aPos, aTemp, {} ) )
                     WMFRecord_TextOut( aPos, aTemp );
             }
             break;
@@ -1173,7 +1173,7 @@ void WMFWriter::WriteRecords( const GDIMetaFile & rMTF )
                 OUString aTemp = pA->GetText().copy( pA->GetIndex(), 
std::min<sal_Int32>(pA->GetText().getLength() - pA->GetIndex(), pA->GetLen()) );
                 aSrcLineInfo = LineInfo();
                 SetAllAttr();
-                if ( !WMFRecord_Escape_Unicode( pA->GetPoint(), aTemp, nullptr 
) )
+                if ( !WMFRecord_Escape_Unicode( pA->GetPoint(), aTemp, {} ) )
                     WMFRecord_TextOut( pA->GetPoint(), aTemp );
             }
             break;
@@ -1185,8 +1185,8 @@ void WMFWriter::WriteRecords( const GDIMetaFile & rMTF )
                 OUString aTemp = pA->GetText().copy( pA->GetIndex(), 
std::min<sal_Int32>(pA->GetText().getLength() - pA->GetIndex(), pA->GetLen()) );
                 aSrcLineInfo = LineInfo();
                 SetAllAttr();
-                if ( !WMFRecord_Escape_Unicode( pA->GetPoint(), aTemp, 
pA->GetDXArray() ) )
-                    WMFRecord_ExtTextOut( pA->GetPoint(), aTemp, 
pA->GetDXArray() );
+                if ( !WMFRecord_Escape_Unicode( pA->GetPoint(), aTemp, { 
pA->GetDXArray().data(), pA->GetDXArray().size() } ) )
+                    WMFRecord_ExtTextOut( pA->GetPoint(), aTemp, { 
pA->GetDXArray().data(), pA->GetDXArray().size() } );
             }
             break;
 
@@ -1211,8 +1211,8 @@ void WMFWriter::WriteRecords( const GDIMetaFile & rMTF )
                         aDXAry.clear();
                     aSrcLineInfo = LineInfo();
                     SetAllAttr();
-                    if ( !WMFRecord_Escape_Unicode( pA->GetPoint(), aTemp, 
aDXAry.empty() ? nullptr : aDXAry.data() ) )
-                        WMFRecord_ExtTextOut( pA->GetPoint(), aTemp, 
aDXAry.empty() ? nullptr : aDXAry.data() );
+                    if ( !WMFRecord_Escape_Unicode( pA->GetPoint(), aTemp, { 
aDXAry.data(), aDXAry.size() } ) )
+                        WMFRecord_ExtTextOut( pA->GetPoint(), aTemp, { 
aDXAry.data(), aDXAry.size() } );
                 }
             }
             break;
diff --git a/vcl/source/filter/wmf/wmfwr.hxx b/vcl/source/filter/wmf/wmfwr.hxx
index 7be7e0bb3e7e..a0961e63a15c 100644
--- a/vcl/source/filter/wmf/wmfwr.hxx
+++ b/vcl/source/filter/wmf/wmfwr.hxx
@@ -142,11 +142,11 @@ private:
     void WMFRecord_DeleteObject(sal_uInt16 nObjectHandle);
     void WMFRecord_Ellipse(const tools::Rectangle& rRect);
     void WMFRecord_Escape( sal_uInt32 nEsc, sal_uInt32 nLen, const sal_Int8* 
pData );
-    bool WMFRecord_Escape_Unicode( const Point& rPoint, const OUString& rStr, 
const tools::Long* pDXAry );
-    void WMFRecord_ExtTextOut(const Point& rPoint, const OUString& rString, 
const tools::Long* pDXAry);
+    bool WMFRecord_Escape_Unicode( const Point& rPoint, const OUString& rStr, 
o3tl::span<const tools::Long> pDXAry );
+    void WMFRecord_ExtTextOut(const Point& rPoint, const OUString& rString, 
o3tl::span<const tools::Long> pDXAry);
 
     void TrueExtTextOut(const Point& rPoint, const OUString& rString,
-                        const OString& rByteString, const tools::Long* pDXAry);
+                        const OString& rByteString, o3tl::span<const 
tools::Long> pDXAry);
     void TrueTextOut(const Point& rPoint, const OString& rString);
     void WMFRecord_LineTo(const Point & rPoint);
     void WMFRecord_MoveTo(const Point & rPoint);
diff --git a/vcl/source/gdi/gdimtf.cxx b/vcl/source/gdi/gdimtf.cxx
index 39fe64c33050..28cd535a1eb6 100644
--- a/vcl/source/gdi/gdimtf.cxx
+++ b/vcl/source/gdi/gdimtf.cxx
@@ -1463,7 +1463,7 @@ tools::Rectangle GDIMetaFile::GetBoundRect( OutputDevice& 
i_rReference, tools::R
             tools::Rectangle aRect;
             // hdu said base = index
             aMapVDev->GetTextBoundRect( aRect, pAct->GetText(), 
pAct->GetIndex(), pAct->GetIndex(), pAct->GetLen(),
-                                       0, pAct->GetDXArray() );
+                                       0, { pAct->GetDXArray().data(), 
pAct->GetDXArray().size() } );
             Point aPt( pAct->GetPoint() );
             aRect.Move( aPt.X(), aPt.Y() );
             ImplActionBounds( aBound, OutputDevice::LogicToLogic( aRect, 
aMapVDev->GetMapMode(), GetPrefMapMode() ), aClipStack, nullptr );
@@ -2257,7 +2257,7 @@ sal_uLong GDIMetaFile::GetSizeBytes() const
 
                 nSizeBytes += ( pTextArrayAction->GetText().getLength() * 
sizeof( sal_Unicode ) );
 

... etc. - the rest is truncated

Reply via email to