cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

sprd_drm.c (4732B)


      1// SPDX-License-Identifier: GPL-2.0
      2/*
      3 * Copyright (C) 2020 Unisoc Inc.
      4 */
      5
      6#include <linux/component.h>
      7#include <linux/dma-mapping.h>
      8#include <linux/module.h>
      9#include <linux/mutex.h>
     10#include <linux/of_graph.h>
     11#include <linux/of_platform.h>
     12
     13#include <drm/drm_atomic_helper.h>
     14#include <drm/drm_crtc_helper.h>
     15#include <drm/drm_drv.h>
     16#include <drm/drm_gem_cma_helper.h>
     17#include <drm/drm_gem_framebuffer_helper.h>
     18#include <drm/drm_of.h>
     19#include <drm/drm_probe_helper.h>
     20#include <drm/drm_vblank.h>
     21
     22#include "sprd_drm.h"
     23
     24#define DRIVER_NAME	"sprd"
     25#define DRIVER_DESC	"Spreadtrum SoCs' DRM Driver"
     26#define DRIVER_DATE	"20200201"
     27#define DRIVER_MAJOR	1
     28#define DRIVER_MINOR	0
     29
     30static const struct drm_mode_config_helper_funcs sprd_drm_mode_config_helper = {
     31	.atomic_commit_tail = drm_atomic_helper_commit_tail_rpm,
     32};
     33
     34static const struct drm_mode_config_funcs sprd_drm_mode_config_funcs = {
     35	.fb_create = drm_gem_fb_create,
     36	.atomic_check = drm_atomic_helper_check,
     37	.atomic_commit = drm_atomic_helper_commit,
     38};
     39
     40static void sprd_drm_mode_config_init(struct drm_device *drm)
     41{
     42	drm->mode_config.min_width = 0;
     43	drm->mode_config.min_height = 0;
     44	drm->mode_config.max_width = 8192;
     45	drm->mode_config.max_height = 8192;
     46
     47	drm->mode_config.funcs = &sprd_drm_mode_config_funcs;
     48	drm->mode_config.helper_private = &sprd_drm_mode_config_helper;
     49}
     50
     51DEFINE_DRM_GEM_CMA_FOPS(sprd_drm_fops);
     52
     53static struct drm_driver sprd_drm_drv = {
     54	.driver_features	= DRIVER_GEM | DRIVER_MODESET | DRIVER_ATOMIC,
     55	.fops			= &sprd_drm_fops,
     56
     57	/* GEM Operations */
     58	DRM_GEM_CMA_DRIVER_OPS,
     59
     60	.name			= DRIVER_NAME,
     61	.desc			= DRIVER_DESC,
     62	.date			= DRIVER_DATE,
     63	.major			= DRIVER_MAJOR,
     64	.minor			= DRIVER_MINOR,
     65};
     66
     67static int sprd_drm_bind(struct device *dev)
     68{
     69	struct platform_device *pdev = to_platform_device(dev);
     70	struct drm_device *drm;
     71	struct sprd_drm *sprd;
     72	int ret;
     73
     74	sprd = devm_drm_dev_alloc(dev, &sprd_drm_drv, struct sprd_drm, drm);
     75	if (IS_ERR(sprd))
     76		return PTR_ERR(sprd);
     77
     78	drm = &sprd->drm;
     79	platform_set_drvdata(pdev, drm);
     80
     81	ret = drmm_mode_config_init(drm);
     82	if (ret)
     83		return ret;
     84
     85	sprd_drm_mode_config_init(drm);
     86
     87	/* bind and init sub drivers */
     88	ret = component_bind_all(drm->dev, drm);
     89	if (ret) {
     90		drm_err(drm, "failed to bind all component.\n");
     91		return ret;
     92	}
     93
     94	/* vblank init */
     95	ret = drm_vblank_init(drm, drm->mode_config.num_crtc);
     96	if (ret) {
     97		drm_err(drm, "failed to initialize vblank.\n");
     98		goto err_unbind_all;
     99	}
    100
    101	/* reset all the states of crtc/plane/encoder/connector */
    102	drm_mode_config_reset(drm);
    103
    104	/* init kms poll for handling hpd */
    105	drm_kms_helper_poll_init(drm);
    106
    107	ret = drm_dev_register(drm, 0);
    108	if (ret < 0)
    109		goto err_kms_helper_poll_fini;
    110
    111	return 0;
    112
    113err_kms_helper_poll_fini:
    114	drm_kms_helper_poll_fini(drm);
    115err_unbind_all:
    116	component_unbind_all(drm->dev, drm);
    117	return ret;
    118}
    119
    120static void sprd_drm_unbind(struct device *dev)
    121{
    122	struct drm_device *drm = dev_get_drvdata(dev);
    123
    124	drm_dev_unregister(drm);
    125
    126	drm_kms_helper_poll_fini(drm);
    127
    128	component_unbind_all(drm->dev, drm);
    129}
    130
    131static const struct component_master_ops drm_component_ops = {
    132	.bind = sprd_drm_bind,
    133	.unbind = sprd_drm_unbind,
    134};
    135
    136static int sprd_drm_probe(struct platform_device *pdev)
    137{
    138	return drm_of_component_probe(&pdev->dev, component_compare_of, &drm_component_ops);
    139}
    140
    141static int sprd_drm_remove(struct platform_device *pdev)
    142{
    143	component_master_del(&pdev->dev, &drm_component_ops);
    144	return 0;
    145}
    146
    147static void sprd_drm_shutdown(struct platform_device *pdev)
    148{
    149	struct drm_device *drm = platform_get_drvdata(pdev);
    150
    151	if (!drm) {
    152		dev_warn(&pdev->dev, "drm device is not available, no shutdown\n");
    153		return;
    154	}
    155
    156	drm_atomic_helper_shutdown(drm);
    157}
    158
    159static const struct of_device_id drm_match_table[] = {
    160	{ .compatible = "sprd,display-subsystem", },
    161	{ /* sentinel */ },
    162};
    163MODULE_DEVICE_TABLE(of, drm_match_table);
    164
    165static struct platform_driver sprd_drm_driver = {
    166	.probe = sprd_drm_probe,
    167	.remove = sprd_drm_remove,
    168	.shutdown = sprd_drm_shutdown,
    169	.driver = {
    170		.name = "sprd-drm-drv",
    171		.of_match_table = drm_match_table,
    172	},
    173};
    174
    175static struct platform_driver *sprd_drm_drivers[]  = {
    176	&sprd_drm_driver,
    177	&sprd_dpu_driver,
    178	&sprd_dsi_driver,
    179};
    180
    181static int __init sprd_drm_init(void)
    182{
    183	if (drm_firmware_drivers_only())
    184		return -ENODEV;
    185
    186	return platform_register_drivers(sprd_drm_drivers,
    187					ARRAY_SIZE(sprd_drm_drivers));
    188}
    189
    190static void __exit sprd_drm_exit(void)
    191{
    192	platform_unregister_drivers(sprd_drm_drivers,
    193				    ARRAY_SIZE(sprd_drm_drivers));
    194}
    195
    196module_init(sprd_drm_init);
    197module_exit(sprd_drm_exit);
    198
    199MODULE_AUTHOR("Leon He <leon.he@unisoc.com>");
    200MODULE_AUTHOR("Kevin Tang <kevin.tang@unisoc.com>");
    201MODULE_DESCRIPTION("Unisoc DRM KMS Master Driver");
    202MODULE_LICENSE("GPL v2");