Serenity Operating System
1/*
2 * Copyright (c) 2022, Liav A. <liavalb@hotmail.co.il>
3 *
4 * SPDX-License-Identifier: BSD-2-Clause
5 */
6
7#include <Kernel/Arch/Delay.h>
8#include <Kernel/Bus/PCI/API.h>
9#include <Kernel/Debug.h>
10#include <Kernel/Devices/DeviceManagement.h>
11#include <Kernel/Graphics/Console/ContiguousFramebufferConsole.h>
12#include <Kernel/Graphics/GraphicsManagement.h>
13#include <Kernel/Graphics/Intel/DisplayConnectorGroup.h>
14#include <Kernel/Graphics/Intel/NativeDisplayConnector.h>
15#include <Kernel/Memory/Region.h>
16
17namespace Kernel {
18
19ErrorOr<NonnullLockRefPtr<IntelNativeDisplayConnector>> IntelNativeDisplayConnector::try_create_with_display_connector_group(IntelDisplayConnectorGroup const& parent_connector_group, ConnectorIndex connector_index, Type type, PhysicalAddress framebuffer_address, size_t framebuffer_resource_size)
20{
21 return TRY(DeviceManagement::try_create_device<IntelNativeDisplayConnector>(parent_connector_group, connector_index, type, framebuffer_address, framebuffer_resource_size));
22}
23
24ErrorOr<void> IntelNativeDisplayConnector::create_attached_framebuffer_console(Badge<IntelDisplayConnectorGroup>)
25{
26 size_t width = 0;
27 size_t height = 0;
28 size_t pitch = 0;
29 {
30 SpinlockLocker control_locker(m_control_lock);
31 SpinlockLocker mode_set_locker(m_modeset_lock);
32 width = m_current_mode_setting.horizontal_active;
33 height = m_current_mode_setting.vertical_active;
34 pitch = m_current_mode_setting.horizontal_stride;
35 }
36 m_framebuffer_console = Graphics::ContiguousFramebufferConsole::initialize(m_framebuffer_address.value(), width, height, pitch);
37 GraphicsManagement::the().set_console(*m_framebuffer_console);
38 return {};
39}
40
41IntelNativeDisplayConnector::IntelNativeDisplayConnector(IntelDisplayConnectorGroup const& parent_connector_group, ConnectorIndex connector_index, Type type, PhysicalAddress framebuffer_address, size_t framebuffer_resource_size)
42 : DisplayConnector(framebuffer_address, framebuffer_resource_size, true)
43 , m_type(type)
44 , m_connector_index(connector_index)
45 , m_parent_connector_group(parent_connector_group)
46{
47}
48
49void IntelNativeDisplayConnector::set_edid_bytes(Badge<IntelDisplayConnectorGroup>, Array<u8, 128> const& raw_bytes)
50{
51 // Note: The provided EDID might be invalid (because there's no attached monitor)
52 // Therefore, set might_be_invalid to true to indicate that.
53 DisplayConnector::set_edid_bytes(raw_bytes, true);
54}
55
56ErrorOr<void> IntelNativeDisplayConnector::set_y_offset(size_t)
57{
58 return Error::from_errno(ENOTIMPL);
59}
60
61ErrorOr<void> IntelNativeDisplayConnector::unblank()
62{
63 return Error::from_errno(ENOTIMPL);
64}
65
66ErrorOr<void> IntelNativeDisplayConnector::set_safe_mode_setting()
67{
68 SpinlockLocker locker(m_modeset_lock);
69 return m_parent_connector_group->set_safe_mode_setting({}, *this);
70}
71
72void IntelNativeDisplayConnector::enable_console()
73{
74 VERIFY(m_control_lock.is_locked());
75 if (m_framebuffer_console)
76 m_framebuffer_console->enable();
77}
78
79void IntelNativeDisplayConnector::disable_console()
80{
81 VERIFY(m_control_lock.is_locked());
82 if (m_framebuffer_console)
83 m_framebuffer_console->disable();
84}
85
86ErrorOr<void> IntelNativeDisplayConnector::flush_first_surface()
87{
88 return Error::from_errno(ENOTSUP);
89}
90
91ErrorOr<void> IntelNativeDisplayConnector::set_mode_setting(DisplayConnector::ModeSetting const&)
92{
93 return Error::from_errno(ENOTIMPL);
94}
95
96}