1 // SPDX-License-Identifier: GPL-2.0-only
2 /*
3 * Copyright (C) 2025 Icenowy Zheng <uwu@icenowy.me>
4 */
5
6 #include <linux/errno.h>
7
8 #include <drm/drm_fourcc.h>
9
10 #include "vs_dc_top_regs.h"
11 #include "vs_hwdb.h"
12
13 static const u32 vs_primary_formats_array_no_yuv444[] = {
14 DRM_FORMAT_XRGB4444,
15 DRM_FORMAT_XBGR4444,
16 DRM_FORMAT_RGBX4444,
17 DRM_FORMAT_BGRX4444,
18 DRM_FORMAT_XRGB1555,
19 DRM_FORMAT_XBGR1555,
20 DRM_FORMAT_RGBX5551,
21 DRM_FORMAT_BGRX5551,
22 DRM_FORMAT_RGB565,
23 DRM_FORMAT_BGR565,
24 DRM_FORMAT_XRGB8888,
25 DRM_FORMAT_XBGR8888,
26 DRM_FORMAT_RGBX8888,
27 DRM_FORMAT_BGRX8888,
28 /* TODO: non-RGB formats */
29 };
30
31 static const u32 vs_primary_formats_array_with_yuv444[] = {
32 DRM_FORMAT_XRGB4444,
33 DRM_FORMAT_XBGR4444,
34 DRM_FORMAT_RGBX4444,
35 DRM_FORMAT_BGRX4444,
36 DRM_FORMAT_XRGB1555,
37 DRM_FORMAT_XBGR1555,
38 DRM_FORMAT_RGBX5551,
39 DRM_FORMAT_BGRX5551,
40 DRM_FORMAT_RGB565,
41 DRM_FORMAT_BGR565,
42 DRM_FORMAT_XRGB8888,
43 DRM_FORMAT_XBGR8888,
44 DRM_FORMAT_RGBX8888,
45 DRM_FORMAT_BGRX8888,
46 /* TODO: non-RGB formats */
47 };
48
49 static const struct vs_formats vs_formats_no_yuv444 = {
50 .primary_array = vs_primary_formats_array_no_yuv444,
51 .primary_num = ARRAY_SIZE(vs_primary_formats_array_no_yuv444)
52 };
53
54 static const struct vs_formats vs_formats_with_yuv444 = {
55 .primary_array = vs_primary_formats_array_with_yuv444,
56 .primary_num = ARRAY_SIZE(vs_primary_formats_array_with_yuv444)
57 };
58
59 static struct vs_chip_identity vs_chip_identities[] = {
60 {
61 .model = 0x8200,
62 .revision = 0x5720,
63 .customer_id = ~0U,
64
65 .display_count = 2,
66 .max_cursor_size = 64,
67 .formats = &vs_formats_no_yuv444,
68 },
69 {
70 .model = 0x8200,
71 .revision = 0x5721,
72 .customer_id = 0x30B,
73
74 .display_count = 2,
75 .max_cursor_size = 64,
76 .formats = &vs_formats_no_yuv444,
77 },
78 {
79 .model = 0x8200,
80 .revision = 0x5720,
81 .customer_id = 0x310,
82
83 .display_count = 2,
84 .max_cursor_size = 64,
85 .formats = &vs_formats_with_yuv444,
86 },
87 {
88 .model = 0x8200,
89 .revision = 0x5720,
90 .customer_id = 0x311,
91
92 .display_count = 2,
93 .max_cursor_size = 64,
94 .formats = &vs_formats_no_yuv444,
95 },
96 };
97
vs_fill_chip_identity(struct regmap * regs,struct vs_chip_identity * ident)98 int vs_fill_chip_identity(struct regmap *regs,
99 struct vs_chip_identity *ident)
100 {
101 u32 model;
102 u32 revision;
103 u32 customer_id;
104 int i;
105
106 regmap_read(regs, VSDC_TOP_CHIP_MODEL, &model);
107 regmap_read(regs, VSDC_TOP_CHIP_REV, &revision);
108 regmap_read(regs, VSDC_TOP_CHIP_CUSTOMER_ID, &customer_id);
109
110 for (i = 0; i < ARRAY_SIZE(vs_chip_identities); i++) {
111 if (vs_chip_identities[i].model == model &&
112 vs_chip_identities[i].revision == revision &&
113 (vs_chip_identities[i].customer_id == customer_id ||
114 vs_chip_identities[i].customer_id == ~0U)) {
115 memcpy(ident, &vs_chip_identities[i], sizeof(*ident));
116 ident->customer_id = customer_id;
117 return 0;
118 }
119 }
120
121 return -EINVAL;
122 }
123