Linux Audio

Check our new training course

Loading...
   1/*
   2 * S5P/EXYNOS4 SoC series camera host interface media device driver
   3 *
   4 * Copyright (C) 2011 Samsung Electronics Co., Ltd.
   5 * Contact: Sylwester Nawrocki, <s.nawrocki@samsung.com>
   6 *
   7 * This program is free software; you can redistribute it and/or modify
   8 * it under the terms of the GNU General Public License as published
   9 * by the Free Software Foundation, either version 2 of the License,
  10 * or (at your option) any later version.
  11 */
  12
  13#include <linux/bug.h>
  14#include <linux/device.h>
  15#include <linux/errno.h>
  16#include <linux/i2c.h>
  17#include <linux/kernel.h>
  18#include <linux/list.h>
  19#include <linux/module.h>
  20#include <linux/platform_device.h>
  21#include <linux/pm_runtime.h>
  22#include <linux/types.h>
  23#include <linux/slab.h>
  24#include <media/v4l2-ctrls.h>
  25#include <media/media-device.h>
  26
  27#include "fimc-core.h"
  28#include "fimc-lite.h"
  29#include "fimc-mdevice.h"
  30#include "mipi-csis.h"
  31
  32static int __fimc_md_set_camclk(struct fimc_md *fmd,
  33				struct fimc_sensor_info *s_info,
  34				bool on);
  35/**
  36 * fimc_pipeline_prepare - update pipeline information with subdevice pointers
  37 * @fimc: fimc device terminating the pipeline
  38 *
  39 * Caller holds the graph mutex.
  40 */
  41void fimc_pipeline_prepare(struct fimc_pipeline *p, struct media_entity *me)
  42{
  43	struct media_pad *pad = &me->pads[0];
  44	struct v4l2_subdev *sd;
  45	int i;
  46
  47	for (i = 0; i < IDX_MAX; i++)
  48		p->subdevs[i] = NULL;
  49
  50	while (1) {
  51		if (!(pad->flags & MEDIA_PAD_FL_SINK))
  52			break;
  53
  54		/* source pad */
  55		pad = media_entity_remote_source(pad);
  56		if (pad == NULL ||
  57		    media_entity_type(pad->entity) != MEDIA_ENT_T_V4L2_SUBDEV)
  58			break;
  59
  60		sd = media_entity_to_v4l2_subdev(pad->entity);
  61
  62		switch (sd->grp_id) {
  63		case SENSOR_GROUP_ID:
  64			p->subdevs[IDX_SENSOR] = sd;
  65			break;
  66		case CSIS_GROUP_ID:
  67			p->subdevs[IDX_CSIS] = sd;
  68			break;
  69		case FLITE_GROUP_ID:
  70			p->subdevs[IDX_FLITE] = sd;
  71			break;
  72		case FIMC_GROUP_ID:
  73			/* No need to control FIMC subdev through subdev ops */
  74			break;
  75		default:
  76			pr_warn("%s: Unknown subdev grp_id: %#x\n",
  77				__func__, sd->grp_id);
  78		}
  79		/* sink pad */
  80		pad = &sd->entity.pads[0];
  81	}
  82}
  83
  84/**
  85 * __subdev_set_power - change power state of a single subdev
  86 * @sd: subdevice to change power state for
  87 * @on: 1 to enable power or 0 to disable
  88 *
  89 * Return result of s_power subdev operation or -ENXIO if sd argument
  90 * is NULL. Return 0 if the subdevice does not implement s_power.
  91 */
  92static int __subdev_set_power(struct v4l2_subdev *sd, int on)
  93{
  94	int *use_count;
  95	int ret;
  96
  97	if (sd == NULL)
  98		return -ENXIO;
  99
 100	use_count = &sd->entity.use_count;
 101	if (on && (*use_count)++ > 0)
 102		return 0;
 103	else if (!on && (*use_count == 0 || --(*use_count) > 0))
 104		return 0;
 105	ret = v4l2_subdev_call(sd, core, s_power, on);
 106
 107	return ret != -ENOIOCTLCMD ? ret : 0;
 108}
 109
 110/**
 111 * fimc_pipeline_s_power - change power state of all pipeline subdevs
 112 * @fimc: fimc device terminating the pipeline
 113 * @state: true to power on, false to power off
 114 *
 115 * Needs to be called with the graph mutex held.
 116 */
 117int fimc_pipeline_s_power(struct fimc_pipeline *p, bool state)
 118{
 119	unsigned int i;
 120	int ret;
 121
 122	if (p->subdevs[IDX_SENSOR] == NULL)
 123		return -ENXIO;
 124
 125	for (i = 0; i < IDX_MAX; i++) {
 126		unsigned int idx = state ? (IDX_MAX - 1) - i : i;
 127
 128		ret = __subdev_set_power(p->subdevs[idx], state);
 129		if (ret < 0 && ret != -ENXIO)
 130			return ret;
 131	}
 132
 133	return 0;
 134}
 135
 136/**
 137 * __fimc_pipeline_initialize - update the pipeline information, enable power
 138 *                              of all pipeline subdevs and the sensor clock
 139 * @me: media entity to start graph walk with
 140 * @prep: true to acquire sensor (and csis) subdevs
 141 *
 142 * This function must be called with the graph mutex held.
 143 */
 144static int __fimc_pipeline_initialize(struct fimc_pipeline *p,
 145				      struct media_entity *me, bool prep)
 146{
 147	int ret;
 148
 149	if (prep)
 150		fimc_pipeline_prepare(p, me);
 151
 152	if (p->subdevs[IDX_SENSOR] == NULL)
 153		return -EINVAL;
 154
 155	ret = fimc_md_set_camclk(p->subdevs[IDX_SENSOR], true);
 156	if (ret)
 157		return ret;
 158
 159	return fimc_pipeline_s_power(p, 1);
 160}
 161
 162int fimc_pipeline_initialize(struct fimc_pipeline *p, struct media_entity *me,
 163			     bool prep)
 164{
 165	int ret;
 166
 167	mutex_lock(&me->parent->graph_mutex);
 168	ret =  __fimc_pipeline_initialize(p, me, prep);
 169	mutex_unlock(&me->parent->graph_mutex);
 170
 171	return ret;
 172}
 173EXPORT_SYMBOL_GPL(fimc_pipeline_initialize);
 174
 175/**
 176 * __fimc_pipeline_shutdown - disable the sensor clock and pipeline power
 177 * @fimc: fimc device terminating the pipeline
 178 *
 179 * Disable power of all subdevs in the pipeline and turn off the external
 180 * sensor clock.
 181 * Called with the graph mutex held.
 182 */
 183int __fimc_pipeline_shutdown(struct fimc_pipeline *p)
 184{
 185	int ret = 0;
 186
 187	if (p->subdevs[IDX_SENSOR]) {
 188		ret = fimc_pipeline_s_power(p, 0);
 189		fimc_md_set_camclk(p->subdevs[IDX_SENSOR], false);
 190	}
 191	return ret == -ENXIO ? 0 : ret;
 192}
 193
 194int fimc_pipeline_shutdown(struct fimc_pipeline *p)
 195{
 196	struct media_entity *me;
 197	int ret;
 198
 199	if (!p || !p->subdevs[IDX_SENSOR])
 200		return -EINVAL;
 201
 202	me = &p->subdevs[IDX_SENSOR]->entity;
 203	mutex_lock(&me->parent->graph_mutex);
 204	ret = __fimc_pipeline_shutdown(p);
 205	mutex_unlock(&me->parent->graph_mutex);
 206
 207	return ret;
 208}
 209EXPORT_SYMBOL_GPL(fimc_pipeline_shutdown);
 210
 211/**
 212 * fimc_pipeline_s_stream - invoke s_stream on pipeline subdevs
 213 * @pipeline: video pipeline structure
 214 * @on: passed as the s_stream call argument
 215 */
 216int fimc_pipeline_s_stream(struct fimc_pipeline *p, bool on)
 217{
 218	int i, ret;
 219
 220	if (p->subdevs[IDX_SENSOR] == NULL)
 221		return -ENODEV;
 222
 223	for (i = 0; i < IDX_MAX; i++) {
 224		unsigned int idx = on ? (IDX_MAX - 1) - i : i;
 225
 226		ret = v4l2_subdev_call(p->subdevs[idx], video, s_stream, on);
 227
 228		if (ret < 0 && ret != -ENOIOCTLCMD && ret != -ENODEV)
 229			return ret;
 230	}
 231
 232	return 0;
 233
 234}
 235EXPORT_SYMBOL_GPL(fimc_pipeline_s_stream);
 236
 237/*
 238 * Sensor subdevice helper functions
 239 */
 240static struct v4l2_subdev *fimc_md_register_sensor(struct fimc_md *fmd,
 241				   struct fimc_sensor_info *s_info)
 242{
 243	struct i2c_adapter *adapter;
 244	struct v4l2_subdev *sd = NULL;
 245
 246	if (!s_info || !fmd)
 247		return NULL;
 248
 249	adapter = i2c_get_adapter(s_info->pdata->i2c_bus_num);
 250	if (!adapter) {
 251		v4l2_warn(&fmd->v4l2_dev,
 252			  "Failed to get I2C adapter %d, deferring probe\n",
 253			  s_info->pdata->i2c_bus_num);
 254		return ERR_PTR(-EPROBE_DEFER);
 255	}
 256	sd = v4l2_i2c_new_subdev_board(&fmd->v4l2_dev, adapter,
 257				       s_info->pdata->board_info, NULL);
 258	if (IS_ERR_OR_NULL(sd)) {
 259		i2c_put_adapter(adapter);
 260		v4l2_warn(&fmd->v4l2_dev,
 261			  "Failed to acquire subdev %s, deferring probe\n",
 262			  s_info->pdata->board_info->type);
 263		return ERR_PTR(-EPROBE_DEFER);
 264	}
 265	v4l2_set_subdev_hostdata(sd, s_info);
 266	sd->grp_id = SENSOR_GROUP_ID;
 267
 268	v4l2_info(&fmd->v4l2_dev, "Registered sensor subdevice %s\n",
 269		  s_info->pdata->board_info->type);
 270	return sd;
 271}
 272
 273static void fimc_md_unregister_sensor(struct v4l2_subdev *sd)
 274{
 275	struct i2c_client *client = v4l2_get_subdevdata(sd);
 276	struct i2c_adapter *adapter;
 277
 278	if (!client)
 279		return;
 280	v4l2_device_unregister_subdev(sd);
 281	adapter = client->adapter;
 282	i2c_unregister_device(client);
 283	if (adapter)
 284		i2c_put_adapter(adapter);
 285}
 286
 287static int fimc_md_register_sensor_entities(struct fimc_md *fmd)
 288{
 289	struct s5p_platform_fimc *pdata = fmd->pdev->dev.platform_data;
 290	struct fimc_dev *fd = NULL;
 291	int num_clients, ret, i;
 292
 293	/*
 294	 * Runtime resume one of the FIMC entities to make sure
 295	 * the sclk_cam clocks are not globally disabled.
 296	 */
 297	for (i = 0; !fd && i < ARRAY_SIZE(fmd->fimc); i++)
 298		if (fmd->fimc[i])
 299			fd = fmd->fimc[i];
 300	if (!fd)
 301		return -ENXIO;
 302	ret = pm_runtime_get_sync(&fd->pdev->dev);
 303	if (ret < 0)
 304		return ret;
 305
 306	WARN_ON(pdata->num_clients > ARRAY_SIZE(fmd->sensor));
 307	num_clients = min_t(u32, pdata->num_clients, ARRAY_SIZE(fmd->sensor));
 308
 309	fmd->num_sensors = num_clients;
 310	for (i = 0; i < num_clients; i++) {
 311		struct v4l2_subdev *sd;
 312
 313		fmd->sensor[i].pdata = &pdata->isp_info[i];
 314		ret = __fimc_md_set_camclk(fmd, &fmd->sensor[i], true);
 315		if (ret)
 316			break;
 317		sd = fimc_md_register_sensor(fmd, &fmd->sensor[i]);
 318		ret = __fimc_md_set_camclk(fmd, &fmd->sensor[i], false);
 319
 320		if (!IS_ERR(sd)) {
 321			fmd->sensor[i].subdev = sd;
 322		} else {
 323			fmd->sensor[i].subdev = NULL;
 324			ret = PTR_ERR(sd);
 325			break;
 326		}
 327		if (ret)
 328			break;
 329	}
 330	pm_runtime_put(&fd->pdev->dev);
 331	return ret;
 332}
 333
 334/*
 335 * MIPI CSIS and FIMC platform devices registration.
 336 */
 337static int fimc_register_callback(struct device *dev, void *p)
 338{
 339	struct fimc_dev *fimc = dev_get_drvdata(dev);
 340	struct v4l2_subdev *sd = &fimc->vid_cap.subdev;
 341	struct fimc_md *fmd = p;
 342	int ret = 0;
 343
 344	if (!fimc || !fimc->pdev)
 345		return 0;
 346
 347	if (fimc->pdev->id < 0 || fimc->pdev->id >= FIMC_MAX_DEVS)
 348		return 0;
 349
 350	fmd->fimc[fimc->pdev->id] = fimc;
 351	sd->grp_id = FIMC_GROUP_ID;
 352
 353	ret = v4l2_device_register_subdev(&fmd->v4l2_dev, sd);
 354	if (ret) {
 355		v4l2_err(&fmd->v4l2_dev, "Failed to register FIMC.%d (%d)\n",
 356			 fimc->id, ret);
 357	}
 358
 359	return ret;
 360}
 361
 362static int fimc_lite_register_callback(struct device *dev, void *p)
 363{
 364	struct fimc_lite *fimc = dev_get_drvdata(dev);
 365	struct v4l2_subdev *sd = &fimc->subdev;
 366	struct fimc_md *fmd = p;
 367	int ret;
 368
 369	if (fimc == NULL)
 370		return 0;
 371
 372	if (fimc->index >= FIMC_LITE_MAX_DEVS)
 373		return 0;
 374
 375	fmd->fimc_lite[fimc->index] = fimc;
 376	sd->grp_id = FLITE_GROUP_ID;
 377
 378	ret = v4l2_device_register_subdev(&fmd->v4l2_dev, sd);
 379	if (ret) {
 380		v4l2_err(&fmd->v4l2_dev,
 381			 "Failed to register FIMC-LITE.%d (%d)\n",
 382			 fimc->index, ret);
 383	}
 384	return ret;
 385}
 386
 387static int csis_register_callback(struct device *dev, void *p)
 388{
 389	struct v4l2_subdev *sd = dev_get_drvdata(dev);
 390	struct platform_device *pdev;
 391	struct fimc_md *fmd = p;
 392	int id, ret;
 393
 394	if (!sd)
 395		return 0;
 396	pdev = v4l2_get_subdevdata(sd);
 397	if (!pdev || pdev->id < 0 || pdev->id >= CSIS_MAX_ENTITIES)
 398		return 0;
 399	v4l2_info(sd, "csis%d sd: %s\n", pdev->id, sd->name);
 400
 401	id = pdev->id < 0 ? 0 : pdev->id;
 402	fmd->csis[id].sd = sd;
 403	sd->grp_id = CSIS_GROUP_ID;
 404	ret = v4l2_device_register_subdev(&fmd->v4l2_dev, sd);
 405	if (ret)
 406		v4l2_err(&fmd->v4l2_dev,
 407			 "Failed to register CSIS subdevice: %d\n", ret);
 408	return ret;
 409}
 410
 411/**
 412 * fimc_md_register_platform_entities - register FIMC and CSIS media entities
 413 */
 414static int fimc_md_register_platform_entities(struct fimc_md *fmd)
 415{
 416	struct s5p_platform_fimc *pdata = fmd->pdev->dev.platform_data;
 417	struct device_driver *driver;
 418	int ret, i;
 419
 420	driver = driver_find(FIMC_MODULE_NAME, &platform_bus_type);
 421	if (!driver) {
 422		v4l2_warn(&fmd->v4l2_dev,
 423			 "%s driver not found, deffering probe\n",
 424			 FIMC_MODULE_NAME);
 425		return -EPROBE_DEFER;
 426	}
 427
 428	ret = driver_for_each_device(driver, NULL, fmd,
 429				     fimc_register_callback);
 430	if (ret)
 431		return ret;
 432
 433	driver = driver_find(FIMC_LITE_DRV_NAME, &platform_bus_type);
 434	if (driver && try_module_get(driver->owner)) {
 435		ret = driver_for_each_device(driver, NULL, fmd,
 436					     fimc_lite_register_callback);
 437		if (ret)
 438			return ret;
 439		module_put(driver->owner);
 440	}
 441	/*
 442	 * Check if there is any sensor on the MIPI-CSI2 bus and
 443	 * if not skip the s5p-csis module loading.
 444	 */
 445	if (pdata == NULL)
 446		return 0;
 447	for (i = 0; i < pdata->num_clients; i++) {
 448		if (pdata->isp_info[i].bus_type == FIMC_MIPI_CSI2) {
 449			ret = 1;
 450			break;
 451		}
 452	}
 453	if (!ret)
 454		return 0;
 455
 456	driver = driver_find(CSIS_DRIVER_NAME, &platform_bus_type);
 457	if (!driver || !try_module_get(driver->owner)) {
 458		v4l2_warn(&fmd->v4l2_dev,
 459			 "%s driver not found, deffering probe\n",
 460			 CSIS_DRIVER_NAME);
 461		return -EPROBE_DEFER;
 462	}
 463
 464	return driver_for_each_device(driver, NULL, fmd,
 465				      csis_register_callback);
 466}
 467
 468static void fimc_md_unregister_entities(struct fimc_md *fmd)
 469{
 470	int i;
 471
 472	for (i = 0; i < FIMC_MAX_DEVS; i++) {
 473		if (fmd->fimc[i] == NULL)
 474			continue;
 475		v4l2_device_unregister_subdev(&fmd->fimc[i]->vid_cap.subdev);
 476		fmd->fimc[i] = NULL;
 477	}
 478	for (i = 0; i < FIMC_LITE_MAX_DEVS; i++) {
 479		if (fmd->fimc_lite[i] == NULL)
 480			continue;
 481		v4l2_device_unregister_subdev(&fmd->fimc_lite[i]->subdev);
 482		fmd->fimc_lite[i] = NULL;
 483	}
 484	for (i = 0; i < CSIS_MAX_ENTITIES; i++) {
 485		if (fmd->csis[i].sd == NULL)
 486			continue;
 487		v4l2_device_unregister_subdev(fmd->csis[i].sd);
 488		module_put(fmd->csis[i].sd->owner);
 489		fmd->csis[i].sd = NULL;
 490	}
 491	for (i = 0; i < fmd->num_sensors; i++) {
 492		if (fmd->sensor[i].subdev == NULL)
 493			continue;
 494		fimc_md_unregister_sensor(fmd->sensor[i].subdev);
 495		fmd->sensor[i].subdev = NULL;
 496	}
 497}
 498
 499/**
 500 * __fimc_md_create_fimc_links - create links to all FIMC entities
 501 * @fmd: fimc media device
 502 * @source: the source entity to create links to all fimc entities from
 503 * @sensor: sensor subdev linked to FIMC[fimc_id] entity, may be null
 504 * @pad: the source entity pad index
 505 * @link_mask: bitmask of the fimc devices for which link should be enabled
 506 */
 507static int __fimc_md_create_fimc_sink_links(struct fimc_md *fmd,
 508					    struct media_entity *source,
 509					    struct v4l2_subdev *sensor,
 510					    int pad, int link_mask)
 511{
 512	struct fimc_sensor_info *s_info;
 513	struct media_entity *sink;
 514	unsigned int flags = 0;
 515	int ret, i;
 516
 517	for (i = 0; i < FIMC_MAX_DEVS; i++) {
 518		if (!fmd->fimc[i])
 519			continue;
 520		/*
 521		 * Some FIMC variants are not fitted with camera capture
 522		 * interface. Skip creating a link from sensor for those.
 523		 */
 524		if (!fmd->fimc[i]->variant->has_cam_if)
 525			continue;
 526
 527		flags = ((1 << i) & link_mask) ? MEDIA_LNK_FL_ENABLED : 0;
 528
 529		sink = &fmd->fimc[i]->vid_cap.subdev.entity;
 530		ret = media_entity_create_link(source, pad, sink,
 531					      FIMC_SD_PAD_SINK, flags);
 532		if (ret)
 533			return ret;
 534
 535		/* Notify FIMC capture subdev entity */
 536		ret = media_entity_call(sink, link_setup, &sink->pads[0],
 537					&source->pads[pad], flags);
 538		if (ret)
 539			break;
 540
 541		v4l2_info(&fmd->v4l2_dev, "created link [%s] %c> [%s]",
 542			  source->name, flags ? '=' : '-', sink->name);
 543
 544		if (flags == 0 || sensor == NULL)
 545			continue;
 546		s_info = v4l2_get_subdev_hostdata(sensor);
 547		if (!WARN_ON(s_info == NULL)) {
 548			unsigned long irq_flags;
 549			spin_lock_irqsave(&fmd->slock, irq_flags);
 550			s_info->host = fmd->fimc[i];
 551			spin_unlock_irqrestore(&fmd->slock, irq_flags);
 552		}
 553	}
 554
 555	for (i = 0; i < FIMC_LITE_MAX_DEVS; i++) {
 556		if (!fmd->fimc_lite[i])
 557			continue;
 558
 559		if (link_mask & (1 << (i + FIMC_MAX_DEVS)))
 560			flags = MEDIA_LNK_FL_ENABLED;
 561		else
 562			flags = 0;
 563
 564		sink = &fmd->fimc_lite[i]->subdev.entity;
 565		ret = media_entity_create_link(source, pad, sink,
 566					       FLITE_SD_PAD_SINK, flags);
 567		if (ret)
 568			return ret;
 569
 570		/* Notify FIMC-LITE subdev entity */
 571		ret = media_entity_call(sink, link_setup, &sink->pads[0],
 572					&source->pads[pad], flags);
 573		if (ret)
 574			break;
 575
 576		v4l2_info(&fmd->v4l2_dev, "created link [%s] %c> [%s]",
 577			  source->name, flags ? '=' : '-', sink->name);
 578	}
 579	return 0;
 580}
 581
 582/* Create links from FIMC-LITE source pads to other entities */
 583static int __fimc_md_create_flite_source_links(struct fimc_md *fmd)
 584{
 585	struct media_entity *source, *sink;
 586	unsigned int flags = MEDIA_LNK_FL_ENABLED;
 587	int i, ret;
 588
 589	for (i = 0; i < FIMC_LITE_MAX_DEVS; i++) {
 590		struct fimc_lite *fimc = fmd->fimc_lite[i];
 591		if (fimc == NULL)
 592			continue;
 593		source = &fimc->subdev.entity;
 594		sink = &fimc->vfd->entity;
 595		/* FIMC-LITE's subdev and video node */
 596		ret = media_entity_create_link(source, FIMC_SD_PAD_SOURCE,
 597					       sink, 0, flags);
 598		if (ret)
 599			break;
 600		/* TODO: create links to other entities */
 601	}
 602
 603	return ret;
 604}
 605
 606/**
 607 * fimc_md_create_links - create default links between registered entities
 608 *
 609 * Parallel interface sensor entities are connected directly to FIMC capture
 610 * entities. The sensors using MIPI CSIS bus are connected through immutable
 611 * link with CSI receiver entity specified by mux_id. Any registered CSIS
 612 * entity has a link to each registered FIMC capture entity. Enabled links
 613 * are created by default between each subsequent registered sensor and
 614 * subsequent FIMC capture entity. The number of default active links is
 615 * determined by the number of available sensors or FIMC entities,
 616 * whichever is less.
 617 */
 618static int fimc_md_create_links(struct fimc_md *fmd)
 619{
 620	struct v4l2_subdev *sensor, *csis;
 621	struct s5p_fimc_isp_info *pdata;
 622	struct fimc_sensor_info *s_info;
 623	struct media_entity *source, *sink;
 624	int i, pad, fimc_id = 0, ret = 0;
 625	u32 flags, link_mask = 0;
 626
 627	for (i = 0; i < fmd->num_sensors; i++) {
 628		if (fmd->sensor[i].subdev == NULL)
 629			continue;
 630
 631		sensor = fmd->sensor[i].subdev;
 632		s_info = v4l2_get_subdev_hostdata(sensor);
 633		if (!s_info || !s_info->pdata)
 634			continue;
 635
 636		source = NULL;
 637		pdata = s_info->pdata;
 638
 639		switch (pdata->bus_type) {
 640		case FIMC_MIPI_CSI2:
 641			if (WARN(pdata->mux_id >= CSIS_MAX_ENTITIES,
 642				"Wrong CSI channel id: %d\n", pdata->mux_id))
 643				return -EINVAL;
 644
 645			csis = fmd->csis[pdata->mux_id].sd;
 646			if (WARN(csis == NULL,
 647				 "MIPI-CSI interface specified "
 648				 "but s5p-csis module is not loaded!\n"))
 649				return -EINVAL;
 650
 651			ret = media_entity_create_link(&sensor->entity, 0,
 652					      &csis->entity, CSIS_PAD_SINK,
 653					      MEDIA_LNK_FL_IMMUTABLE |
 654					      MEDIA_LNK_FL_ENABLED);
 655			if (ret)
 656				return ret;
 657
 658			v4l2_info(&fmd->v4l2_dev, "created link [%s] => [%s]",
 659				  sensor->entity.name, csis->entity.name);
 660
 661			source = NULL;
 662			break;
 663
 664		case FIMC_ITU_601...FIMC_ITU_656:
 665			source = &sensor->entity;
 666			pad = 0;
 667			break;
 668
 669		default:
 670			v4l2_err(&fmd->v4l2_dev, "Wrong bus_type: %x\n",
 671				 pdata->bus_type);
 672			return -EINVAL;
 673		}
 674		if (source == NULL)
 675			continue;
 676
 677		link_mask = 1 << fimc_id++;
 678		ret = __fimc_md_create_fimc_sink_links(fmd, source, sensor,
 679						       pad, link_mask);
 680	}
 681
 682	for (i = 0; i < ARRAY_SIZE(fmd->csis); i++) {
 683		if (fmd->csis[i].sd == NULL)
 684			continue;
 685		source = &fmd->csis[i].sd->entity;
 686		pad = CSIS_PAD_SOURCE;
 687
 688		link_mask = 1 << fimc_id++;
 689		ret = __fimc_md_create_fimc_sink_links(fmd, source, NULL,
 690						       pad, link_mask);
 691	}
 692
 693	/* Create immutable links between each FIMC's subdev and video node */
 694	flags = MEDIA_LNK_FL_IMMUTABLE | MEDIA_LNK_FL_ENABLED;
 695	for (i = 0; i < FIMC_MAX_DEVS; i++) {
 696		if (!fmd->fimc[i])
 697			continue;
 698		source = &fmd->fimc[i]->vid_cap.subdev.entity;
 699		sink = &fmd->fimc[i]->vid_cap.vfd->entity;
 700		ret = media_entity_create_link(source, FIMC_SD_PAD_SOURCE,
 701					      sink, 0, flags);
 702		if (ret)
 703			break;
 704	}
 705
 706	return __fimc_md_create_flite_source_links(fmd);
 707}
 708
 709/*
 710 * The peripheral sensor clock management.
 711 */
 712static int fimc_md_get_clocks(struct fimc_md *fmd)
 713{
 714	char clk_name[32];
 715	struct clk *clock;
 716	int i;
 717
 718	for (i = 0; i < FIMC_MAX_CAMCLKS; i++) {
 719		snprintf(clk_name, sizeof(clk_name), "sclk_cam%u", i);
 720		clock = clk_get(NULL, clk_name);
 721		if (IS_ERR_OR_NULL(clock)) {
 722			v4l2_err(&fmd->v4l2_dev, "Failed to get clock: %s",
 723				  clk_name);
 724			return -ENXIO;
 725		}
 726		fmd->camclk[i].clock = clock;
 727	}
 728	return 0;
 729}
 730
 731static void fimc_md_put_clocks(struct fimc_md *fmd)
 732{
 733	int i = FIMC_MAX_CAMCLKS;
 734
 735	while (--i >= 0) {
 736		if (IS_ERR_OR_NULL(fmd->camclk[i].clock))
 737			continue;
 738		clk_put(fmd->camclk[i].clock);
 739		fmd->camclk[i].clock = NULL;
 740	}
 741}
 742
 743static int __fimc_md_set_camclk(struct fimc_md *fmd,
 744				struct fimc_sensor_info *s_info,
 745				bool on)
 746{
 747	struct s5p_fimc_isp_info *pdata = s_info->pdata;
 748	struct fimc_camclk_info *camclk;
 749	int ret = 0;
 750
 751	if (WARN_ON(pdata->clk_id >= FIMC_MAX_CAMCLKS) || fmd == NULL)
 752		return -EINVAL;
 753
 754	camclk = &fmd->camclk[pdata->clk_id];
 755
 756	dbg("camclk %d, f: %lu, use_count: %d, on: %d",
 757	    pdata->clk_id, pdata->clk_frequency, camclk->use_count, on);
 758
 759	if (on) {
 760		if (camclk->use_count > 0 &&
 761		    camclk->frequency != pdata->clk_frequency)
 762			return -EINVAL;
 763
 764		if (camclk->use_count++ == 0) {
 765			clk_set_rate(camclk->clock, pdata->clk_frequency);
 766			camclk->frequency = pdata->clk_frequency;
 767			ret = clk_enable(camclk->clock);
 768			dbg("Enabled camclk %d: f: %lu", pdata->clk_id,
 769			    clk_get_rate(camclk->clock));
 770		}
 771		return ret;
 772	}
 773
 774	if (WARN_ON(camclk->use_count == 0))
 775		return 0;
 776
 777	if (--camclk->use_count == 0) {
 778		clk_disable(camclk->clock);
 779		dbg("Disabled camclk %d", pdata->clk_id);
 780	}
 781	return ret;
 782}
 783
 784/**
 785 * fimc_md_set_camclk - peripheral sensor clock setup
 786 * @sd: sensor subdev to configure sclk_cam clock for
 787 * @on: 1 to enable or 0 to disable the clock
 788 *
 789 * There are 2 separate clock outputs available in the SoC for external
 790 * image processors. These clocks are shared between all registered FIMC
 791 * devices to which sensors can be attached, either directly or through
 792 * the MIPI CSI receiver. The clock is allowed here to be used by
 793 * multiple sensors concurrently if they use same frequency.
 794 * This function should only be called when the graph mutex is held.
 795 */
 796int fimc_md_set_camclk(struct v4l2_subdev *sd, bool on)
 797{
 798	struct fimc_sensor_info *s_info = v4l2_get_subdev_hostdata(sd);
 799	struct fimc_md *fmd = entity_to_fimc_mdev(&sd->entity);
 800
 801	return __fimc_md_set_camclk(fmd, s_info, on);
 802}
 803
 804static int fimc_md_link_notify(struct media_pad *source,
 805			       struct media_pad *sink, u32 flags)
 806{
 807	struct fimc_lite *fimc_lite = NULL;
 808	struct fimc_dev *fimc = NULL;
 809	struct fimc_pipeline *pipeline;
 810	struct v4l2_subdev *sd;
 811	int ret = 0;
 812
 813	if (media_entity_type(sink->entity) != MEDIA_ENT_T_V4L2_SUBDEV)
 814		return 0;
 815
 816	sd = media_entity_to_v4l2_subdev(sink->entity);
 817
 818	switch (sd->grp_id) {
 819	case FLITE_GROUP_ID:
 820		fimc_lite = v4l2_get_subdevdata(sd);
 821		pipeline = &fimc_lite->pipeline;
 822		break;
 823	case FIMC_GROUP_ID:
 824		fimc = v4l2_get_subdevdata(sd);
 825		pipeline = &fimc->pipeline;
 826		break;
 827	default:
 828		return 0;
 829	}
 830
 831	if (!(flags & MEDIA_LNK_FL_ENABLED)) {
 832		ret = __fimc_pipeline_shutdown(pipeline);
 833		pipeline->subdevs[IDX_SENSOR] = NULL;
 834		pipeline->subdevs[IDX_CSIS] = NULL;
 835
 836		if (fimc) {
 837			mutex_lock(&fimc->lock);
 838			fimc_ctrls_delete(fimc->vid_cap.ctx);
 839			mutex_unlock(&fimc->lock);
 840		}
 841		return ret;
 842	}
 843	/*
 844	 * Link activation. Enable power of pipeline elements only if the
 845	 * pipeline is already in use, i.e. its video node is opened.
 846	 * Recreate the controls destroyed during the link deactivation.
 847	 */
 848	if (fimc) {
 849		mutex_lock(&fimc->lock);
 850		if (fimc->vid_cap.refcnt > 0) {
 851			ret = __fimc_pipeline_initialize(pipeline,
 852							 source->entity, true);
 853		if (!ret)
 854			ret = fimc_capture_ctrls_create(fimc);
 855		}
 856		mutex_unlock(&fimc->lock);
 857	} else {
 858		mutex_lock(&fimc_lite->lock);
 859		if (fimc_lite->ref_count > 0) {
 860			ret = __fimc_pipeline_initialize(pipeline,
 861							 source->entity, true);
 862		}
 863		mutex_unlock(&fimc_lite->lock);
 864	}
 865	return ret ? -EPIPE : ret;
 866}
 867
 868static ssize_t fimc_md_sysfs_show(struct device *dev,
 869				  struct device_attribute *attr, char *buf)
 870{
 871	struct platform_device *pdev = to_platform_device(dev);
 872	struct fimc_md *fmd = platform_get_drvdata(pdev);
 873
 874	if (fmd->user_subdev_api)
 875		return strlcpy(buf, "Sub-device API (sub-dev)\n", PAGE_SIZE);
 876
 877	return strlcpy(buf, "V4L2 video node only API (vid-dev)\n", PAGE_SIZE);
 878}
 879
 880static ssize_t fimc_md_sysfs_store(struct device *dev,
 881				   struct device_attribute *attr,
 882				   const char *buf, size_t count)
 883{
 884	struct platform_device *pdev = to_platform_device(dev);
 885	struct fimc_md *fmd = platform_get_drvdata(pdev);
 886	bool subdev_api;
 887	int i;
 888
 889	if (!strcmp(buf, "vid-dev\n"))
 890		subdev_api = false;
 891	else if (!strcmp(buf, "sub-dev\n"))
 892		subdev_api = true;
 893	else
 894		return count;
 895
 896	fmd->user_subdev_api = subdev_api;
 897	for (i = 0; i < FIMC_MAX_DEVS; i++)
 898		if (fmd->fimc[i])
 899			fmd->fimc[i]->vid_cap.user_subdev_api = subdev_api;
 900	return count;
 901}
 902/*
 903 * This device attribute is to select video pipeline configuration method.
 904 * There are following valid values:
 905 *  vid-dev - for V4L2 video node API only, subdevice will be configured
 906 *  by the host driver.
 907 *  sub-dev - for media controller API, subdevs must be configured in user
 908 *  space before starting streaming.
 909 */
 910static DEVICE_ATTR(subdev_conf_mode, S_IWUSR | S_IRUGO,
 911		   fimc_md_sysfs_show, fimc_md_sysfs_store);
 912
 913static int fimc_md_probe(struct platform_device *pdev)
 914{
 915	struct v4l2_device *v4l2_dev;
 916	struct fimc_md *fmd;
 917	int ret;
 918
 919	fmd = devm_kzalloc(&pdev->dev, sizeof(*fmd), GFP_KERNEL);
 920	if (!fmd)
 921		return -ENOMEM;
 922
 923	spin_lock_init(&fmd->slock);
 924	fmd->pdev = pdev;
 925
 926	strlcpy(fmd->media_dev.model, "SAMSUNG S5P FIMC",
 927		sizeof(fmd->media_dev.model));
 928	fmd->media_dev.link_notify = fimc_md_link_notify;
 929	fmd->media_dev.dev = &pdev->dev;
 930
 931	v4l2_dev = &fmd->v4l2_dev;
 932	v4l2_dev->mdev = &fmd->media_dev;
 933	v4l2_dev->notify = fimc_sensor_notify;
 934	snprintf(v4l2_dev->name, sizeof(v4l2_dev->name), "%s",
 935		 dev_name(&pdev->dev));
 936
 937	ret = v4l2_device_register(&pdev->dev, &fmd->v4l2_dev);
 938	if (ret < 0) {
 939		v4l2_err(v4l2_dev, "Failed to register v4l2_device: %d\n", ret);
 940		return ret;
 941	}
 942	ret = media_device_register(&fmd->media_dev);
 943	if (ret < 0) {
 944		v4l2_err(v4l2_dev, "Failed to register media device: %d\n", ret);
 945		goto err_md;
 946	}
 947	ret = fimc_md_get_clocks(fmd);
 948	if (ret)
 949		goto err_clk;
 950
 951	fmd->user_subdev_api = false;
 952
 953	/* Protect the media graph while we're registering entities */
 954	mutex_lock(&fmd->media_dev.graph_mutex);
 955
 956	ret = fimc_md_register_platform_entities(fmd);
 957	if (ret)
 958		goto err_unlock;
 959
 960	if (pdev->dev.platform_data) {
 961		ret = fimc_md_register_sensor_entities(fmd);
 962		if (ret)
 963			goto err_unlock;
 964	}
 965	ret = fimc_md_create_links(fmd);
 966	if (ret)
 967		goto err_unlock;
 968	ret = v4l2_device_register_subdev_nodes(&fmd->v4l2_dev);
 969	if (ret)
 970		goto err_unlock;
 971
 972	ret = device_create_file(&pdev->dev, &dev_attr_subdev_conf_mode);
 973	if (ret)
 974		goto err_unlock;
 975
 976	platform_set_drvdata(pdev, fmd);
 977	mutex_unlock(&fmd->media_dev.graph_mutex);
 978	return 0;
 979
 980err_unlock:
 981	mutex_unlock(&fmd->media_dev.graph_mutex);
 982err_clk:
 983	media_device_unregister(&fmd->media_dev);
 984	fimc_md_put_clocks(fmd);
 985	fimc_md_unregister_entities(fmd);
 986err_md:
 987	v4l2_device_unregister(&fmd->v4l2_dev);
 988	return ret;
 989}
 990
 991static int __devexit fimc_md_remove(struct platform_device *pdev)
 992{
 993	struct fimc_md *fmd = platform_get_drvdata(pdev);
 994
 995	if (!fmd)
 996		return 0;
 997	device_remove_file(&pdev->dev, &dev_attr_subdev_conf_mode);
 998	fimc_md_unregister_entities(fmd);
 999	media_device_unregister(&fmd->media_dev);
1000	fimc_md_put_clocks(fmd);
1001	return 0;
1002}
1003
1004static struct platform_driver fimc_md_driver = {
1005	.probe		= fimc_md_probe,
1006	.remove		= __devexit_p(fimc_md_remove),
1007	.driver = {
1008		.name	= "s5p-fimc-md",
1009		.owner	= THIS_MODULE,
1010	}
1011};
1012
1013int __init fimc_md_init(void)
1014{
1015	int ret;
1016
1017	request_module("s5p-csis");
1018	ret = fimc_register_driver();
1019	if (ret)
1020		return ret;
1021
1022	return platform_driver_register(&fimc_md_driver);
1023}
1024void __exit fimc_md_exit(void)
1025{
1026	platform_driver_unregister(&fimc_md_driver);
1027	fimc_unregister_driver();
1028}
1029
1030module_init(fimc_md_init);
1031module_exit(fimc_md_exit);
1032
1033MODULE_AUTHOR("Sylwester Nawrocki <s.nawrocki@samsung.com>");
1034MODULE_DESCRIPTION("S5P FIMC camera host interface/video postprocessor driver");
1035MODULE_LICENSE("GPL");
1036MODULE_VERSION("2.0.1");