Commit graph

347 commits

Author SHA1 Message Date
Xaver Hugl
13d079cdd7 backends/x11: do less manual memory management 2022-06-21 17:50:49 +00:00
Xaver Hugl
e745577b4c backends: port vsync helpers to std::unique_ptr 2022-06-21 17:50:49 +00:00
Xaver Hugl
4cab9c4fc7 backends: port from QScopedPointer to std::unique_ptr 2022-06-21 17:50:49 +00:00
Aleix Pol
1112c29eb4 drm: Drop wrong assert
It blows out on nvidia proving my assumption was wrong back then
2022-06-21 14:16:46 +00:00
Aleix Pol
7b933abc0f backends/wayland: Don't rearrange outputs every time the window is resized
It makes it very hard to debug any use-case that isn't a strip of
outputs and even then, we should have other mechanisms to arrange
outputs properly (i.e. through kscreen).
2022-06-21 10:33:12 +00:00
Aleix Pol
5490b00117 backends/wayland: Allow outputs to have a name
As expected in many parts of our codebase
2022-06-21 10:33:12 +00:00
Aleix Pol i Gonzalez
5338d1a2b0 backends: We need to make current before calling importDmaBufAsTexture
Calls it for the WaylandBackend, ensures the declaration of the pointer
to the EglBackend in the drm case is done in the correct scope.
2022-06-18 20:00:32 +02:00
Xaver Hugl
1966638017 backends/drm: do cross-gpu imports again for test commits
Otherwise all commits will fail without a clear visible reason.

BUG: 454086
2022-06-17 17:45:18 +02:00
Marco Martin
32e6632d13 Make gbm_bo_create_with_modifiers2 inline
needed to link some tests

APPROVED-BY: vlad.zahorodnii@kde.org
2022-06-17 11:16:19 +02:00
Xaver Hugl
34ce3dde87 backends/drm: use GBM_BO_USE_SCANOUT when importing buffers for multi gpu
The gbm surface may not have the scanout use flag, and if the buffer is imported
without it, creating the framebuffer may fail

CCBUG: 454086
2022-06-16 17:02:16 +02:00
Aleix Pol
cd2567a838 drm & wayland: Remove unnecessary close() 2022-06-16 13:18:32 +00:00
Aleix Pol
1d5c803ce0 drm: Change where we call makeCurrent when creating dmabufs
We only need to call it before issuing opengl calls, so it's not
necessary when testing or when gbm fails to create the Buffer Object.
2022-06-16 13:18:32 +00:00
Aleix Pol
538b848f80 backends: Split out a DmaBufParams class
Instead of using a DmaBufAttributes instance to communicate the settings
to create a new dmabuf, use a smaller DmaBufParams class that only
contains the information we need after destroying the BO.
2022-06-16 13:18:32 +00:00
Aleix Pol
56ab74a143 backends: Share gbm create implementations between drm and wayland 2022-06-16 13:18:32 +00:00
Aleix Pol
aa59344be7 Platform: Improve our infrastructure to support dmabufs in backends
Allows creating buffers with modifiers.
Lets the windowed wayland backend support it, which makes testing
everything else much simpler.
2022-06-16 13:18:32 +00:00
Aleix Pol
29946be29f backends/wayland: Fix window title 2022-06-13 14:33:43 +02:00
Vlad Zahorodnii
9d916fa60d wayland: Use shared DmaBufAttributes type 2022-06-13 10:22:29 +00:00
Vlad Zahorodnii
2761df727d wayland: Refactor dmabuf attributes in linux-dmabuf-v1
At the moment, dmabuf importing is scattered all over the place in kwin.
It would be great if we had one function that takes dma-buf attributes
and returns an EGLImage if successful.

As the first step, make linux-dmabuf-v1 implementation provide dmabuf
attrs compatible with KWin::DmaBufAttributes.
2022-06-13 10:22:29 +00:00
l10n daemon script
ef1d97ac86 SVN_SILENT made messages (.desktop file) - always resolve ours
In case of conflict in i18n, keep the version of the branch "ours"
To resolve a particular conflict, "git checkout --ours path/to/file.desktop"
2022-06-13 02:35:40 +00:00
Aleix Pol i Gonzalez
5bea508590 drm: Readability, no need to copy the modifiers vector 2022-06-10 20:54:17 +02:00
Xaver Hugl
baf0f7b8d2 backends/drm: add fallback for systems without gbm modifier support
It was missing for lease outputs, which causes all atomic tests to fail

