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 #include <linux/printk.h> 8 9 #include <drm/drm_fb_dma_helper.h> 10 #include <drm/drm_fourcc.h> 11 #include <drm/drm_gem_dma_helper.h> 12 13 #include "vs_plane.h" 14 15 void drm_format_to_vs_format(u32 drm_format, struct vs_format *vs_format) 16 { 17 switch (drm_format) { 18 case DRM_FORMAT_XRGB4444: 19 case DRM_FORMAT_RGBX4444: 20 case DRM_FORMAT_XBGR4444: 21 case DRM_FORMAT_BGRX4444: 22 vs_format->color = VSDC_COLOR_FORMAT_X4R4G4B4; 23 break; 24 case DRM_FORMAT_ARGB4444: 25 case DRM_FORMAT_RGBA4444: 26 case DRM_FORMAT_ABGR4444: 27 case DRM_FORMAT_BGRA4444: 28 vs_format->color = VSDC_COLOR_FORMAT_A4R4G4B4; 29 break; 30 case DRM_FORMAT_XRGB1555: 31 case DRM_FORMAT_RGBX5551: 32 case DRM_FORMAT_XBGR1555: 33 case DRM_FORMAT_BGRX5551: 34 vs_format->color = VSDC_COLOR_FORMAT_X1R5G5B5; 35 break; 36 case DRM_FORMAT_ARGB1555: 37 case DRM_FORMAT_RGBA5551: 38 case DRM_FORMAT_ABGR1555: 39 case DRM_FORMAT_BGRA5551: 40 vs_format->color = VSDC_COLOR_FORMAT_A1R5G5B5; 41 break; 42 case DRM_FORMAT_RGB565: 43 case DRM_FORMAT_BGR565: 44 vs_format->color = VSDC_COLOR_FORMAT_R5G6B5; 45 break; 46 case DRM_FORMAT_XRGB8888: 47 case DRM_FORMAT_RGBX8888: 48 case DRM_FORMAT_XBGR8888: 49 case DRM_FORMAT_BGRX8888: 50 vs_format->color = VSDC_COLOR_FORMAT_X8R8G8B8; 51 break; 52 case DRM_FORMAT_ARGB8888: 53 case DRM_FORMAT_RGBA8888: 54 case DRM_FORMAT_ABGR8888: 55 case DRM_FORMAT_BGRA8888: 56 vs_format->color = VSDC_COLOR_FORMAT_A8R8G8B8; 57 break; 58 case DRM_FORMAT_ARGB2101010: 59 case DRM_FORMAT_RGBA1010102: 60 case DRM_FORMAT_ABGR2101010: 61 case DRM_FORMAT_BGRA1010102: 62 vs_format->color = VSDC_COLOR_FORMAT_A2R10G10B10; 63 break; 64 default: 65 pr_warn("Unexpected drm format!\n"); 66 } 67 68 switch (drm_format) { 69 case DRM_FORMAT_RGBX4444: 70 case DRM_FORMAT_RGBA4444: 71 case DRM_FORMAT_RGBX5551: 72 case DRM_FORMAT_RGBA5551: 73 case DRM_FORMAT_RGBX8888: 74 case DRM_FORMAT_RGBA8888: 75 case DRM_FORMAT_RGBA1010102: 76 vs_format->swizzle = VSDC_SWIZZLE_RGBA; 77 break; 78 case DRM_FORMAT_XBGR4444: 79 case DRM_FORMAT_ABGR4444: 80 case DRM_FORMAT_XBGR1555: 81 case DRM_FORMAT_ABGR1555: 82 case DRM_FORMAT_BGR565: 83 case DRM_FORMAT_XBGR8888: 84 case DRM_FORMAT_ABGR8888: 85 case DRM_FORMAT_ABGR2101010: 86 vs_format->swizzle = VSDC_SWIZZLE_ABGR; 87 break; 88 case DRM_FORMAT_BGRX4444: 89 case DRM_FORMAT_BGRA4444: 90 case DRM_FORMAT_BGRX5551: 91 case DRM_FORMAT_BGRA5551: 92 case DRM_FORMAT_BGRX8888: 93 case DRM_FORMAT_BGRA8888: 94 case DRM_FORMAT_BGRA1010102: 95 vs_format->swizzle = VSDC_SWIZZLE_BGRA; 96 break; 97 default: 98 /* N/A for YUV formats */ 99 vs_format->swizzle = VSDC_SWIZZLE_ARGB; 100 } 101 102 /* N/A for non-YUV formats */ 103 vs_format->uv_swizzle = false; 104 } 105 106 dma_addr_t vs_fb_get_dma_addr(struct drm_framebuffer *fb, 107 const struct drm_rect *src_rect) 108 { 109 struct drm_gem_dma_object *gem; 110 dma_addr_t dma_addr; 111 112 /* Get the physical address of the buffer in memory */ 113 gem = drm_fb_dma_get_gem_obj(fb, 0); 114 115 /* Compute the start of the displayed memory */ 116 dma_addr = gem->dma_addr + fb->offsets[0]; 117 118 /* Fixup framebuffer address for src coordinates */ 119 dma_addr += drm_format_info_min_pitch(fb->format, 0, 120 src_rect->x1 >> 16); 121 dma_addr += (src_rect->y1 >> 16) * fb->pitches[0]; 122 123 return dma_addr; 124 } 125