aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorFriedemann Kleint <Friedemann.Kleint@qt.io>2022-12-21 16:01:59 +0100
committerFriedemann Kleint <Friedemann.Kleint@qt.io>2023-03-07 13:10:10 +0100
commit504cf3341c0622c16d4283eef58aed9fe9c35036 (patch)
tree4b09fad4d74021319dab2adb71e11ab30996d9a8
parent21fbc5ec9a973a80199134db77708b7bc48a0707 (diff)
shiboken6: Add support for std::span
Convert std::span to a Python list. For the conversion from Python to C++, make it a view on a vector. A special type is introduced since a different implementation is needed for opaque containers. Task-number: PYSIDE-2174 Change-Id: I17a7385282a7d373dc73d5ac63a5d3363d61d130 Reviewed-by: Cristian Maureira-Fredes <cristian.maureira-fredes@qt.io> Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
-rw-r--r--sources/shiboken6/ApiExtractor/containertypeentry.h1
-rw-r--r--sources/shiboken6/ApiExtractor/typedatabase.cpp10
-rw-r--r--sources/shiboken6/ApiExtractor/typesystem.cpp1
-rw-r--r--sources/shiboken6/ApiExtractor/typesystemparser.cpp3
-rw-r--r--sources/shiboken6/doc/typesystem_builtin_types.rst13
-rw-r--r--sources/shiboken6/doc/typesystem_converters.rst10
-rw-r--r--sources/shiboken6/generator/shiboken/cppgenerator.cpp1
-rw-r--r--sources/shiboken6/generator/shiboken/shibokengenerator.cpp1
-rw-r--r--sources/shiboken6/tests/libminimal/CMakeLists.txt1
-rw-r--r--sources/shiboken6/tests/libminimal/spanuser.cpp41
-rw-r--r--sources/shiboken6/tests/libminimal/spanuser.h31
-rw-r--r--sources/shiboken6/tests/minimalbinding/CMakeLists.txt1
-rw-r--r--sources/shiboken6/tests/minimalbinding/global.h1
-rw-r--r--sources/shiboken6/tests/minimalbinding/spanuser_test.py31
-rw-r--r--sources/shiboken6/tests/minimalbinding/typesystem_minimal.xml2
15 files changed, 136 insertions, 12 deletions
diff --git a/sources/shiboken6/ApiExtractor/containertypeentry.h b/sources/shiboken6/ApiExtractor/containertypeentry.h
index 0f1e03054..b2003816b 100644
--- a/sources/shiboken6/ApiExtractor/containertypeentry.h
+++ b/sources/shiboken6/ApiExtractor/containertypeentry.h
@@ -29,6 +29,7 @@ public:
MapContainer,
MultiMapContainer,
PairContainer,
+ SpanContainer, // Fixed size
};
explicit ContainerTypeEntry(const QString &entryName, ContainerKind containerKind,
diff --git a/sources/shiboken6/ApiExtractor/typedatabase.cpp b/sources/shiboken6/ApiExtractor/typedatabase.cpp
index 240ad0df8..8f232aee1 100644
--- a/sources/shiboken6/ApiExtractor/typedatabase.cpp
+++ b/sources/shiboken6/ApiExtractor/typedatabase.cpp
@@ -862,6 +862,7 @@ void TypeDatabasePrivate::addBuiltInContainerTypes(const TypeDatabaseParserConte
const bool hasStdVector = findType(u"std::vector"_s) != nullptr;
const bool hasStdMap = findType(u"std::map"_s) != nullptr;
const bool hasStdUnorderedMap = findType(u"std::unordered_map"_s) != nullptr;
+ const bool hasStdSpan = findType(u"std::span"_s) != nullptr;
if (hasStdPair && hasStdList && hasStdVector && hasStdMap && hasStdUnorderedMap)
return;
@@ -906,6 +907,15 @@ void TypeDatabasePrivate::addBuiltInContainerTypes(const TypeDatabaseParserConte
"shiboken_conversion_stdmap_to_pydict",
"PyDict", "shiboken_conversion_pydict_to_stdmap");
}
+ if (!hasStdSpan) {
+ auto spanSnip = containerTypeSystemSnippet(
+ "std::span", "span", "span",
+ "shiboken_conversion_cppsequence_to_pylist");
+ auto pos = spanSnip.indexOf('>');
+ spanSnip.insert(pos, R"( view-on="std::vector")");
+ ts += spanSnip;
+ }
+
ts += "</typesystem>";
QBuffer buffer(&ts);
buffer.open(QIODevice::ReadOnly);
diff --git a/sources/shiboken6/ApiExtractor/typesystem.cpp b/sources/shiboken6/ApiExtractor/typesystem.cpp
index 541c84484..6a0870914 100644
--- a/sources/shiboken6/ApiExtractor/typesystem.cpp
+++ b/sources/shiboken6/ApiExtractor/typesystem.cpp
@@ -1884,6 +1884,7 @@ qsizetype ContainerTypeEntry::templateParameterCount() const
case MapContainer:
case MultiMapContainer:
case PairContainer:
+ case SpanContainer:
result = 2;
break;
case ListContainer:
diff --git a/sources/shiboken6/ApiExtractor/typesystemparser.cpp b/sources/shiboken6/ApiExtractor/typesystemparser.cpp
index 26b9fc94a..632bb4451 100644
--- a/sources/shiboken6/ApiExtractor/typesystemparser.cpp
+++ b/sources/shiboken6/ApiExtractor/typesystemparser.cpp
@@ -375,7 +375,8 @@ ENUM_LOOKUP_BEGIN(ContainerTypeEntry::ContainerKind, Qt::CaseSensitive,
{u"multi-map", ContainerTypeEntry::MultiMapContainer},
{u"hash", ContainerTypeEntry::MapContainer},
{u"multi-hash", ContainerTypeEntry::MultiMapContainer},
- {u"pair", ContainerTypeEntry::PairContainer}
+ {u"pair", ContainerTypeEntry::PairContainer},
+ {u"span", ContainerTypeEntry::SpanContainer}
};
ENUM_LOOKUP_LINEAR_SEARCH()
diff --git a/sources/shiboken6/doc/typesystem_builtin_types.rst b/sources/shiboken6/doc/typesystem_builtin_types.rst
index 133396d8e..dea253930 100644
--- a/sources/shiboken6/doc/typesystem_builtin_types.rst
+++ b/sources/shiboken6/doc/typesystem_builtin_types.rst
@@ -32,12 +32,13 @@ on platform.
C++ Container Types
^^^^^^^^^^^^^^^^^^^
-Since version 6.3, some common standard containers (``std::list``,
-``std::vector``, ``std::pair``, ``std::map`` and ``std::unordered_map``)
-are built-in. They only need to be specified if :ref:`opaque-containers`
-should be generated. In this case, the appropriate
-:ref:`predefined conversion templates <predefined_templates>`
-should be specified.
+The C++ containers ``std::list``\, ``std::vector``\,
+``std::pair``\, ``std::map``\, ``std::span`` and ``std::unordered_map`` are
+built-in.
+To specify :ref:`opaque-containers`, use the :ref:`opaque-container` element.
+:ref:`container-type` can still be specified to modify the built-in behavior.
+For this case, a number of pre-defined conversion templates
+are provided (see :ref:`predefined_templates`).
.. _cpython-types:
diff --git a/sources/shiboken6/doc/typesystem_converters.rst b/sources/shiboken6/doc/typesystem_converters.rst
index 02600e7b1..1de39f020 100644
--- a/sources/shiboken6/doc/typesystem_converters.rst
+++ b/sources/shiboken6/doc/typesystem_converters.rst
@@ -175,11 +175,11 @@ defined (or automatically generated) for the containers.
</conversion-rule>
</container-type>
-.. note:: From version 6.3, we do not have to explicitly specify the
- `<container-type/>` for C++ containers ``std::list``\, ``std::vector``\,
- ``std::pair``\, ``std::map`` and ``std::unordered_map``\. They are
- now built-in. However, they still have to be added for opaque
- containers or when modifying the built-in behavior.
+.. note:: The C++ containers ``std::list``\, ``std::vector``\,
+ ``std::pair``\, ``std::map``\, ``std::span`` and ``std::unordered_map`` are
+ built-in.
+ To specify :ref:`opaque-containers`, use the :ref:`opaque-container` element.
+ :ref:`container-type` can still be specified to modify the built-in behavior.
For this case, a number of pre-defined conversion templates
are provided (see :ref:`predefined_templates`).
diff --git a/sources/shiboken6/generator/shiboken/cppgenerator.cpp b/sources/shiboken6/generator/shiboken/cppgenerator.cpp
index c26d06999..9f2d74093 100644
--- a/sources/shiboken6/generator/shiboken/cppgenerator.cpp
+++ b/sources/shiboken6/generator/shiboken/cppgenerator.cpp
@@ -1143,6 +1143,7 @@ QString CppGenerator::getVirtualFunctionReturnTypeName(const AbstractMetaFunctio
const auto cte = std::static_pointer_cast<const ContainerTypeEntry>(typeEntry);
switch (cte->containerKind()) {
case ContainerTypeEntry::ListContainer:
+ case ContainerTypeEntry::SpanContainer:
break;
case ContainerTypeEntry::SetContainer:
return uR"("set")"_s;
diff --git a/sources/shiboken6/generator/shiboken/shibokengenerator.cpp b/sources/shiboken6/generator/shiboken/shibokengenerator.cpp
index 55851e650..071fa1f66 100644
--- a/sources/shiboken6/generator/shiboken/shibokengenerator.cpp
+++ b/sources/shiboken6/generator/shiboken/shibokengenerator.cpp
@@ -576,6 +576,7 @@ QString ShibokenGenerator::containerCpythonBaseName(const ContainerTypeEntryCPtr
return u"PyDict"_s;
case ContainerTypeEntry::ListContainer:
case ContainerTypeEntry::PairContainer:
+ case ContainerTypeEntry::SpanContainer:
break;
default:
Q_ASSERT(false);
diff --git a/sources/shiboken6/tests/libminimal/CMakeLists.txt b/sources/shiboken6/tests/libminimal/CMakeLists.txt
index 8a5ad4fe2..4a10f96bf 100644
--- a/sources/shiboken6/tests/libminimal/CMakeLists.txt
+++ b/sources/shiboken6/tests/libminimal/CMakeLists.txt
@@ -9,6 +9,7 @@ libminimalmacros.h
listuser.cpp listuser.h
minbool.h
obj.cpp obj.h
+spanuser.cpp spanuser.h
typedef.cpp typedef.h
val.h
)
diff --git a/sources/shiboken6/tests/libminimal/spanuser.cpp b/sources/shiboken6/tests/libminimal/spanuser.cpp
new file mode 100644
index 000000000..1fcfe1e97
--- /dev/null
+++ b/sources/shiboken6/tests/libminimal/spanuser.cpp
@@ -0,0 +1,41 @@
+// Copyright (C) 2023 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only WITH Qt-GPL-exception-1.0
+
+#include "spanuser.h"
+
+#include <numeric>
+
+SpanUser::SpanUser() = default;
+
+bool SpanUser::enabled()
+{
+#if __cplusplus >= 202002L
+ return true;
+#else
+ return false;
+#endif
+}
+
+#if __cplusplus >= 202002L
+IntSpan3 SpanUser::getIntSpan3()
+{
+ static int iv[] = {1, 2, 3};
+ return IntSpan3(iv);
+}
+
+ConstIntSpan3 SpanUser::getConstIntSpan3()
+{
+ static const int civ[] = {1, 2, 3};
+ return ConstIntSpan3(civ);
+}
+
+int SpanUser::sumIntSpan3(IntSpan3 isp3)
+{
+ return std::accumulate(isp3.begin(), isp3.end(), 0);
+}
+
+int SpanUser::sumConstIntSpan3(ConstIntSpan3 ispc3)
+{
+ return std::accumulate(ispc3.begin(), ispc3.end(), 0);
+}
+#endif // C++ 20
diff --git a/sources/shiboken6/tests/libminimal/spanuser.h b/sources/shiboken6/tests/libminimal/spanuser.h
new file mode 100644
index 000000000..ad6a0f2df
--- /dev/null
+++ b/sources/shiboken6/tests/libminimal/spanuser.h
@@ -0,0 +1,31 @@
+// Copyright (C) 2023 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only WITH Qt-GPL-exception-1.0
+
+#ifndef SPANUSER_H
+#define SPANUSER_H
+
+#include "libminimalmacros.h"
+
+#if __cplusplus >= 202002L
+# include <span>
+
+using IntSpan3 = std::span<int, 3>;
+using ConstIntSpan3 = std::span<const int, 3>;
+#endif
+
+struct LIBMINIMAL_API SpanUser
+{
+ SpanUser();
+
+ static bool enabled();
+
+#if __cplusplus >= 202002L
+ static IntSpan3 getIntSpan3();
+ static ConstIntSpan3 getConstIntSpan3();
+
+ static int sumIntSpan3(IntSpan3 isp3);
+ static int sumConstIntSpan3(ConstIntSpan3 ispc3);
+#endif // C++ 20
+};
+
+#endif // SPANUSER_H
diff --git a/sources/shiboken6/tests/minimalbinding/CMakeLists.txt b/sources/shiboken6/tests/minimalbinding/CMakeLists.txt
index ffbf9f111..7f132bd34 100644
--- a/sources/shiboken6/tests/minimalbinding/CMakeLists.txt
+++ b/sources/shiboken6/tests/minimalbinding/CMakeLists.txt
@@ -13,6 +13,7 @@ ${CMAKE_CURRENT_BINARY_DIR}/minimal/containeruser_wrapper.cpp
${CMAKE_CURRENT_BINARY_DIR}/minimal/obj_wrapper.cpp
${CMAKE_CURRENT_BINARY_DIR}/minimal/val_wrapper.cpp
${CMAKE_CURRENT_BINARY_DIR}/minimal/listuser_wrapper.cpp
+${CMAKE_CURRENT_BINARY_DIR}/minimal/spanuser_wrapper.cpp
${CMAKE_CURRENT_BINARY_DIR}/minimal/minbooluser_wrapper.cpp
)
diff --git a/sources/shiboken6/tests/minimalbinding/global.h b/sources/shiboken6/tests/minimalbinding/global.h
index 4e792705a..fc5c59a26 100644
--- a/sources/shiboken6/tests/minimalbinding/global.h
+++ b/sources/shiboken6/tests/minimalbinding/global.h
@@ -6,4 +6,5 @@
#include "val.h"
#include "minbool.h"
#include "listuser.h"
+#include "spanuser.h"
#include "typedef.h"
diff --git a/sources/shiboken6/tests/minimalbinding/spanuser_test.py b/sources/shiboken6/tests/minimalbinding/spanuser_test.py
new file mode 100644
index 000000000..ee384eb81
--- /dev/null
+++ b/sources/shiboken6/tests/minimalbinding/spanuser_test.py
@@ -0,0 +1,31 @@
+#!/usr/bin/env python
+# Copyright (C) 2023 The Qt Company Ltd.
+# SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only WITH Qt-GPL-exception-1.0
+
+import os
+import sys
+import unittest
+
+from pathlib import Path
+sys.path.append(os.fspath(Path(__file__).resolve().parents[1]))
+from shiboken_paths import init_paths
+init_paths()
+
+from minimal import SpanUser
+
+
+class IntSpanTest(unittest.TestCase):
+
+ def testCreateIntSpan(self):
+ if not SpanUser.enabled():
+ return
+ expected = [1, 2, 3]
+ self.assertEqual(SpanUser.getIntSpan3(), expected)
+ self.assertEqual(SpanUser.getConstIntSpan3(), expected)
+
+ self.assertEqual(SpanUser.sumIntSpan3(expected), 6)
+ self.assertEqual(SpanUser.sumConstIntSpan3(expected), 6)
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/sources/shiboken6/tests/minimalbinding/typesystem_minimal.xml b/sources/shiboken6/tests/minimalbinding/typesystem_minimal.xml
index e73ddc228..ef317f415 100644
--- a/sources/shiboken6/tests/minimalbinding/typesystem_minimal.xml
+++ b/sources/shiboken6/tests/minimalbinding/typesystem_minimal.xml
@@ -38,6 +38,8 @@
</modify-argument>
</modify-function>
</value-type>
+ <value-type name="SpanUser"/>
+
<value-type name="MinBoolUser"/>
<value-type name="ContainerUser">