BUG: 454961
2022-06-09 14:31:15 +02:00
l10n daemon script
51999deadb SVN_SILENT made messages (.desktop file) - always resolve ours
In case of conflict in i18n, keep the version of the branch "ours"
To resolve a particular conflict, "git checkout --ours path/to/file.desktop"
2022-06-07 02:21:00 +00:00
Alexander Volkov
00379da3d3 Ignore fake input devices when detecting tablet mode
Otherwise launching firefox, which in turn leads to launching of
xdg-desktop-portal-kde, disables auto-rotation.
2022-06-06 17:25:37 +00:00
Xaver Hugl
4874066423 port many Qt shared pointers to standard smart pointers
There are a few benefits to using smart pointers from the standard library:
- std::unique_ptr has move semantics. With move semantics, transfer of ownership
can be properly expressed
- std::shared_ptr is more efficient than QSharedPointer
- more developers are used to them, making contributions for newcomers easier

We're also already using a mix of both; because Qt shared pointers provide
no benefits, porting to standard smart pointers improves consistency in
the code base. Because of that, this commit ports most of the uses of QSharedPointer
to std::shared_ptr, and some uses of QScopedPointer to std::unique_ptr
2022-06-04 16:57:29 +00:00
Aleix Pol
9db4fd1a17 DmaBufTexture: The modifier is a global dmabuf attribute
We don't get one per plane, but one per allocation.
2022-06-02 03:42:13 +02:00
Aleix Pol
51bfadab63 backends/wayland: Fix behaviour when disabling outputs
Makes sure disabled outputs are reported as such, leaving behind the
assumption that all outputs are always enabled.
Ensures the corresponding outputEnabled/Disabled signals are emitted.
Updates the window title to reflect the output state.
2022-06-01 10:53:03 +00:00
l10n daemon script
465aa7edee SVN_SILENT made messages (.desktop file) - always resolve ours
In case of conflict in i18n, keep the version of the branch "ours"
To resolve a particular conflict, "git checkout --ours path/to/file.desktop"
2022-06-01 01:57:49 +00:00
Xaver Hugl
e7365bf43f backends/drm: don't do direct scanout if transformations don't match
Part-of: <https://invent.kde.org/plasma/kwin/-/merge_requests/2128>
2022-05-31 07:10:08 +00:00
l10n daemon script
0a7ae31e4c SVN_SILENT made messages (.desktop file) - always resolve ours
In case of conflict in i18n, keep the version of the branch "ours"
To resolve a particular conflict, "git checkout --ours path/to/file.desktop"
2022-05-31 02:02:56 +00:00
Xaver Hugl
f86f159fd5 backends/drm: fall back to a software cursor if drmModeAddFB2 fails
CCBUG: 453860
2022-05-27 15:24:27 +00:00
Kai Uwe Broulik
b6001d12cc backends/x11/windowed: Don't create cursor pixmap from null image
There's no point and it results in a "QImage::scaled: Image is
a null image" warning.

Signed-off-by: Victoria Fischer <victoria.fischer@mbition.io>
Part-of: <https://invent.kde.org/plasma/kwin/-/merge_requests/2469>
2022-05-26 06:51:46 +00:00
Kai Uwe Broulik
b062d09fdc backends/x11: Support resizing the windowed output
In response to a XCB_CONFIGURE_NOTIFY on the output window, the new size
is set as mode and the output layer buffer is recreated.

Signed-off-by: Victoria Fischer <victoria.fischer@mbition.io>
Part-of: <https://invent.kde.org/plasma/kwin/-/merge_requests/2459>
2022-05-26 06:38:32 +00:00
Vlad Zahorodnii
e57be93108 backends/drm: Specify clear color for cursor plane
Otherwise the results are undefined.

BUG: 454068
Tested-by: Merge Service <https://invent.kde.org/plasma/kwin/-/merge_requests/2466>
Part-of: <https://invent.kde.org/plasma/kwin/-/merge_requests/2466>
2022-05-25 09:45:18 +00:00
Kai Uwe Broulik
d143f6e3c4 backends/x11: Arm vsync monitor in EglX11Backend
This was originally on `EglX11Backend::endFrame` and got lost
as part of refactoring in 7358daa9, breaking nested `kwin_wayland`
rendering with GL.

