summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/core/CMakeLists.txt7
-rw-r--r--src/core/hle/service/nvdrv/devices/nvdevice.h33
-rw-r--r--src/core/hle/service/nvdrv/devices/nvdisp_disp0.cpp29
-rw-r--r--src/core/hle/service/nvdrv/devices/nvdisp_disp0.h34
-rw-r--r--src/core/hle/service/nvdrv/devices/nvhost_as_gpu.cpp20
-rw-r--r--src/core/hle/service/nvdrv/devices/nvhost_as_gpu.h25
-rw-r--r--src/core/hle/service/nvdrv/devices/nvmap.cpp153
-rw-r--r--src/core/hle/service/nvdrv/devices/nvmap.h108
-rw-r--r--src/core/hle/service/nvdrv/nvdrv_a.cpp169
-rw-r--r--src/core/hle/service/nvdrv/nvdrv_a.h15
-rw-r--r--src/core/hle/service/vi/vi.cpp3
11 files changed, 430 insertions, 166 deletions
diff --git a/src/core/CMakeLists.txt b/src/core/CMakeLists.txt
index cc2b5b084..c836c0196 100644
--- a/src/core/CMakeLists.txt
+++ b/src/core/CMakeLists.txt
@@ -45,6 +45,9 @@ set(SRCS
45 hle/service/gsp_gpu.cpp 45 hle/service/gsp_gpu.cpp
46 hle/service/hid/hid.cpp 46 hle/service/hid/hid.cpp
47 hle/service/lm/lm.cpp 47 hle/service/lm/lm.cpp
48 hle/service/nvdrv/devices/nvdisp_disp0.cpp
49 hle/service/nvdrv/devices/nvhost_as_gpu.cpp
50 hle/service/nvdrv/devices/nvmap.cpp
48 hle/service/nvdrv/nvdrv.cpp 51 hle/service/nvdrv/nvdrv.cpp
49 hle/service/nvdrv/nvdrv_a.cpp 52 hle/service/nvdrv/nvdrv_a.cpp
50 hle/service/pctl/pctl.cpp 53 hle/service/pctl/pctl.cpp
@@ -132,6 +135,10 @@ set(HEADERS
132 hle/service/gsp_gpu.h 135 hle/service/gsp_gpu.h
133 hle/service/hid/hid.h 136 hle/service/hid/hid.h
134 hle/service/lm/lm.h 137 hle/service/lm/lm.h
138 hle/service/nvdrv/devices/nvdevice.h
139 hle/service/nvdrv/devices/nvdisp_disp0.h
140 hle/service/nvdrv/devices/nvhost_as_gpu.h
141 hle/service/nvdrv/devices/nvmap.h
135 hle/service/nvdrv/nvdrv.h 142 hle/service/nvdrv/nvdrv.h
136 hle/service/nvdrv/nvdrv_a.h 143 hle/service/nvdrv/nvdrv_a.h
137 hle/service/pctl/pctl.h 144 hle/service/pctl/pctl.h
diff --git a/src/core/hle/service/nvdrv/devices/nvdevice.h b/src/core/hle/service/nvdrv/devices/nvdevice.h
new file mode 100644
index 000000000..b4efce3a1
--- /dev/null
+++ b/src/core/hle/service/nvdrv/devices/nvdevice.h
@@ -0,0 +1,33 @@
1// Copyright 2018 Citra Emulator Project
2// Licensed under GPLv2 or any later version
3// Refer to the license.txt file included.
4
5#pragma once
6
7#include <vector>
8#include "common/common_types.h"
9
10namespace Service {
11namespace NVDRV {
12namespace Devices {
13
14/// Represents an abstract nvidia device node. It is to be subclassed by concrete device nodes to
15/// implement the ioctl interface.
16class nvdevice {
17public:
18 nvdevice() = default;
19 virtual ~nvdevice() = default;
20
21 /**
22 * Handles an ioctl request.
23 * @param command The ioctl command id.
24 * @param input A buffer containing the input data for the ioctl.
25 * @param output A buffer where the output data will be written to.
26 * @returns The result code of the ioctl.
27 */
28 virtual u32 ioctl(u32 command, const std::vector<u8>& input, std::vector<u8>& output) = 0;
29};
30
31} // namespace Devices
32} // namespace NVDRV
33} // namespace Service
diff --git a/src/core/hle/service/nvdrv/devices/nvdisp_disp0.cpp b/src/core/hle/service/nvdrv/devices/nvdisp_disp0.cpp
new file mode 100644
index 000000000..faed626ba
--- /dev/null
+++ b/src/core/hle/service/nvdrv/devices/nvdisp_disp0.cpp
@@ -0,0 +1,29 @@
1// Copyright 2018 Yuzu Emulator Team
2// Licensed under GPLv2 or any later version
3// Refer to the license.txt file included.
4
5#include "common/assert.h"
6#include "common/logging/log.h"
7#include "core/hle/service/nvdrv/devices/nvdisp_disp0.h"
8#include "core/hle/service/nvdrv/devices/nvmap.h"
9
10namespace Service {
11namespace NVDRV {
12namespace Devices {
13
14u32 nvdisp_disp0::ioctl(u32 command, const std::vector<u8>& input, std::vector<u8>& output) {
15 ASSERT(false, "Unimplemented");
16 return 0;
17}
18
19void nvdisp_disp0::flip(u32 buffer_handle, u32 offset, u32 format, u32 width, u32 height,
20 u32 stride) {
21 VAddr addr = nvmap_dev->GetObjectAddress(buffer_handle);
22 LOG_WARNING(Service,
23 "Drawing from address %llx offset %08X Width %u Height %u Stride %u Format %u",
24 addr, offset, width, height, stride, format);
25}
26
27} // namespace Devices
28} // namespace NVDRV
29} // namespace Service
diff --git a/src/core/hle/service/nvdrv/devices/nvdisp_disp0.h b/src/core/hle/service/nvdrv/devices/nvdisp_disp0.h
new file mode 100644
index 000000000..54725917f
--- /dev/null
+++ b/src/core/hle/service/nvdrv/devices/nvdisp_disp0.h
@@ -0,0 +1,34 @@
1// Copyright 2018 Citra Emulator Project
2// Licensed under GPLv2 or any later version
3// Refer to the license.txt file included.
4
5#pragma once
6
7#include <memory>
8#include <vector>
9#include "common/common_types.h"
10#include "core/hle/service/nvdrv/devices/nvdevice.h"
11
12namespace Service {
13namespace NVDRV {
14namespace Devices {
15
16class nvmap;
17
18class nvdisp_disp0 final : public nvdevice {
19public:
20 nvdisp_disp0(std::shared_ptr<nvmap> nvmap_dev) : nvdevice(), nvmap_dev(std::move(nvmap_dev)) {}
21 ~nvdisp_disp0() = default;
22
23 u32 ioctl(u32 command, const std::vector<u8>& input, std::vector<u8>& output) override;
24
25 /// Performs a screen flip, drawing the buffer pointed to by the handle.
26 void flip(u32 buffer_handle, u32 offset, u32 format, u32 width, u32 height, u32 stride);
27
28private:
29 std::shared_ptr<nvmap> nvmap_dev;
30};
31
32} // namespace Devices
33} // namespace NVDRV
34} // namespace Service
diff --git a/src/core/hle/service/nvdrv/devices/nvhost_as_gpu.cpp b/src/core/hle/service/nvdrv/devices/nvhost_as_gpu.cpp
new file mode 100644
index 000000000..50fee8f46
--- /dev/null
+++ b/src/core/hle/service/nvdrv/devices/nvhost_as_gpu.cpp
@@ -0,0 +1,20 @@
1// Copyright 2018 Yuzu Emulator Team
2// Licensed under GPLv2 or any later version
3// Refer to the license.txt file included.
4
5#include "common/assert.h"
6#include "common/logging/log.h"
7#include "core/hle/service/nvdrv/devices/nvhost_as_gpu.h"
8
9namespace Service {
10namespace NVDRV {
11namespace Devices {
12
13u32 nvhost_as_gpu::ioctl(u32 command, const std::vector<u8>& input, std::vector<u8>& output) {
14 ASSERT(false, "Unimplemented");
15 return 0;
16}
17
18} // namespace Devices
19} // namespace NVDRV
20} // namespace Service
diff --git a/src/core/hle/service/nvdrv/devices/nvhost_as_gpu.h b/src/core/hle/service/nvdrv/devices/nvhost_as_gpu.h
new file mode 100644
index 000000000..411275922
--- /dev/null
+++ b/src/core/hle/service/nvdrv/devices/nvhost_as_gpu.h
@@ -0,0 +1,25 @@
1// Copyright 2018 Citra Emulator Project
2// Licensed under GPLv2 or any later version
3// Refer to the license.txt file included.
4
5#pragma once
6
7#include <vector>
8#include "common/common_types.h"
9#include "core/hle/service/nvdrv/devices/nvdevice.h"
10
11namespace Service {
12namespace NVDRV {
13namespace Devices {
14
15class nvhost_as_gpu final : public nvdevice {
16public:
17 nvhost_as_gpu() = default;
18 ~nvhost_as_gpu() override = default;
19
20 u32 ioctl(u32 command, const std::vector<u8>& input, std::vector<u8>& output) override;
21};
22
23} // namespace Devices
24} // namespace NVDRV
25} // namespace Service
diff --git a/src/core/hle/service/nvdrv/devices/nvmap.cpp b/src/core/hle/service/nvdrv/devices/nvmap.cpp
new file mode 100644
index 000000000..fdf2f7be5
--- /dev/null
+++ b/src/core/hle/service/nvdrv/devices/nvmap.cpp
@@ -0,0 +1,153 @@
1// Copyright 2018 Yuzu Emulator Team
2// Licensed under GPLv2 or any later version
3// Refer to the license.txt file included.
4
5#include "common/assert.h"
6#include "common/logging/log.h"
7#include "core/hle/service/nvdrv/devices/nvmap.h"
8
9namespace Service {
10namespace NVDRV {
11namespace Devices {
12
13VAddr nvmap::GetObjectAddress(u32 handle) const {
14 auto itr = handles.find(handle);
15 ASSERT(itr != handles.end());
16
17 auto object = itr->second;
18 ASSERT(object->status == Object::Status::Allocated);
19 return object->addr;
20}
21
22u32 nvmap::ioctl(u32 command, const std::vector<u8>& input, std::vector<u8>& output) {
23 switch (command) {
24 case IocCreateCommand:
25 return IocCreate(input, output);
26 case IocAllocCommand:
27 return IocAlloc(input, output);
28 case IocGetIdCommand:
29 return IocGetId(input, output);
30 case IocFromIdCommand:
31 return IocFromId(input, output);
32 case IocParamCommand:
33 return IocParam(input, output);
34 }
35
36 ASSERT(false, "Unimplemented");
37}
38
39u32 nvmap::IocCreate(const std::vector<u8>& input, std::vector<u8>& output) {
40 IocCreateParams params;
41 std::memcpy(&params, input.data(), sizeof(params));
42
43 // Create a new nvmap object and obtain a handle to it.
44 auto object = std::make_shared<Object>();
45 object->id = next_id++;
46 object->size = params.size;
47 object->status = Object::Status::Created;
48
49 u32 handle = next_handle++;
50 handles[handle] = std::move(object);
51
52 LOG_WARNING(Service, "(STUBBED) size 0x%08X", params.size);
53
54 params.handle = handle;
55
56 std::memcpy(output.data(), &params, sizeof(params));
57 return 0;
58}
59
60u32 nvmap::IocAlloc(const std::vector<u8>& input, std::vector<u8>& output) {
61 IocAllocParams params;
62 std::memcpy(&params, input.data(), sizeof(params));
63
64 auto itr = handles.find(params.handle);
65 ASSERT(itr != handles.end());
66
67 auto object = itr->second;
68 object->flags = params.flags;
69 object->align = params.align;
70 object->kind = params.kind;
71 object->addr = params.addr;
72 object->status = Object::Status::Allocated;
73
74 LOG_WARNING(Service, "(STUBBED) Allocated address 0x%llx", params.addr);
75
76 std::memcpy(output.data(), &params, sizeof(params));
77 return 0;
78}
79
80u32 nvmap::IocGetId(const std::vector<u8>& input, std::vector<u8>& output) {
81 IocGetIdParams params;
82 std::memcpy(&params, input.data(), sizeof(params));
83
84 LOG_WARNING(Service, "called");
85
86 auto itr = handles.find(params.handle);
87 ASSERT(itr != handles.end());
88
89 params.id = itr->second->id;
90
91 std::memcpy(output.data(), &params, sizeof(params));
92 return 0;
93}
94
95u32 nvmap::IocFromId(const std::vector<u8>& input, std::vector<u8>& output) {
96 IocFromIdParams params;
97 std::memcpy(&params, input.data(), sizeof(params));
98
99 LOG_WARNING(Service, "(STUBBED) called");
100
101 auto itr = std::find_if(handles.begin(), handles.end(),
102 [&](const auto& entry) { return entry.second->id == params.id; });
103 ASSERT(itr != handles.end());
104
105 // Make a new handle for the object
106 u32 handle = next_handle++;
107 handles[handle] = itr->second;
108
109 params.handle = handle;
110
111 std::memcpy(output.data(), &params, sizeof(params));
112 return 0;
113}
114
115u32 nvmap::IocParam(const std::vector<u8>& input, std::vector<u8>& output) {
116 enum class ParamTypes { Size = 1, Alignment = 2, Base = 3, Heap = 4, Kind = 5, Compr = 6 };
117
118 IocParamParams params;
119 std::memcpy(&params, input.data(), sizeof(params));
120
121 LOG_WARNING(Service, "(STUBBED) called type=%u", params.type);
122
123 auto itr = handles.find(params.handle);
124 ASSERT(itr != handles.end());
125
126 auto object = itr->second;
127 ASSERT(object->status == Object::Status::Allocated);
128
129 switch (static_cast<ParamTypes>(params.type)) {
130 case ParamTypes::Size:
131 params.value = object->size;
132 break;
133 case ParamTypes::Alignment:
134 params.value = object->align;
135 break;
136 case ParamTypes::Heap:
137 // TODO(Subv): Seems to be a hardcoded value?
138 params.value = 0x40000000;
139 break;
140 case ParamTypes::Kind:
141 params.value = object->kind;
142 break;
143 default:
144 ASSERT(false, "Unimplemented");
145 }
146
147 std::memcpy(output.data(), &params, sizeof(params));
148 return 0;
149}
150
151} // namespace Devices
152} // namespace NVDRV
153} // namespace Service
diff --git a/src/core/hle/service/nvdrv/devices/nvmap.h b/src/core/hle/service/nvdrv/devices/nvmap.h
new file mode 100644
index 000000000..e8b08f3fb
--- /dev/null
+++ b/src/core/hle/service/nvdrv/devices/nvmap.h
@@ -0,0 +1,108 @@
1// Copyright 2018 Citra Emulator Project
2// Licensed under GPLv2 or any later version
3// Refer to the license.txt file included.
4
5#pragma once
6
7#include <memory>
8#include <unordered_map>
9#include <vector>
10#include "common/common_funcs.h"
11#include "common/common_types.h"
12#include "common/swap.h"
13#include "core/hle/service/nvdrv/devices/nvdevice.h"
14
15namespace Service {
16namespace NVDRV {
17namespace Devices {
18
19class nvmap final : public nvdevice {
20public:
21 nvmap() = default;
22 ~nvmap() override = default;
23
24 /// Returns the allocated address of an nvmap object given its handle.
25 VAddr GetObjectAddress(u32 handle) const;
26
27 u32 ioctl(u32 command, const std::vector<u8>& input, std::vector<u8>& output) override;
28
29private:
30 // Represents an nvmap object.
31 struct Object {
32 enum class Status { Created, Allocated };
33 u32 id;
34 u32 size;
35 u32 flags;
36 u32 align;
37 u8 kind;
38 VAddr addr;
39 Status status;
40 };
41
42 /// Id to use for the next handle that is created.
43 u32 next_handle = 1;
44
45 // Id to use for the next object that is created.
46 u32 next_id = 1;
47
48 /// Mapping of currently allocated handles to the objects they represent.
49 std::unordered_map<u32, std::shared_ptr<Object>> handles;
50
51 enum IoctlCommands {
52 IocCreateCommand = 0xC0080101,
53 IocFromIdCommand = 0xC0080103,
54 IocAllocCommand = 0xC0200104,
55 IocParamCommand = 0xC00C0109,
56 IocGetIdCommand = 0xC008010E
57 };
58
59 struct IocCreateParams {
60 // Input
61 u32_le size;
62 // Output
63 u32_le handle;
64 };
65
66 struct IocAllocParams {
67 // Input
68 u32_le handle;
69 u32_le heap_mask;
70 u32_le flags;
71 u32_le align;
72 u8 kind;
73 INSERT_PADDING_BYTES(7);
74 u64_le addr;
75 };
76
77 struct IocGetIdParams {
78 // Output
79 u32_le id;
80 // Input
81 u32_le handle;
82 };
83
84 struct IocFromIdParams {
85 // Input
86 u32_le id;
87 // Output
88 u32_le handle;
89 };
90
91 struct IocParamParams {
92 // Input
93 u32_le handle;
94 u32_le type;
95 // Output
96 u32_le value;
97 };
98
99 u32 IocCreate(const std::vector<u8>& input, std::vector<u8>& output);
100 u32 IocAlloc(const std::vector<u8>& input, std::vector<u8>& output);
101 u32 IocGetId(const std::vector<u8>& input, std::vector<u8>& output);
102 u32 IocFromId(const std::vector<u8>& input, std::vector<u8>& output);
103 u32 IocParam(const std::vector<u8>& input, std::vector<u8>& output);
104};
105
106} // namespace Devices
107} // namespace NVDRV
108} // namespace Service
diff --git a/src/core/hle/service/nvdrv/nvdrv_a.cpp b/src/core/hle/service/nvdrv/nvdrv_a.cpp
index cede4a883..cfecea924 100644
--- a/src/core/hle/service/nvdrv/nvdrv_a.cpp
+++ b/src/core/hle/service/nvdrv/nvdrv_a.cpp
@@ -4,171 +4,16 @@
4 4
5#include "common/logging/log.h" 5#include "common/logging/log.h"
6#include "core/hle/ipc_helpers.h" 6#include "core/hle/ipc_helpers.h"
7#include "core/hle/service/nvdrv/devices/nvdevice.h"
8#include "core/hle/service/nvdrv/devices/nvdisp_disp0.h"
9#include "core/hle/service/nvdrv/devices/nvhost_as_gpu.h"
10#include "core/hle/service/nvdrv/devices/nvmap.h"
7#include "core/hle/service/nvdrv/nvdrv.h" 11#include "core/hle/service/nvdrv/nvdrv.h"
8#include "core/hle/service/nvdrv/nvdrv_a.h" 12#include "core/hle/service/nvdrv/nvdrv_a.h"
9 13
10namespace Service { 14namespace Service {
11namespace NVDRV { 15namespace NVDRV {
12 16
13class nvhost_as_gpu : public nvdevice {
14public:
15 u32 ioctl(u32 command, const std::vector<u8>& input, std::vector<u8>& output) override {
16 ASSERT(false, "Unimplemented");
17 return 0;
18 }
19};
20
21VAddr nvmap::GetObjectAddress(u32 handle) const {
22 auto itr = handles.find(handle);
23 ASSERT(itr != handles.end());
24
25 auto object = itr->second;
26 ASSERT(object->status == Object::Status::Allocated);
27 return object->addr;
28}
29
30u32 nvmap::ioctl(u32 command, const std::vector<u8>& input, std::vector<u8>& output) {
31 switch (command) {
32 case IocCreateCommand:
33 return IocCreate(input, output);
34 case IocAllocCommand:
35 return IocAlloc(input, output);
36 case IocGetIdCommand:
37 return IocGetId(input, output);
38 case IocFromIdCommand:
39 return IocFromId(input, output);
40 case IocParamCommand:
41 return IocParam(input, output);
42 }
43
44 ASSERT(false, "Unimplemented");
45}
46
47u32 nvmap::IocCreate(const std::vector<u8>& input, std::vector<u8>& output) {
48 IocCreateParams params;
49 std::memcpy(&params, input.data(), sizeof(params));
50
51 // Create a new nvmap object and obtain a handle to it.
52 auto object = std::make_shared<Object>();
53 object->id = next_id++;
54 object->size = params.size;
55 object->status = Object::Status::Created;
56
57 u32 handle = next_handle++;
58 handles[handle] = std::move(object);
59
60 LOG_WARNING(Service, "(STUBBED) size 0x%08X", params.size);
61
62 params.handle = handle;
63
64 std::memcpy(output.data(), &params, sizeof(params));
65 return 0;
66}
67
68u32 nvmap::IocAlloc(const std::vector<u8>& input, std::vector<u8>& output) {
69 IocAllocParams params;
70 std::memcpy(&params, input.data(), sizeof(params));
71
72 auto itr = handles.find(params.handle);
73 ASSERT(itr != handles.end());
74
75 auto object = itr->second;
76 object->flags = params.flags;
77 object->align = params.align;
78 object->kind = params.kind;
79 object->addr = params.addr;
80 object->status = Object::Status::Allocated;
81
82 LOG_WARNING(Service, "(STUBBED) Allocated address 0x%llx", params.addr);
83
84 std::memcpy(output.data(), &params, sizeof(params));
85 return 0;
86}
87
88u32 nvmap::IocGetId(const std::vector<u8>& input, std::vector<u8>& output) {
89 IocGetIdParams params;
90 std::memcpy(&params, input.data(), sizeof(params));
91
92 LOG_WARNING(Service, "called");
93
94 auto itr = handles.find(params.handle);
95 ASSERT(itr != handles.end());
96
97 params.id = itr->second->id;
98
99 std::memcpy(output.data(), &params, sizeof(params));
100 return 0;
101}
102
103u32 nvmap::IocFromId(const std::vector<u8>& input, std::vector<u8>& output) {
104 IocFromIdParams params;
105 std::memcpy(&params, input.data(), sizeof(params));
106
107 LOG_WARNING(Service, "(STUBBED) called");
108
109 auto itr = std::find_if(handles.begin(), handles.end(),
110 [&](const auto& entry) { return entry.second->id == params.id; });
111 ASSERT(itr != handles.end());
112
113 // Make a new handle for the object
114 u32 handle = next_handle++;
115 handles[handle] = itr->second;
116
117 params.handle = handle;
118
119 std::memcpy(output.data(), &params, sizeof(params));
120 return 0;
121}
122
123u32 nvmap::IocParam(const std::vector<u8>& input, std::vector<u8>& output) {
124 enum class ParamTypes { Size = 1, Alignment = 2, Base = 3, Heap = 4, Kind = 5, Compr = 6 };
125
126 IocParamParams params;
127 std::memcpy(&params, input.data(), sizeof(params));
128
129 LOG_WARNING(Service, "(STUBBED) called type=%u", params.type);
130
131 auto itr = handles.find(params.handle);
132 ASSERT(itr != handles.end());
133
134 auto object = itr->second;
135 ASSERT(object->status == Object::Status::Allocated);
136
137 switch (static_cast<ParamTypes>(params.type)) {
138 case ParamTypes::Size:
139 params.value = object->size;
140 break;
141 case ParamTypes::Alignment:
142 params.value = object->align;
143 break;
144 case ParamTypes::Heap:
145 // TODO(Subv): Seems to be a hardcoded value?
146 params.value = 0x40000000;
147 break;
148 case ParamTypes::Kind:
149 params.value = object->kind;
150 break;
151 default:
152 ASSERT(false, "Unimplemented");
153 }
154
155 std::memcpy(output.data(), &params, sizeof(params));
156 return 0;
157}
158
159u32 nvdisp_disp0::ioctl(u32 command, const std::vector<u8>& input, std::vector<u8>& output) {
160 ASSERT(false, "Unimplemented");
161 return 0;
162}
163
164void nvdisp_disp0::flip(u32 buffer_handle, u32 offset, u32 format, u32 width, u32 height,
165 u32 stride) {
166 VAddr addr = nvmap_dev->GetObjectAddress(buffer_handle);
167 LOG_WARNING(Service,
168 "Drawing from address %llx offset %08X Width %u Height %u Stride %u Format %u",
169 addr, offset, width, height, stride, format);
170}
171
172void NVDRV_A::Open(Kernel::HLERequestContext& ctx) { 17void NVDRV_A::Open(Kernel::HLERequestContext& ctx) {
173 LOG_WARNING(Service, "(STUBBED) called"); 18 LOG_WARNING(Service, "(STUBBED) called");
174 19
@@ -229,10 +74,10 @@ NVDRV_A::NVDRV_A() : ServiceFramework("nvdrv:a") {
229 }; 74 };
230 RegisterHandlers(functions); 75 RegisterHandlers(functions);
231 76
232 auto nvmap_dev = std::make_shared<nvmap>(); 77 auto nvmap_dev = std::make_shared<Devices::nvmap>();
233 devices["/dev/nvhost-as-gpu"] = std::make_shared<nvhost_as_gpu>(); 78 devices["/dev/nvhost-as-gpu"] = std::make_shared<Devices::nvhost_as_gpu>();
234 devices["/dev/nvmap"] = nvmap_dev; 79 devices["/dev/nvmap"] = nvmap_dev;
235 devices["/dev/nvdisp_disp0"] = std::make_shared<nvdisp_disp0>(nvmap_dev); 80 devices["/dev/nvdisp_disp0"] = std::make_shared<Devices::nvdisp_disp0>(nvmap_dev);
236} 81}
237 82
238} // namespace NVDRV 83} // namespace NVDRV
diff --git a/src/core/hle/service/nvdrv/nvdrv_a.h b/src/core/hle/service/nvdrv/nvdrv_a.h
index af1017881..4cd04adea 100644
--- a/src/core/hle/service/nvdrv/nvdrv_a.h
+++ b/src/core/hle/service/nvdrv/nvdrv_a.h
@@ -5,12 +5,17 @@
5#pragma once 5#pragma once
6 6
7#include <memory> 7#include <memory>
8#include "core/hle/service/service.h" 8#include <string>
9#include "core/hle/service/nvdrv/nvdrv.h" 9#include "core/hle/service/nvdrv/nvdrv.h"
10#include "core/hle/service/service.h"
10 11
11namespace Service { 12namespace Service {
12namespace NVDRV { 13namespace NVDRV {
13 14
15namespace Devices {
16class nvdevice;
17}
18
14class NVDRV_A final : public ServiceFramework<NVDRV_A> { 19class NVDRV_A final : public ServiceFramework<NVDRV_A> {
15public: 20public:
16 NVDRV_A(); 21 NVDRV_A();
@@ -30,10 +35,14 @@ private:
30 void Ioctl(Kernel::HLERequestContext& ctx); 35 void Ioctl(Kernel::HLERequestContext& ctx);
31 void Initialize(Kernel::HLERequestContext& ctx); 36 void Initialize(Kernel::HLERequestContext& ctx);
32 37
38 /// Id to use for the next open file descriptor.
33 u32 next_fd = 1; 39 u32 next_fd = 1;
34 40
35 std::unordered_map<u32, std::shared_ptr<nvdevice>> open_files; 41 /// Mapping of file descriptors to the devices they reference.
36 std::unordered_map<std::string, std::shared_ptr<nvdevice>> devices; 42 std::unordered_map<u32, std::shared_ptr<Devices::nvdevice>> open_files;
43
44 /// Mapping of device node names to their implementation.
45 std::unordered_map<std::string, std::shared_ptr<Devices::nvdevice>> devices;
37}; 46};
38 47
39extern std::weak_ptr<NVDRV_A> nvdrv_a; 48extern std::weak_ptr<NVDRV_A> nvdrv_a;
diff --git a/src/core/hle/service/vi/vi.cpp b/src/core/hle/service/vi/vi.cpp
index 55bbd45db..0b089702c 100644
--- a/src/core/hle/service/vi/vi.cpp
+++ b/src/core/hle/service/vi/vi.cpp
@@ -6,6 +6,7 @@
6#include "common/scope_exit.h" 6#include "common/scope_exit.h"
7#include "core/core_timing.h" 7#include "core/core_timing.h"
8#include "core/hle/ipc_helpers.h" 8#include "core/hle/ipc_helpers.h"
9#include "core/hle/service/nvdrv/devices/nvdisp_disp0.h"
9#include "core/hle/service/nvdrv/nvdrv_a.h" 10#include "core/hle/service/nvdrv/nvdrv_a.h"
10#include "core/hle/service/vi/vi.h" 11#include "core/hle/service/vi/vi.h"
11#include "core/hle/service/vi/vi_m.h" 12#include "core/hle/service/vi/vi_m.h"
@@ -752,7 +753,7 @@ void NVFlinger::Compose() {
752 753
753 // TODO(Subv): Support more than just disp0. The display device selection is probably based 754 // TODO(Subv): Support more than just disp0. The display device selection is probably based
754 // on which display we're drawing (Default, Internal, External, etc) 755 // on which display we're drawing (Default, Internal, External, etc)
755 auto nvdisp = nvdrv->GetDevice<NVDRV::nvdisp_disp0>("/dev/nvdisp_disp0"); 756 auto nvdisp = nvdrv->GetDevice<NVDRV::Devices::nvdisp_disp0>("/dev/nvdisp_disp0");
756 ASSERT(nvdisp); 757 ASSERT(nvdisp);
757 758
758 nvdisp->flip(igbp_buffer.gpu_buffer_id, igbp_buffer.offset, igbp_buffer.format, 759 nvdisp->flip(igbp_buffer.gpu_buffer_id, igbp_buffer.offset, igbp_buffer.format,