Skip to content

Commit e223b1e

Browse files
jackzhustfhal-feng
authored andcommitted
media: staging: media: starfive: camss: Register devices
Register ISP sub-device and video devices for StarFive Camera Subsystem. Signed-off-by: Jack Zhu <jack.zhu@starfivetech.com>
1 parent 3a39213 commit e223b1e

1 file changed

Lines changed: 96 additions & 1 deletion

File tree

drivers/staging/media/starfive/camss/stf_camss.c

Lines changed: 96 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -120,6 +120,85 @@ static int stfcamss_of_parse_ports(struct stfcamss *stfcamss)
120120
return num_subdevs;
121121
}
122122

123+
static int stfcamss_register_devs(struct stfcamss *stfcamss)
124+
{
125+
struct stf_capture *cap_yuv = &stfcamss->captures[STF_CAPTURE_YUV];
126+
struct stf_isp_dev *isp_dev = &stfcamss->isp_dev;
127+
int ret;
128+
129+
ret = stf_isp_register(isp_dev, &stfcamss->v4l2_dev);
130+
if (ret < 0) {
131+
dev_err(stfcamss->dev,
132+
"failed to register stf isp%d entity: %d\n", 0, ret);
133+
return ret;
134+
}
135+
136+
ret = stf_capture_register(stfcamss, &stfcamss->v4l2_dev);
137+
if (ret < 0) {
138+
dev_err(stfcamss->dev,
139+
"failed to register capture: %d\n", ret);
140+
goto err_isp_unregister;
141+
}
142+
143+
ret = media_create_pad_link(&isp_dev->subdev.entity, STF_ISP_PAD_SRC,
144+
&cap_yuv->video.vdev.entity, 0, 0);
145+
if (ret)
146+
goto err_cap_unregister;
147+
148+
cap_yuv->video.source_subdev = &isp_dev->subdev;
149+
150+
return ret;
151+
152+
err_cap_unregister:
153+
stf_capture_unregister(stfcamss);
154+
err_isp_unregister:
155+
stf_isp_unregister(&stfcamss->isp_dev);
156+
157+
return ret;
158+
}
159+
160+
static void stfcamss_unregister_devs(struct stfcamss *stfcamss)
161+
{
162+
stf_isp_unregister(&stfcamss->isp_dev);
163+
stf_capture_unregister(stfcamss);
164+
}
165+
166+
static int stfcamss_subdev_notifier_bound(struct v4l2_async_notifier *async,
167+
struct v4l2_subdev *subdev,
168+
struct v4l2_async_subdev *asd)
169+
{
170+
struct stfcamss *stfcamss =
171+
container_of(async, struct stfcamss, notifier);
172+
struct stfcamss_async_subdev *csd =
173+
container_of(asd, struct stfcamss_async_subdev, asd);
174+
enum stf_port_num port = csd->port;
175+
struct stf_isp_dev *isp_dev = &stfcamss->isp_dev;
176+
struct stf_capture *cap_raw = &stfcamss->captures[STF_CAPTURE_RAW];
177+
struct media_pad *pad;
178+
int ret;
179+
180+
if (port == STF_PORT_CSI2RX) {
181+
pad = &isp_dev->pads[STF_ISP_PAD_SINK];
182+
} else {
183+
dev_err(stfcamss->dev, "not support port %d\n", port);
184+
return -EPERM;
185+
}
186+
187+
ret = v4l2_create_fwnode_links_to_pad(subdev, pad, 0);
188+
if (ret)
189+
return ret;
190+
191+
ret = media_create_pad_link(&subdev->entity, 1,
192+
&cap_raw->video.vdev.entity, 0, 0);
193+
if (ret)
194+
return ret;
195+
196+
isp_dev->source_subdev = subdev;
197+
cap_raw->video.source_subdev = subdev;
198+
199+
return 0;
200+
}
201+
123202
static int stfcamss_subdev_notifier_complete(struct v4l2_async_notifier *ntf)
124203
{
125204
struct stfcamss *stfcamss =
@@ -130,6 +209,7 @@ static int stfcamss_subdev_notifier_complete(struct v4l2_async_notifier *ntf)
130209

131210
static const struct v4l2_async_notifier_operations
132211
stfcamss_subdev_notifier_ops = {
212+
.bound = stfcamss_subdev_notifier_bound,
133213
.complete = stfcamss_subdev_notifier_complete,
134214
};
135215

@@ -214,6 +294,12 @@ static int stfcamss_probe(struct platform_device *pdev)
214294
goto err_cleanup_notifier;
215295
}
216296

297+
ret = stf_isp_init(stfcamss);
298+
if (ret < 0) {
299+
dev_err(dev, "Failed to init isp: %d\n", ret);
300+
goto err_cleanup_notifier;
301+
}
302+
217303
stfcamss_mc_init(pdev, stfcamss);
218304

219305
ret = v4l2_device_register(stfcamss->dev, &stfcamss->v4l2_dev);
@@ -228,6 +314,12 @@ static int stfcamss_probe(struct platform_device *pdev)
228314
goto err_unregister_device;
229315
}
230316

317+
ret = stfcamss_register_devs(stfcamss);
318+
if (ret < 0) {
319+
dev_err(dev, "Failed to register subdevice: %d\n", ret);
320+
goto err_unregister_media_dev;
321+
}
322+
231323
pm_runtime_enable(dev);
232324

233325
stfcamss->notifier.ops = &stfcamss_subdev_notifier_ops;
@@ -236,11 +328,13 @@ static int stfcamss_probe(struct platform_device *pdev)
236328
dev_err(dev, "Failed to register async subdev nodes: %d\n",
237329
ret);
238330
pm_runtime_disable(dev);
239-
goto err_unregister_media_dev;
331+
goto err_unregister_subdevs;
240332
}
241333

242334
return 0;
243335

336+
err_unregister_subdevs:
337+
stfcamss_unregister_devs(stfcamss);
244338
err_unregister_media_dev:
245339
media_device_unregister(&stfcamss->media_dev);
246340
err_unregister_device:
@@ -262,6 +356,7 @@ static int stfcamss_remove(struct platform_device *pdev)
262356
{
263357
struct stfcamss *stfcamss = platform_get_drvdata(pdev);
264358

359+
stfcamss_unregister_devs(stfcamss);
265360
v4l2_device_unregister(&stfcamss->v4l2_dev);
266361
media_device_cleanup(&stfcamss->media_dev);
267362
pm_runtime_disable(&pdev->dev);

0 commit comments

Comments
 (0)