Signed-off-by: Victoria Fischer <victoria.fischer@mbition.io>
Tested-by: Merge Service <https://invent.kde.org/plasma/kwin/-/merge_requests/2458>
Part-of: <https://invent.kde.org/plasma/kwin/-/merge_requests/2458>
2022-05-24 14:44:59 +00:00
Kai Uwe Broulik
cfd3676e96 backends/x11: Restore dedicated XRenderUtils::init function
Under kwin_wayland `kwinApp()->connection()` is for communicating with
XWayland, but in X11Windowed backend we need to talk to the host XServer.

Restore `XRenderUtils::init` and set it accordingly based on
whether we're running standalone or windowed, so that `kwin_wayland`
works running nested in an X session again.

Signed-off-by: Victoria Fischer <victoria.fischer@mbition.io>
Tested-by: Merge Service <https://invent.kde.org/plasma/kwin/-/merge_requests/2457>
Part-of: <https://invent.kde.org/plasma/kwin/-/merge_requests/2457>
2022-05-24 11:45:52 +00:00
Vlad Zahorodnii
8b644fee58 backends/x11: Ensure that Output::geometryChanged is emitted when modes change
BUG: 453696
Tested-by: Merge Service <https://invent.kde.org/plasma/kwin/-/merge_requests/2454>
Part-of: <https://invent.kde.org/plasma/kwin/-/merge_requests/2454>
2022-05-24 09:51:44 +00:00
Kai Uwe Broulik
a2c91f9434 backends/x11: Cleanup KWinXRenderUtils and move it to eglx11common
The XRender backend has been removed, leaving most of KWinXRenderUtils unused.

The few features that are still used, notable `XRenderPicture` and pict format
are moved into the x11/common directory.

Signed-off-by: Victoria Fischer <victoria.fischer@mbition.io>
2022-05-19 12:10:18 +00:00
Xaver Hugl
0bbd4445f2 backends/drm: fix offset cursor
For some reason with legacy the cursor gets an offset when changing the
image. In order to work around this, directly issue a cursor move with the
corrected position when changing the buffer
2022-05-19 09:43:27 +00:00
David Redondo
d3a37aa9ae Update device outputName when setting output
BUG:451279
FIXED-IN:5.25.0
2022-05-18 12:50:24 +00:00
Xaver Hugl
b0b551653f backends/drm: update cursor after compositing reset
Otherwise the cursor won't be shown, as its buffer and layer got destroyed

BUG: 453823
2022-05-18 11:00:14 +00:00
Vlad Zahorodnii
00fb259c41 backends/drm: Fix cursor size check
Currently, the cursor size check ignores the cursor bitmap's size, so
the hardware cursor is used even though the bitmap size exceeds cursor
limits.
2022-05-16 12:09:27 +00:00
Vlad Zahorodnii
a601a08ba7 wayland: Make setting realtime scheduler more fine grained
With this only the main and the libinput threads will use realtime
scheduling, so it will be harder to leak realtime scheduling to somebody
else.

The only caveat is that kwin would need to keep CAP_SYS_NICE around,
however on the other hand, it's needed to ensure that kwin_wayland is
able to get high priority EGL contexts with some drivers, e.g. intel.
2022-05-16 11:15:20 +00:00
Kai Uwe Broulik
1878ba0e10 backends/drm: Guard gbm_bo_get_fd_for_plane in dmaBufAttributesForBo
It is guarded elsewhere but not here.

Signed-off-by: Victoria Fischer <victoria.fischer@mbition.io>
2022-05-16 10:48:58 +00:00
Kai Uwe Broulik
edf9698e23 backends/drm: Drop QObject and moc include from layer
There's no QObject anymore which causes a MOC warning

Signed-off-by: Victoria Fischer <victoria.fischer@mbition.io>
2022-05-16 10:49:50 +02:00
Vlad Zahorodnii
6451cb2cfe backends/drm: Also release cursor layer buffers 2022-05-15 08:31:39 +00:00
Vlad Zahorodnii
d7ec51998b backends/drm: Import gbm bos using dmabuf
It appears that importing gbm_bo's using eglCreateImageKHR() doesn't
work on nvidia.

