From 9f1a853cc83a08ece3fa949a637c8b9f1bbb142c Mon Sep 17 00:00:00 2001 From: Andreas Kling Date: Wed, 17 Jul 2024 19:14:16 +0200 Subject: [PATCH] LibGfx: Add ability to pass NonnullRefPtr over IPC --- Userland/Libraries/LibGfx/Bitmap.cpp | 42 ++++++++++++++++++++++++++++ Userland/Libraries/LibGfx/Bitmap.h | 13 ++++++++- 2 files changed, 54 insertions(+), 1 deletion(-) diff --git a/Userland/Libraries/LibGfx/Bitmap.cpp b/Userland/Libraries/LibGfx/Bitmap.cpp index aa9cabd30ae..2c745240bec 100644 --- a/Userland/Libraries/LibGfx/Bitmap.cpp +++ b/Userland/Libraries/LibGfx/Bitmap.cpp @@ -17,6 +17,9 @@ #include #include #include +#include +#include +#include #include namespace Gfx { @@ -435,3 +438,42 @@ bool Bitmap::visually_equals(Bitmap const& other) const } } + +namespace IPC { + +template<> +ErrorOr encode(Encoder& encoder, AK::NonnullRefPtr const& bitmap) +{ + Core::AnonymousBuffer buffer; + if (bitmap->anonymous_buffer().is_valid()) { + buffer = bitmap->anonymous_buffer(); + } else { + buffer = MUST(Core::AnonymousBuffer::create_with_size(bitmap->size_in_bytes())); + memcpy(buffer.data(), bitmap->scanline(0), bitmap->size_in_bytes()); + } + TRY(encoder.encode(TRY(IPC::File::clone_fd(buffer.fd())))); + TRY(encoder.encode(static_cast(bitmap->format()))); + TRY(encoder.encode(bitmap->size_in_bytes())); + TRY(encoder.encode(bitmap->pitch())); + TRY(encoder.encode(bitmap->size())); + return {}; +} + +template<> +ErrorOr> decode(Decoder& decoder) +{ + auto anon_file = TRY(decoder.decode()); + auto raw_bitmap_format = TRY(decoder.decode()); + if (!Gfx::is_valid_bitmap_format(raw_bitmap_format)) + return Error::from_string_literal("IPC: Invalid Gfx::ShareableBitmap format"); + auto bitmap_format = static_cast(raw_bitmap_format); + auto size_in_bytes = TRY(decoder.decode()); + auto pitch = TRY(decoder.decode()); + auto size = TRY(decoder.decode()); + auto* data = TRY(Core::System::mmap(nullptr, round_up_to_power_of_two(size_in_bytes, PAGE_SIZE), PROT_READ | PROT_WRITE, MAP_SHARED, anon_file.fd(), 0)); + return Gfx::Bitmap::create_wrapper(bitmap_format, size, pitch, data, [data, size_in_bytes] { + MUST(Core::System::munmap(data, size_in_bytes)); + }); +} + +} diff --git a/Userland/Libraries/LibGfx/Bitmap.h b/Userland/Libraries/LibGfx/Bitmap.h index 3d183e531a4..9b8be274c4c 100644 --- a/Userland/Libraries/LibGfx/Bitmap.h +++ b/Userland/Libraries/LibGfx/Bitmap.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2018-2023, Andreas Kling + * Copyright (c) 2018-2024, Andreas Kling * Copyright (c) 2022, Timothy Slater * * SPDX-License-Identifier: BSD-2-Clause @@ -15,6 +15,7 @@ #include #include #include +#include namespace Gfx { @@ -295,3 +296,13 @@ ALWAYS_INLINE void Bitmap::set_pixel(int x, int y, Color color) } } + +namespace IPC { + +template<> +ErrorOr encode(Encoder&, AK::NonnullRefPtr const&); + +template<> +ErrorOr> decode(Decoder&); + +}