Another issue is that Platform::createDmaBufTexture() uses
gbm_bo_create(). The nvidia driver doesn't like that, it's preferred to
use gbm_bo_create_with_modifiers().

In order to address those issues, this change refactors how gbm_bo
objects are imported and how gbm_bo's are allocated for dmabuf textures,
so the same code can be reused in EglGbmBackend::textureForOutput()
and Platform::createDmaBufTexture().
2022-05-13 15:55:05 +00:00
Vlad Zahorodnii
fa0143fb97 backends/drm: Ensure that there's opengl context when painting cursor 2022-05-12 12:34:48 +00:00
Xaver Hugl
ed06d752f0 backends/drm: blacklist hardware cursors with the NVidia driver
It doesn't work and seems to cause hangs. If desired, this can be overwritten
by explicitly setting KWIN_FORCE_SW_CURSOR to 0.

BUG: 453632
2022-05-11 21:53:00 +00:00
Xaver Hugl
78794b4239 backends/drm: disable cursor layer when setCursor fails
Otherwise the next commit will still try to enable the cursor layer, and
possibly fail because of it
2022-05-11 21:53:00 +00:00
Xaver Hugl
d83121dbe4 backends/drm: also use modifiers by default for virtual outputs 2022-05-10 19:42:36 +02:00
Xaver Hugl
f02a6fd128 backends/drm: add fallback for missing gbm modifier support
It can happen that a gbm implementation does not support modifiers, while
the drm driver does. To prevent that from breaking KWin, fall back to creating
a gbm surface without modifiers when creating one with modifiers fails.

BUG: 453320
2022-05-10 19:42:32 +02:00
Xaver Hugl
f07d6bd400 backends/drm: port the cursor to use output layers
CCBUG: 447797
2022-05-10 07:06:53 +00:00
Xaver Hugl
12515b4656 backends/drm: fix qpainter 2022-05-10 06:09:34 +00:00
Méven Car
1dd12a064a Fix a couple unused warnings
GIT_SILENT
NO_CHANGELOG
2022-05-10 07:33:30 +02:00
Xaver Hugl
e4695325a6 backends/drm: store gbm buffer for screen recording 2022-05-09 14:06:55 +00:00
Xaver Hugl
a110aabbcc backends/drm: consider escaped separators KWIN_DRM_DEVICES
':' conflicts with the file names in /dev/dri/by-path, so allow it to be
escaped with '\'

CCBUG: 453386
2022-05-09 08:16:47 +00:00
Erik Kurzinger
e6d2bc153f platforms/drm: set read buffer in GbmSurface::makeContextCurrent
The first time the GBM backend's EGL context is made current after
creation, both the read and draw surfaces are set to EGL_NO_SURFACE.
This will set the GL read and draw buffers to GL_NONE in accordance with
the EGL spec.

When a real surface is later made current, however, the spec is arguably
unclear on whether the read and draw buffers should remain set to
GL_NONE or whether they should be restored to the default GL_BACK.  The
Mesa driver does the latter, the NVIDIA driver does the former.

To work around this difference, Kwin has an explicit call to
glDrawBuffer in GbmSurface::makeContextCurrent. It does not have a
corresponding call to glReadBuffer, though, which can cause some desktop
effects such as background contrast to render incorrectly with the
NVIDIA driver. This change adds that missing call.
2022-05-08 12:58:10 -07:00
Xaver Hugl
9ef882f3fb backends/drm: use addfb2modifier again when supported
Otherwise the kernel might fail our request because the modifier doesn't
match the buffer
2022-05-07 13:28:47 +00:00
Xaver Hugl
788ae5891a backends/drm: zero metadata for unused planes
The kernel may fail requests if data for unused planes is non-zero.
2022-05-07 10:09:30 +00:00
Xaver Hugl
04509aaeb7 backends/drm: when creating a fd fails, reset all fds to -1 2022-05-06 18:31:03 +00:00
Vlad Zahorodnii
bc57e89b75 backends/drm: Fix file descriptor check 2022-05-06 17:24:47 +00:00
Vlad Zahorodnii
ad45deaf80 backends/drm: Add missing file descriptor initializer
We need to initialize file descriptors to -1 explicitly.

BUG: 453470
2022-05-06 17:24:47 +00:00
Xaver Hugl
d5dad1b471 backends/drm: properly release all buffers on render backend destruction
Releasing the buffers is necessary for example in the case of a GPU reset,
to make sure that the gbm surface is still properly destroyed and all buffers
with invalid content freed.
2022-05-06 12:39:15 +00:00
Xaver Hugl
c65c822392 backends/drm: refactor buffer management
Instead of buffers being both drm framebuffers and gbm / dumb buffers, these
responsibilities are now split, which makes it possible to do zero copy
screen casting in the future.

Both framebuffers and gbm / dumb buffers also now always hold a valid underlying
resource, which simplifies code a bit.
2022-05-06 12:39:15 +00:00
Xaver Hugl
46bbe4ff0c backends/drm: don't rely on test commits producing a buffer
When DrmPipeline::commitPipelines returns false without creating a test
buffer, we'd crash.

CCBUG: 453320
2022-05-03 08:14:53 +00:00
Xaver Hugl
8d3de947af backends/drm: re-create gamma ramps if necessary when switching crtcs
The gamma ramp size of different crtcs is not guaranteed to be the same,
so the gamma blob may need to be re-created
2022-05-02 17:40:25 +02:00
Xaver Hugl
b5aebc83ee backends/drm: fix gamma ramps with legacy
With legacy, gamma ramps wouldn't be calculated from the color transformation,
which made them not be applied.

BUG: 453070
2022-05-02 17:39:19 +02:00
Xaver Hugl
3c9d209344 backends/drm: fix mode updates with generated modes
DrmOutput::updateModes was called unnecessarily every time, because the
mode list the driver modes was compared against contained generated modes
2022-04-30 11:10:06 +00:00
Xaver Hugl
d50c9b8cb6 backends/drm: initialize layers earlier
With how layers are initialized before this commit, the atomic commit in
DrmOutput::updateModes can cause segfaults.
2022-04-30 10:46:14 +00:00
Aleix Pol
9a31b0d727 x11: trigger shortcuts when releasing rather than pressing
This way we can issue a keyboard grab without problems
2022-04-30 07:24:50 +00:00
Vlad Zahorodnii
066ac3200a backends/libinput: Rework Device getter
libinput_device_get_user_data() can be used to get the associated Device
object with libinput_device. That way, we won't need to maintain a
private list of all input devices.
2022-04-29 12:47:34 +00:00
Xaver Hugl
05877a8321 backends/drm: reduce "max bpc" to what is actually used
This prevents triggering a bug in the BenQ GW2765 monitor, and should
in theory have no downsides.

BUG: 449906
FIXED-IN: 5.24.5
2022-04-28 02:32:11 +02:00
Xaver Hugl
b522bbc8fc backends/drm: fix build with HAVE_GBM_BO_GET_FD_FOR_PLANE=0 2022-04-27 15:33:04 +00:00
Vlad Zahorodnii
fd453537c5 Drop Platform::screenSize()
It's effectively unused.
2022-04-27 06:49:26 +00:00
Xaver Hugl
14e7afcb4e color management: refactor and move to its own directory
The pipeline stages are also now properly managed, which should prevent
use-after-free errors.

BUG: 453026
2022-04-26 16:20:47 +00:00
Xaver Hugl
68a54a67b8 backends/drm: enable format modifiers by default
Format modifiers enable the graphics hardware to be much more efficient,
especially when it comes to multi-gpu transfers. With the issues regarding
bandwidth limits now solved, enable them by default to make all supported
systems benefit from them.

CCBUG: 452397
CCBUG: 452219
2022-04-26 17:03:19 +02:00
Xaver Hugl
916f1f4ea8 backends/drm: prune format modifiers when tests fail
When explicit modifiers are used, it can happen that Mesa chooses modifiers that make
the display hardware hit bandwidth limits. In that case, atomic tests fail and the
outputs don't work, or KWin may even crash.
In order to work around that, DrmGpu now removes the used modifier whenever an atomic
test fails, and tries to find a working combination of outputs and modifiers.
2022-04-26 17:03:02 +02:00
Xaver Hugl
e7959b9693 backends/drm: don't expose DrmPipeline state as a public member
While having all state be public is great for avoiding the boilerplate that
comes with setters and getters, it also exposes more state than necessary
to the rest of the backend and makes it more error-prone if more than one
part of the state needs to be changed at the same time.
2022-04-26 07:43:37 +00:00
Vlad Zahorodnii
175037d9d1 Prefer the term "window" over "client" in Workspace 2022-04-25 11:33:55 +00:00
Xaver Hugl
9ed87a4e23 backends/drm: support common display modes
BUG: 448398
2022-04-23 23:29:57 +02:00
Xaver Hugl
a343af674b backends/drm: fix damage tracking for virtual outputs 2022-04-23 10:51:09 +00:00
Vlad Zahorodnii
a21aa839b1 Rename X11Client to X11Window
The word "client" means different things in wayland and kwin. Use a
better word to refer to windows.
2022-04-23 07:55:51 +00:00
Nils Fenner
b491aeb9ae Rename AbstractClient to Window 2022-04-22 17:39:12 +00:00
Xaver Hugl
99761901ee backends/drm: don't check the test buffer if we don't need one
BUG: 452572
2022-04-22 15:17:01 +00:00
Xaver Hugl
941bae2810 backends/drm: fail atomic tests gracefully when buffer allocations fail
This should fix the crash. However, it's still unclear to me why allocations
fail in the first place

CCBUG: 452572
2022-04-22 15:17:01 +00:00
Vlad Zahorodnii
2b7fa206e8 Refactor Output information initialization
Instead of passing all possible field values to the initialize()
function, pass all relevant data in a struct. With designated
initializers, it's more readable and makes code more comprehensible.

The general goal is to split Output's data in two categories - general
information about the output (e.g. edid) and mutable state (position,
mode, etc).
2022-04-22 14:36:41 +00:00
Vlad Zahorodnii
a4a2ee0428 Refactor output mode abstractions
With this, the drm backend will be able to associate drmModeModeInfo
with Output's modes, which can be useful if there are several modes with
the same resolution and refresh rate but different flags.
2022-04-22 11:17:11 +00:00
Vlad Zahorodnii
b64f95b703 Integrate kwaylandserver
This makes KWin switch to in-tree copy of KWaylandServer codebase.

KWaylandServer namespace has been left as is. It will be addressed later
by renaming classes in order to fit in the KWin namespace.
2022-04-22 12:27:33 +03:00
Xaver Hugl
de73dfae35 backends/drm: rename transformation variables to be more intuitive 2022-04-20 15:57:51 +02:00
Xaver Hugl
d2d0049213 backends/drm: fix some problems with rotation
source and buffer rotation / sizes were used wrongly in a few places
2022-04-20 15:46:05 +02:00
Xaver Hugl
c3954eab8f Port gamma ramp code to generic color transformations
Instead of creating a gammaramp object with a fixed size, make the color
device create a color transformation object that can be used to construct
arbitrary LUTs. This is needed in order to support tiled displays well
and is useful for further color management work.
2022-04-20 12:29:26 +02:00
Xaver Hugl
7aad5df7d9 backends/drm: fix rebase mistake 2022-04-19 20:00:45 +02:00
Xaver Hugl
cc6b549112 backends/drm: drop QPainterLayer class
It's unused
2022-04-18 17:35:28 +02:00
Xaver Hugl
c43eb6ec42 backends/drm: extract dmabuf feedback into its own class
This should reduce code duplication with overlay planes
2022-04-18 17:34:04 +02:00
Xaver Hugl
5df65e4be5 backends/drm: refactor egl/gbm render surface into its own class
This allows sharing most code with overlay plane layers
2022-04-18 17:34:04 +02:00
Xaver Hugl
c30339cc82 backends/drm: move texture creation for gbm buffers into GbmBuffer 2022-04-18 17:34:04 +02:00
Nils Fenner
aaa429ee0a Merge Toplevel into AbstractClient
References issue #81
2022-04-18 07:42:11 +00:00
Xaver Hugl
3d556bba83 backends/drm: drop DrmGpu test mode
It's unused
2022-04-16 21:23:57 +00:00
Xaver Hugl
8cb8d2f627 backends/drm: drop DrmPipeline format helpers 2022-04-16 21:23:57 +00:00
Vlad Zahorodnii
e6f08665fe Drop Output::updateTransform()
If the backend needs to apply custom logic when changing the transform,
it should override Platform::applyOutputChanges(); otherwise just update
the Output's internal transform state.
2022-04-15 19:22:41 +03:00