1 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt 2 3 #include <media/drv-intf/saa7146_vv.h> 4 #include <media/v4l2-event.h> 5 #include <media/v4l2-ctrls.h> 6 #include <linux/module.h> 7 #include <linux/kernel.h> 8 9 static int max_memory = 32; 10 11 module_param(max_memory, int, 0644); 12 MODULE_PARM_DESC(max_memory, "maximum memory usage for capture buffers (default: 32Mb)"); 13 14 #define IS_CAPTURE_ACTIVE(fh) \ 15 (((vv->video_status & STATUS_CAPTURE) != 0) && (vv->video_fh == fh)) 16 17 #define IS_OVERLAY_ACTIVE(fh) \ 18 (((vv->video_status & STATUS_OVERLAY) != 0) && (vv->video_fh == fh)) 19 20 /* format descriptions for capture and preview */ 21 static struct saa7146_format formats[] = { 22 { 23 .pixelformat = V4L2_PIX_FMT_RGB332, 24 .trans = RGB08_COMPOSED, 25 .depth = 8, 26 .flags = 0, 27 }, { 28 .pixelformat = V4L2_PIX_FMT_RGB565, 29 .trans = RGB16_COMPOSED, 30 .depth = 16, 31 .flags = 0, 32 }, { 33 .pixelformat = V4L2_PIX_FMT_BGR24, 34 .trans = RGB24_COMPOSED, 35 .depth = 24, 36 .flags = 0, 37 }, { 38 .pixelformat = V4L2_PIX_FMT_BGR32, 39 .trans = RGB32_COMPOSED, 40 .depth = 32, 41 .flags = 0, 42 }, { 43 .pixelformat = V4L2_PIX_FMT_RGB32, 44 .trans = RGB32_COMPOSED, 45 .depth = 32, 46 .flags = 0, 47 .swap = 0x2, 48 }, { 49 .pixelformat = V4L2_PIX_FMT_GREY, 50 .trans = Y8, 51 .depth = 8, 52 .flags = 0, 53 }, { 54 .pixelformat = V4L2_PIX_FMT_YUV422P, 55 .trans = YUV422_DECOMPOSED, 56 .depth = 16, 57 .flags = FORMAT_BYTE_SWAP|FORMAT_IS_PLANAR, 58 }, { 59 .pixelformat = V4L2_PIX_FMT_YVU420, 60 .trans = YUV420_DECOMPOSED, 61 .depth = 12, 62 .flags = FORMAT_BYTE_SWAP|FORMAT_IS_PLANAR, 63 }, { 64 .pixelformat = V4L2_PIX_FMT_YUV420, 65 .trans = YUV420_DECOMPOSED, 66 .depth = 12, 67 .flags = FORMAT_IS_PLANAR, 68 }, { 69 .pixelformat = V4L2_PIX_FMT_UYVY, 70 .trans = YUV422_COMPOSED, 71 .depth = 16, 72 .flags = 0, 73 } 74 }; 75 76 /* unfortunately, the saa7146 contains a bug which prevents it from doing on-the-fly byte swaps. 77 due to this, it's impossible to provide additional *packed* formats, which are simply byte swapped 78 (like V4L2_PIX_FMT_YUYV) ... 8-( */ 79 80 struct saa7146_format* saa7146_format_by_fourcc(struct saa7146_dev *dev, int fourcc) 81 { 82 int i; 83 84 for (i = 0; i < ARRAY_SIZE(formats); i++) { 85 if (formats[i].pixelformat == fourcc) { 86 return formats+i; 87 } 88 } 89 90 DEB_D("unknown pixelformat:'%4.4s'\n", (char *)&fourcc); 91 return NULL; 92 } 93 94 static int vidioc_try_fmt_vid_overlay(struct file *file, void *fh, struct v4l2_format *f); 95 96 int saa7146_start_preview(struct saa7146_fh *fh) 97 { 98 struct saa7146_dev *dev = fh->dev; 99 struct saa7146_vv *vv = dev->vv_data; 100 struct v4l2_format fmt; 101 int ret = 0, err = 0; 102 103 DEB_EE("dev:%p, fh:%p\n", dev, fh); 104 105 /* check if we have overlay information */ 106 if (vv->ov.fh == NULL) { 107 DEB_D("no overlay data available. try S_FMT first.\n"); 108 return -EAGAIN; 109 } 110 111 /* check if streaming capture is running */ 112 if (IS_CAPTURE_ACTIVE(fh) != 0) { 113 DEB_D("streaming capture is active\n"); 114 return -EBUSY; 115 } 116 117 /* check if overlay is running */ 118 if (IS_OVERLAY_ACTIVE(fh) != 0) { 119 if (vv->video_fh == fh) { 120 DEB_D("overlay is already active\n"); 121 return 0; 122 } 123 DEB_D("overlay is already active in another open\n"); 124 return -EBUSY; 125 } 126 127 if (0 == saa7146_res_get(fh, RESOURCE_DMA1_HPS|RESOURCE_DMA2_CLP)) { 128 DEB_D("cannot get necessary overlay resources\n"); 129 return -EBUSY; 130 } 131 132 fmt.fmt.win = vv->ov.win; 133 err = vidioc_try_fmt_vid_overlay(NULL, fh, &fmt); 134 if (0 != err) { 135 saa7146_res_free(vv->video_fh, RESOURCE_DMA1_HPS|RESOURCE_DMA2_CLP); 136 return -EBUSY; 137 } 138 vv->ov.win = fmt.fmt.win; 139 140 DEB_D("%dx%d+%d+%d 0x%08x field=%s\n", 141 vv->ov.win.w.width, vv->ov.win.w.height, 142 vv->ov.win.w.left, vv->ov.win.w.top, 143 vv->ov_fmt->pixelformat, v4l2_field_names[vv->ov.win.field]); 144 145 if (0 != (ret = saa7146_enable_overlay(fh))) { 146 DEB_D("enabling overlay failed: %d\n", ret); 147 saa7146_res_free(vv->video_fh, RESOURCE_DMA1_HPS|RESOURCE_DMA2_CLP); 148 return ret; 149 } 150 151 vv->video_status = STATUS_OVERLAY; 152 vv->video_fh = fh; 153 154 return 0; 155 } 156 EXPORT_SYMBOL_GPL(saa7146_start_preview); 157 158 int saa7146_stop_preview(struct saa7146_fh *fh) 159 { 160 struct saa7146_dev *dev = fh->dev; 161 struct saa7146_vv *vv = dev->vv_data; 162 163 DEB_EE("dev:%p, fh:%p\n", dev, fh); 164 165 /* check if streaming capture is running */ 166 if (IS_CAPTURE_ACTIVE(fh) != 0) { 167 DEB_D("streaming capture is active\n"); 168 return -EBUSY; 169 } 170 171 /* check if overlay is running at all */ 172 if ((vv->video_status & STATUS_OVERLAY) == 0) { 173 DEB_D("no active overlay\n"); 174 return 0; 175 } 176 177 if (vv->video_fh != fh) { 178 DEB_D("overlay is active, but in another open\n"); 179 return -EBUSY; 180 } 181 182 vv->video_status = 0; 183 vv->video_fh = NULL; 184 185 saa7146_disable_overlay(fh); 186 187 saa7146_res_free(fh, RESOURCE_DMA1_HPS|RESOURCE_DMA2_CLP); 188 189 return 0; 190 } 191 EXPORT_SYMBOL_GPL(saa7146_stop_preview); 192 193 /********************************************************************************/ 194 /* common pagetable functions */ 195 196 static int saa7146_pgtable_build(struct saa7146_dev *dev, struct saa7146_buf *buf) 197 { 198 struct pci_dev *pci = dev->pci; 199 struct videobuf_dmabuf *dma=videobuf_to_dma(&buf->vb); 200 struct scatterlist *list = dma->sglist; 201 int length = dma->sglen; 202 struct saa7146_format *sfmt = saa7146_format_by_fourcc(dev,buf->fmt->pixelformat); 203 204 DEB_EE("dev:%p, buf:%p, sg_len:%d\n", dev, buf, length); 205 206 if( 0 != IS_PLANAR(sfmt->trans)) { 207 struct saa7146_pgtable *pt1 = &buf->pt[0]; 208 struct saa7146_pgtable *pt2 = &buf->pt[1]; 209 struct saa7146_pgtable *pt3 = &buf->pt[2]; 210 __le32 *ptr1, *ptr2, *ptr3; 211 __le32 fill; 212 213 int size = buf->fmt->width*buf->fmt->height; 214 int i,p,m1,m2,m3,o1,o2; 215 216 switch( sfmt->depth ) { 217 case 12: { 218 /* create some offsets inside the page table */ 219 m1 = ((size+PAGE_SIZE)/PAGE_SIZE)-1; 220 m2 = ((size+(size/4)+PAGE_SIZE)/PAGE_SIZE)-1; 221 m3 = ((size+(size/2)+PAGE_SIZE)/PAGE_SIZE)-1; 222 o1 = size%PAGE_SIZE; 223 o2 = (size+(size/4))%PAGE_SIZE; 224 DEB_CAP("size:%d, m1:%d, m2:%d, m3:%d, o1:%d, o2:%d\n", 225 size, m1, m2, m3, o1, o2); 226 break; 227 } 228 case 16: { 229 /* create some offsets inside the page table */ 230 m1 = ((size+PAGE_SIZE)/PAGE_SIZE)-1; 231 m2 = ((size+(size/2)+PAGE_SIZE)/PAGE_SIZE)-1; 232 m3 = ((2*size+PAGE_SIZE)/PAGE_SIZE)-1; 233 o1 = size%PAGE_SIZE; 234 o2 = (size+(size/2))%PAGE_SIZE; 235 DEB_CAP("size:%d, m1:%d, m2:%d, m3:%d, o1:%d, o2:%d\n", 236 size, m1, m2, m3, o1, o2); 237 break; 238 } 239 default: { 240 return -1; 241 } 242 } 243 244 ptr1 = pt1->cpu; 245 ptr2 = pt2->cpu; 246 ptr3 = pt3->cpu; 247 248 /* walk all pages, copy all page addresses to ptr1 */ 249 for (i = 0; i < length; i++, list++) { 250 for (p = 0; p * 4096 < list->length; p++, ptr1++) { 251 *ptr1 = cpu_to_le32(sg_dma_address(list) - list->offset); 252 } 253 } 254 /* 255 ptr1 = pt1->cpu; 256 for(j=0;j<40;j++) { 257 printk("ptr1 %d: 0x%08x\n",j,ptr1[j]); 258 } 259 */ 260 261 /* if we have a user buffer, the first page may not be 262 aligned to a page boundary. */ 263 pt1->offset = dma->sglist->offset; 264 pt2->offset = pt1->offset+o1; 265 pt3->offset = pt1->offset+o2; 266 267 /* create video-dma2 page table */ 268 ptr1 = pt1->cpu; 269 for(i = m1; i <= m2 ; i++, ptr2++) { 270 *ptr2 = ptr1[i]; 271 } 272 fill = *(ptr2-1); 273 for(;i<1024;i++,ptr2++) { 274 *ptr2 = fill; 275 } 276 /* create video-dma3 page table */ 277 ptr1 = pt1->cpu; 278 for(i = m2; i <= m3; i++,ptr3++) { 279 *ptr3 = ptr1[i]; 280 } 281 fill = *(ptr3-1); 282 for(;i<1024;i++,ptr3++) { 283 *ptr3 = fill; 284 } 285 /* finally: finish up video-dma1 page table */ 286 ptr1 = pt1->cpu+m1; 287 fill = pt1->cpu[m1]; 288 for(i=m1;i<1024;i++,ptr1++) { 289 *ptr1 = fill; 290 } 291 /* 292 ptr1 = pt1->cpu; 293 ptr2 = pt2->cpu; 294 ptr3 = pt3->cpu; 295 for(j=0;j<40;j++) { 296 printk("ptr1 %d: 0x%08x\n",j,ptr1[j]); 297 } 298 for(j=0;j<40;j++) { 299 printk("ptr2 %d: 0x%08x\n",j,ptr2[j]); 300 } 301 for(j=0;j<40;j++) { 302 printk("ptr3 %d: 0x%08x\n",j,ptr3[j]); 303 } 304 */ 305 } else { 306 struct saa7146_pgtable *pt = &buf->pt[0]; 307 return saa7146_pgtable_build_single(pci, pt, list, length); 308 } 309 310 return 0; 311 } 312 313 314 /********************************************************************************/ 315 /* file operations */ 316 317 static int video_begin(struct saa7146_fh *fh) 318 { 319 struct saa7146_dev *dev = fh->dev; 320 struct saa7146_vv *vv = dev->vv_data; 321 struct saa7146_format *fmt = NULL; 322 unsigned int resource; 323 int ret = 0, err = 0; 324 325 DEB_EE("dev:%p, fh:%p\n", dev, fh); 326 327 if ((vv->video_status & STATUS_CAPTURE) != 0) { 328 if (vv->video_fh == fh) { 329 DEB_S("already capturing\n"); 330 return 0; 331 } 332 DEB_S("already capturing in another open\n"); 333 return -EBUSY; 334 } 335 336 if ((vv->video_status & STATUS_OVERLAY) != 0) { 337 DEB_S("warning: suspending overlay video for streaming capture\n"); 338 vv->ov_suspend = vv->video_fh; 339 err = saa7146_stop_preview(vv->video_fh); /* side effect: video_status is now 0, video_fh is NULL */ 340 if (0 != err) { 341 DEB_D("suspending video failed. aborting\n"); 342 return err; 343 } 344 } 345 346 fmt = saa7146_format_by_fourcc(dev, vv->video_fmt.pixelformat); 347 /* we need to have a valid format set here */ 348 if (!fmt) 349 return -EINVAL; 350 351 if (0 != (fmt->flags & FORMAT_IS_PLANAR)) { 352 resource = RESOURCE_DMA1_HPS|RESOURCE_DMA2_CLP|RESOURCE_DMA3_BRS; 353 } else { 354 resource = RESOURCE_DMA1_HPS; 355 } 356 357 ret = saa7146_res_get(fh, resource); 358 if (0 == ret) { 359 DEB_S("cannot get capture resource %d\n", resource); 360 if (vv->ov_suspend != NULL) { 361 saa7146_start_preview(vv->ov_suspend); 362 vv->ov_suspend = NULL; 363 } 364 return -EBUSY; 365 } 366 367 /* clear out beginning of streaming bit (rps register 0)*/ 368 saa7146_write(dev, MC2, MASK_27 ); 369 370 /* enable rps0 irqs */ 371 SAA7146_IER_ENABLE(dev, MASK_27); 372 373 vv->video_fh = fh; 374 vv->video_status = STATUS_CAPTURE; 375 376 return 0; 377 } 378 379 static int video_end(struct saa7146_fh *fh, struct file *file) 380 { 381 struct saa7146_dev *dev = fh->dev; 382 struct saa7146_vv *vv = dev->vv_data; 383 struct saa7146_dmaqueue *q = &vv->video_dmaq; 384 struct saa7146_format *fmt = NULL; 385 unsigned long flags; 386 unsigned int resource; 387 u32 dmas = 0; 388 DEB_EE("dev:%p, fh:%p\n", dev, fh); 389 390 if ((vv->video_status & STATUS_CAPTURE) != STATUS_CAPTURE) { 391 DEB_S("not capturing\n"); 392 return 0; 393 } 394 395 if (vv->video_fh != fh) { 396 DEB_S("capturing, but in another open\n"); 397 return -EBUSY; 398 } 399 400 fmt = saa7146_format_by_fourcc(dev, vv->video_fmt.pixelformat); 401 /* we need to have a valid format set here */ 402 if (!fmt) 403 return -EINVAL; 404 405 if (0 != (fmt->flags & FORMAT_IS_PLANAR)) { 406 resource = RESOURCE_DMA1_HPS|RESOURCE_DMA2_CLP|RESOURCE_DMA3_BRS; 407 dmas = MASK_22 | MASK_21 | MASK_20; 408 } else { 409 resource = RESOURCE_DMA1_HPS; 410 dmas = MASK_22; 411 } 412 spin_lock_irqsave(&dev->slock,flags); 413 414 /* disable rps0 */ 415 saa7146_write(dev, MC1, MASK_28); 416 417 /* disable rps0 irqs */ 418 SAA7146_IER_DISABLE(dev, MASK_27); 419 420 /* shut down all used video dma transfers */ 421 saa7146_write(dev, MC1, dmas); 422 423 if (q->curr) 424 saa7146_buffer_finish(dev, q, VIDEOBUF_DONE); 425 426 spin_unlock_irqrestore(&dev->slock, flags); 427 428 vv->video_fh = NULL; 429 vv->video_status = 0; 430 431 saa7146_res_free(fh, resource); 432 433 if (vv->ov_suspend != NULL) { 434 saa7146_start_preview(vv->ov_suspend); 435 vv->ov_suspend = NULL; 436 } 437 438 return 0; 439 } 440 441 static int vidioc_querycap(struct file *file, void *fh, struct v4l2_capability *cap) 442 { 443 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev; 444 445 strscpy((char *)cap->driver, "saa7146 v4l2", sizeof(cap->driver)); 446 strscpy((char *)cap->card, dev->ext->name, sizeof(cap->card)); 447 sprintf((char *)cap->bus_info, "PCI:%s", pci_name(dev->pci)); 448 cap->capabilities = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_VIDEO_OVERLAY | 449 V4L2_CAP_READWRITE | V4L2_CAP_STREAMING | 450 V4L2_CAP_DEVICE_CAPS; 451 cap->capabilities |= dev->ext_vv_data->capabilities; 452 return 0; 453 } 454 455 static int vidioc_g_fbuf(struct file *file, void *fh, struct v4l2_framebuffer *fb) 456 { 457 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev; 458 struct saa7146_vv *vv = dev->vv_data; 459 460 *fb = vv->ov_fb; 461 fb->capability = V4L2_FBUF_CAP_LIST_CLIPPING; 462 fb->flags = V4L2_FBUF_FLAG_PRIMARY; 463 return 0; 464 } 465 466 static int vidioc_s_fbuf(struct file *file, void *fh, const struct v4l2_framebuffer *fb) 467 { 468 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev; 469 struct saa7146_vv *vv = dev->vv_data; 470 struct saa7146_format *fmt; 471 472 DEB_EE("VIDIOC_S_FBUF\n"); 473 474 if (!capable(CAP_SYS_ADMIN) && !capable(CAP_SYS_RAWIO)) 475 return -EPERM; 476 477 /* check args */ 478 fmt = saa7146_format_by_fourcc(dev, fb->fmt.pixelformat); 479 if (NULL == fmt) 480 return -EINVAL; 481 482 /* planar formats are not allowed for overlay video, clipping and video dma would clash */ 483 if (fmt->flags & FORMAT_IS_PLANAR) 484 DEB_S("planar pixelformat '%4.4s' not allowed for overlay\n", 485 (char *)&fmt->pixelformat); 486 487 /* check if overlay is running */ 488 if (IS_OVERLAY_ACTIVE(fh) != 0) { 489 if (vv->video_fh != fh) { 490 DEB_D("refusing to change framebuffer information while overlay is active in another open\n"); 491 return -EBUSY; 492 } 493 } 494 495 /* ok, accept it */ 496 vv->ov_fb = *fb; 497 vv->ov_fmt = fmt; 498 499 if (vv->ov_fb.fmt.bytesperline < vv->ov_fb.fmt.width) { 500 vv->ov_fb.fmt.bytesperline = vv->ov_fb.fmt.width * fmt->depth / 8; 501 DEB_D("setting bytesperline to %d\n", vv->ov_fb.fmt.bytesperline); 502 } 503 return 0; 504 } 505 506 static int vidioc_enum_fmt_vid_cap(struct file *file, void *fh, struct v4l2_fmtdesc *f) 507 { 508 if (f->index >= ARRAY_SIZE(formats)) 509 return -EINVAL; 510 f->pixelformat = formats[f->index].pixelformat; 511 return 0; 512 } 513 514 int saa7146_s_ctrl(struct v4l2_ctrl *ctrl) 515 { 516 struct saa7146_dev *dev = container_of(ctrl->handler, 517 struct saa7146_dev, ctrl_handler); 518 struct saa7146_vv *vv = dev->vv_data; 519 u32 val; 520 521 switch (ctrl->id) { 522 case V4L2_CID_BRIGHTNESS: 523 val = saa7146_read(dev, BCS_CTRL); 524 val &= 0x00ffffff; 525 val |= (ctrl->val << 24); 526 saa7146_write(dev, BCS_CTRL, val); 527 saa7146_write(dev, MC2, MASK_22 | MASK_06); 528 break; 529 530 case V4L2_CID_CONTRAST: 531 val = saa7146_read(dev, BCS_CTRL); 532 val &= 0xff00ffff; 533 val |= (ctrl->val << 16); 534 saa7146_write(dev, BCS_CTRL, val); 535 saa7146_write(dev, MC2, MASK_22 | MASK_06); 536 break; 537 538 case V4L2_CID_SATURATION: 539 val = saa7146_read(dev, BCS_CTRL); 540 val &= 0xffffff00; 541 val |= (ctrl->val << 0); 542 saa7146_write(dev, BCS_CTRL, val); 543 saa7146_write(dev, MC2, MASK_22 | MASK_06); 544 break; 545 546 case V4L2_CID_HFLIP: 547 /* fixme: we can support changing VFLIP and HFLIP here... */ 548 if ((vv->video_status & STATUS_CAPTURE)) 549 return -EBUSY; 550 vv->hflip = ctrl->val; 551 break; 552 553 case V4L2_CID_VFLIP: 554 if ((vv->video_status & STATUS_CAPTURE)) 555 return -EBUSY; 556 vv->vflip = ctrl->val; 557 break; 558 559 default: 560 return -EINVAL; 561 } 562 563 if ((vv->video_status & STATUS_OVERLAY) != 0) { /* CHECK: && (vv->video_fh == fh)) */ 564 struct saa7146_fh *fh = vv->video_fh; 565 566 saa7146_stop_preview(fh); 567 saa7146_start_preview(fh); 568 } 569 return 0; 570 } 571 572 static int vidioc_g_parm(struct file *file, void *fh, 573 struct v4l2_streamparm *parm) 574 { 575 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev; 576 struct saa7146_vv *vv = dev->vv_data; 577 578 if (parm->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) 579 return -EINVAL; 580 parm->parm.capture.readbuffers = 1; 581 v4l2_video_std_frame_period(vv->standard->id, 582 &parm->parm.capture.timeperframe); 583 return 0; 584 } 585 586 static int vidioc_g_fmt_vid_cap(struct file *file, void *fh, struct v4l2_format *f) 587 { 588 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev; 589 struct saa7146_vv *vv = dev->vv_data; 590 591 f->fmt.pix = vv->video_fmt; 592 return 0; 593 } 594 595 static int vidioc_g_fmt_vid_overlay(struct file *file, void *fh, struct v4l2_format *f) 596 { 597 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev; 598 struct saa7146_vv *vv = dev->vv_data; 599 600 f->fmt.win = vv->ov.win; 601 return 0; 602 } 603 604 static int vidioc_g_fmt_vbi_cap(struct file *file, void *fh, struct v4l2_format *f) 605 { 606 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev; 607 struct saa7146_vv *vv = dev->vv_data; 608 609 f->fmt.vbi = vv->vbi_fmt; 610 return 0; 611 } 612 613 static int vidioc_try_fmt_vid_cap(struct file *file, void *fh, struct v4l2_format *f) 614 { 615 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev; 616 struct saa7146_vv *vv = dev->vv_data; 617 struct saa7146_format *fmt; 618 enum v4l2_field field; 619 int maxw, maxh; 620 int calc_bpl; 621 622 DEB_EE("V4L2_BUF_TYPE_VIDEO_CAPTURE: dev:%p, fh:%p\n", dev, fh); 623 624 fmt = saa7146_format_by_fourcc(dev, f->fmt.pix.pixelformat); 625 if (NULL == fmt) 626 return -EINVAL; 627 628 field = f->fmt.pix.field; 629 maxw = vv->standard->h_max_out; 630 maxh = vv->standard->v_max_out; 631 632 if (V4L2_FIELD_ANY == field) { 633 field = (f->fmt.pix.height > maxh / 2) 634 ? V4L2_FIELD_INTERLACED 635 : V4L2_FIELD_BOTTOM; 636 } 637 switch (field) { 638 case V4L2_FIELD_ALTERNATE: 639 vv->last_field = V4L2_FIELD_TOP; 640 maxh = maxh / 2; 641 break; 642 case V4L2_FIELD_TOP: 643 case V4L2_FIELD_BOTTOM: 644 vv->last_field = V4L2_FIELD_INTERLACED; 645 maxh = maxh / 2; 646 break; 647 case V4L2_FIELD_INTERLACED: 648 vv->last_field = V4L2_FIELD_INTERLACED; 649 break; 650 default: 651 DEB_D("no known field mode '%d'\n", field); 652 return -EINVAL; 653 } 654 655 f->fmt.pix.field = field; 656 f->fmt.pix.colorspace = V4L2_COLORSPACE_SMPTE170M; 657 if (f->fmt.pix.width > maxw) 658 f->fmt.pix.width = maxw; 659 if (f->fmt.pix.height > maxh) 660 f->fmt.pix.height = maxh; 661 662 calc_bpl = (f->fmt.pix.width * fmt->depth) / 8; 663 664 if (f->fmt.pix.bytesperline < calc_bpl) 665 f->fmt.pix.bytesperline = calc_bpl; 666 667 if (f->fmt.pix.bytesperline > (2 * PAGE_SIZE * fmt->depth) / 8) /* arbitrary constraint */ 668 f->fmt.pix.bytesperline = calc_bpl; 669 670 f->fmt.pix.sizeimage = f->fmt.pix.bytesperline * f->fmt.pix.height; 671 DEB_D("w:%d, h:%d, bytesperline:%d, sizeimage:%d\n", 672 f->fmt.pix.width, f->fmt.pix.height, 673 f->fmt.pix.bytesperline, f->fmt.pix.sizeimage); 674 675 return 0; 676 } 677 678 679 static int vidioc_try_fmt_vid_overlay(struct file *file, void *fh, struct v4l2_format *f) 680 { 681 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev; 682 struct saa7146_vv *vv = dev->vv_data; 683 struct v4l2_window *win = &f->fmt.win; 684 enum v4l2_field field; 685 int maxw, maxh; 686 687 DEB_EE("dev:%p\n", dev); 688 689 if (NULL == vv->ov_fb.base) { 690 DEB_D("no fb base set\n"); 691 return -EINVAL; 692 } 693 if (NULL == vv->ov_fmt) { 694 DEB_D("no fb fmt set\n"); 695 return -EINVAL; 696 } 697 if (win->w.width < 48 || win->w.height < 32) { 698 DEB_D("min width/height. (%d,%d)\n", 699 win->w.width, win->w.height); 700 return -EINVAL; 701 } 702 if (win->clipcount > 16) { 703 DEB_D("clipcount too big\n"); 704 return -EINVAL; 705 } 706 707 field = win->field; 708 maxw = vv->standard->h_max_out; 709 maxh = vv->standard->v_max_out; 710 711 if (V4L2_FIELD_ANY == field) { 712 field = (win->w.height > maxh / 2) 713 ? V4L2_FIELD_INTERLACED 714 : V4L2_FIELD_TOP; 715 } 716 switch (field) { 717 case V4L2_FIELD_TOP: 718 case V4L2_FIELD_BOTTOM: 719 case V4L2_FIELD_ALTERNATE: 720 maxh = maxh / 2; 721 break; 722 case V4L2_FIELD_INTERLACED: 723 break; 724 default: 725 DEB_D("no known field mode '%d'\n", field); 726 return -EINVAL; 727 } 728 729 win->field = field; 730 if (win->w.width > maxw) 731 win->w.width = maxw; 732 if (win->w.height > maxh) 733 win->w.height = maxh; 734 735 return 0; 736 } 737 738 static int vidioc_s_fmt_vid_cap(struct file *file, void *__fh, struct v4l2_format *f) 739 { 740 struct saa7146_fh *fh = __fh; 741 struct saa7146_dev *dev = fh->dev; 742 struct saa7146_vv *vv = dev->vv_data; 743 int err; 744 745 DEB_EE("V4L2_BUF_TYPE_VIDEO_CAPTURE: dev:%p, fh:%p\n", dev, fh); 746 if (IS_CAPTURE_ACTIVE(fh) != 0) { 747 DEB_EE("streaming capture is active\n"); 748 return -EBUSY; 749 } 750 err = vidioc_try_fmt_vid_cap(file, fh, f); 751 if (0 != err) 752 return err; 753 vv->video_fmt = f->fmt.pix; 754 DEB_EE("set to pixelformat '%4.4s'\n", 755 (char *)&vv->video_fmt.pixelformat); 756 return 0; 757 } 758 759 static int vidioc_s_fmt_vid_overlay(struct file *file, void *__fh, struct v4l2_format *f) 760 { 761 struct saa7146_fh *fh = __fh; 762 struct saa7146_dev *dev = fh->dev; 763 struct saa7146_vv *vv = dev->vv_data; 764 int err; 765 766 DEB_EE("V4L2_BUF_TYPE_VIDEO_OVERLAY: dev:%p, fh:%p\n", dev, fh); 767 err = vidioc_try_fmt_vid_overlay(file, fh, f); 768 if (0 != err) 769 return err; 770 vv->ov.win = f->fmt.win; 771 vv->ov.nclips = f->fmt.win.clipcount; 772 if (vv->ov.nclips > 16) 773 vv->ov.nclips = 16; 774 if (copy_from_user(vv->ov.clips, f->fmt.win.clips, 775 sizeof(struct v4l2_clip) * vv->ov.nclips)) { 776 return -EFAULT; 777 } 778 779 /* vv->ov.fh is used to indicate that we have valid overlay information, too */ 780 vv->ov.fh = fh; 781 782 /* check if our current overlay is active */ 783 if (IS_OVERLAY_ACTIVE(fh) != 0) { 784 saa7146_stop_preview(fh); 785 saa7146_start_preview(fh); 786 } 787 return 0; 788 } 789 790 static int vidioc_g_std(struct file *file, void *fh, v4l2_std_id *norm) 791 { 792 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev; 793 struct saa7146_vv *vv = dev->vv_data; 794 795 *norm = vv->standard->id; 796 return 0; 797 } 798 799 /* the saa7146 supfhrts (used in conjunction with the saa7111a for example) 800 PAL / NTSC / SECAM. if your hardware does not (or does more) 801 -- override this function in your extension */ 802 /* 803 case VIDIOC_ENUMSTD: 804 { 805 struct v4l2_standard *e = arg; 806 if (e->index < 0 ) 807 return -EINVAL; 808 if( e->index < dev->ext_vv_data->num_stds ) { 809 DEB_EE("VIDIOC_ENUMSTD: index:%d\n", e->index); 810 v4l2_video_std_construct(e, dev->ext_vv_data->stds[e->index].id, dev->ext_vv_data->stds[e->index].name); 811 return 0; 812 } 813 return -EINVAL; 814 } 815 */ 816 817 static int vidioc_s_std(struct file *file, void *fh, v4l2_std_id id) 818 { 819 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev; 820 struct saa7146_vv *vv = dev->vv_data; 821 int found = 0; 822 int err, i; 823 824 DEB_EE("VIDIOC_S_STD\n"); 825 826 if ((vv->video_status & STATUS_CAPTURE) == STATUS_CAPTURE) { 827 DEB_D("cannot change video standard while streaming capture is active\n"); 828 return -EBUSY; 829 } 830 831 if ((vv->video_status & STATUS_OVERLAY) != 0) { 832 vv->ov_suspend = vv->video_fh; 833 err = saa7146_stop_preview(vv->video_fh); /* side effect: video_status is now 0, video_fh is NULL */ 834 if (0 != err) { 835 DEB_D("suspending video failed. aborting\n"); 836 return err; 837 } 838 } 839 840 for (i = 0; i < dev->ext_vv_data->num_stds; i++) 841 if (id & dev->ext_vv_data->stds[i].id) 842 break; 843 if (i != dev->ext_vv_data->num_stds) { 844 vv->standard = &dev->ext_vv_data->stds[i]; 845 if (NULL != dev->ext_vv_data->std_callback) 846 dev->ext_vv_data->std_callback(dev, vv->standard); 847 found = 1; 848 } 849 850 if (vv->ov_suspend != NULL) { 851 saa7146_start_preview(vv->ov_suspend); 852 vv->ov_suspend = NULL; 853 } 854 855 if (!found) { 856 DEB_EE("VIDIOC_S_STD: standard not found\n"); 857 return -EINVAL; 858 } 859 860 DEB_EE("VIDIOC_S_STD: set to standard to '%s'\n", vv->standard->name); 861 return 0; 862 } 863 864 static int vidioc_overlay(struct file *file, void *fh, unsigned int on) 865 { 866 int err; 867 868 DEB_D("VIDIOC_OVERLAY on:%d\n", on); 869 if (on) 870 err = saa7146_start_preview(fh); 871 else 872 err = saa7146_stop_preview(fh); 873 return err; 874 } 875 876 static int vidioc_reqbufs(struct file *file, void *__fh, struct v4l2_requestbuffers *b) 877 { 878 struct saa7146_fh *fh = __fh; 879 880 if (b->type == V4L2_BUF_TYPE_VIDEO_CAPTURE) 881 return videobuf_reqbufs(&fh->video_q, b); 882 if (b->type == V4L2_BUF_TYPE_VBI_CAPTURE) 883 return videobuf_reqbufs(&fh->vbi_q, b); 884 return -EINVAL; 885 } 886 887 static int vidioc_querybuf(struct file *file, void *__fh, struct v4l2_buffer *buf) 888 { 889 struct saa7146_fh *fh = __fh; 890 891 if (buf->type == V4L2_BUF_TYPE_VIDEO_CAPTURE) 892 return videobuf_querybuf(&fh->video_q, buf); 893 if (buf->type == V4L2_BUF_TYPE_VBI_CAPTURE) 894 return videobuf_querybuf(&fh->vbi_q, buf); 895 return -EINVAL; 896 } 897 898 static int vidioc_qbuf(struct file *file, void *__fh, struct v4l2_buffer *buf) 899 { 900 struct saa7146_fh *fh = __fh; 901 902 if (buf->type == V4L2_BUF_TYPE_VIDEO_CAPTURE) 903 return videobuf_qbuf(&fh->video_q, buf); 904 if (buf->type == V4L2_BUF_TYPE_VBI_CAPTURE) 905 return videobuf_qbuf(&fh->vbi_q, buf); 906 return -EINVAL; 907 } 908 909 static int vidioc_dqbuf(struct file *file, void *__fh, struct v4l2_buffer *buf) 910 { 911 struct saa7146_fh *fh = __fh; 912 913 if (buf->type == V4L2_BUF_TYPE_VIDEO_CAPTURE) 914 return videobuf_dqbuf(&fh->video_q, buf, file->f_flags & O_NONBLOCK); 915 if (buf->type == V4L2_BUF_TYPE_VBI_CAPTURE) 916 return videobuf_dqbuf(&fh->vbi_q, buf, file->f_flags & O_NONBLOCK); 917 return -EINVAL; 918 } 919 920 static int vidioc_streamon(struct file *file, void *__fh, enum v4l2_buf_type type) 921 { 922 struct saa7146_fh *fh = __fh; 923 int err; 924 925 DEB_D("VIDIOC_STREAMON, type:%d\n", type); 926 927 err = video_begin(fh); 928 if (err) 929 return err; 930 if (type == V4L2_BUF_TYPE_VIDEO_CAPTURE) 931 return videobuf_streamon(&fh->video_q); 932 if (type == V4L2_BUF_TYPE_VBI_CAPTURE) 933 return videobuf_streamon(&fh->vbi_q); 934 return -EINVAL; 935 } 936 937 static int vidioc_streamoff(struct file *file, void *__fh, enum v4l2_buf_type type) 938 { 939 struct saa7146_fh *fh = __fh; 940 struct saa7146_dev *dev = fh->dev; 941 struct saa7146_vv *vv = dev->vv_data; 942 int err; 943 944 DEB_D("VIDIOC_STREAMOFF, type:%d\n", type); 945 946 /* ugly: we need to copy some checks from video_end(), 947 because videobuf_streamoff() relies on the capture running. 948 check and fix this */ 949 if ((vv->video_status & STATUS_CAPTURE) != STATUS_CAPTURE) { 950 DEB_S("not capturing\n"); 951 return 0; 952 } 953 954 if (vv->video_fh != fh) { 955 DEB_S("capturing, but in another open\n"); 956 return -EBUSY; 957 } 958 959 err = -EINVAL; 960 if (type == V4L2_BUF_TYPE_VIDEO_CAPTURE) 961 err = videobuf_streamoff(&fh->video_q); 962 else if (type == V4L2_BUF_TYPE_VBI_CAPTURE) 963 err = videobuf_streamoff(&fh->vbi_q); 964 if (0 != err) { 965 DEB_D("warning: videobuf_streamoff() failed\n"); 966 video_end(fh, file); 967 } else { 968 err = video_end(fh, file); 969 } 970 return err; 971 } 972 973 const struct v4l2_ioctl_ops saa7146_video_ioctl_ops = { 974 .vidioc_querycap = vidioc_querycap, 975 .vidioc_enum_fmt_vid_cap = vidioc_enum_fmt_vid_cap, 976 .vidioc_enum_fmt_vid_overlay = vidioc_enum_fmt_vid_cap, 977 .vidioc_g_fmt_vid_cap = vidioc_g_fmt_vid_cap, 978 .vidioc_try_fmt_vid_cap = vidioc_try_fmt_vid_cap, 979 .vidioc_s_fmt_vid_cap = vidioc_s_fmt_vid_cap, 980 .vidioc_g_fmt_vid_overlay = vidioc_g_fmt_vid_overlay, 981 .vidioc_try_fmt_vid_overlay = vidioc_try_fmt_vid_overlay, 982 .vidioc_s_fmt_vid_overlay = vidioc_s_fmt_vid_overlay, 983 984 .vidioc_overlay = vidioc_overlay, 985 .vidioc_g_fbuf = vidioc_g_fbuf, 986 .vidioc_s_fbuf = vidioc_s_fbuf, 987 .vidioc_reqbufs = vidioc_reqbufs, 988 .vidioc_querybuf = vidioc_querybuf, 989 .vidioc_qbuf = vidioc_qbuf, 990 .vidioc_dqbuf = vidioc_dqbuf, 991 .vidioc_g_std = vidioc_g_std, 992 .vidioc_s_std = vidioc_s_std, 993 .vidioc_streamon = vidioc_streamon, 994 .vidioc_streamoff = vidioc_streamoff, 995 .vidioc_g_parm = vidioc_g_parm, 996 .vidioc_subscribe_event = v4l2_ctrl_subscribe_event, 997 .vidioc_unsubscribe_event = v4l2_event_unsubscribe, 998 }; 999 1000 const struct v4l2_ioctl_ops saa7146_vbi_ioctl_ops = { 1001 .vidioc_querycap = vidioc_querycap, 1002 .vidioc_g_fmt_vbi_cap = vidioc_g_fmt_vbi_cap, 1003 1004 .vidioc_reqbufs = vidioc_reqbufs, 1005 .vidioc_querybuf = vidioc_querybuf, 1006 .vidioc_qbuf = vidioc_qbuf, 1007 .vidioc_dqbuf = vidioc_dqbuf, 1008 .vidioc_g_std = vidioc_g_std, 1009 .vidioc_s_std = vidioc_s_std, 1010 .vidioc_streamon = vidioc_streamon, 1011 .vidioc_streamoff = vidioc_streamoff, 1012 .vidioc_g_parm = vidioc_g_parm, 1013 .vidioc_subscribe_event = v4l2_ctrl_subscribe_event, 1014 .vidioc_unsubscribe_event = v4l2_event_unsubscribe, 1015 }; 1016 1017 /*********************************************************************************/ 1018 /* buffer handling functions */ 1019 1020 static int buffer_activate (struct saa7146_dev *dev, 1021 struct saa7146_buf *buf, 1022 struct saa7146_buf *next) 1023 { 1024 struct saa7146_vv *vv = dev->vv_data; 1025 1026 buf->vb.state = VIDEOBUF_ACTIVE; 1027 saa7146_set_capture(dev,buf,next); 1028 1029 mod_timer(&vv->video_dmaq.timeout, jiffies+BUFFER_TIMEOUT); 1030 return 0; 1031 } 1032 1033 static void release_all_pagetables(struct saa7146_dev *dev, struct saa7146_buf *buf) 1034 { 1035 saa7146_pgtable_free(dev->pci, &buf->pt[0]); 1036 saa7146_pgtable_free(dev->pci, &buf->pt[1]); 1037 saa7146_pgtable_free(dev->pci, &buf->pt[2]); 1038 } 1039 1040 static int buffer_prepare(struct videobuf_queue *q, 1041 struct videobuf_buffer *vb, enum v4l2_field field) 1042 { 1043 struct file *file = q->priv_data; 1044 struct saa7146_fh *fh = file->private_data; 1045 struct saa7146_dev *dev = fh->dev; 1046 struct saa7146_vv *vv = dev->vv_data; 1047 struct saa7146_buf *buf = (struct saa7146_buf *)vb; 1048 int size,err = 0; 1049 1050 DEB_CAP("vbuf:%p\n", vb); 1051 1052 /* sanity checks */ 1053 if (vv->video_fmt.width < 48 || 1054 vv->video_fmt.height < 32 || 1055 vv->video_fmt.width > vv->standard->h_max_out || 1056 vv->video_fmt.height > vv->standard->v_max_out) { 1057 DEB_D("w (%d) / h (%d) out of bounds\n", 1058 vv->video_fmt.width, vv->video_fmt.height); 1059 return -EINVAL; 1060 } 1061 1062 size = vv->video_fmt.sizeimage; 1063 if (0 != buf->vb.baddr && buf->vb.bsize < size) { 1064 DEB_D("size mismatch\n"); 1065 return -EINVAL; 1066 } 1067 1068 DEB_CAP("buffer_prepare [size=%dx%d,bytes=%d,fields=%s]\n", 1069 vv->video_fmt.width, vv->video_fmt.height, 1070 size, v4l2_field_names[vv->video_fmt.field]); 1071 if (buf->vb.width != vv->video_fmt.width || 1072 buf->vb.bytesperline != vv->video_fmt.bytesperline || 1073 buf->vb.height != vv->video_fmt.height || 1074 buf->vb.size != size || 1075 buf->vb.field != field || 1076 buf->vb.field != vv->video_fmt.field || 1077 buf->fmt != &vv->video_fmt) { 1078 saa7146_dma_free(dev,q,buf); 1079 } 1080 1081 if (VIDEOBUF_NEEDS_INIT == buf->vb.state) { 1082 struct saa7146_format *sfmt; 1083 1084 buf->vb.bytesperline = vv->video_fmt.bytesperline; 1085 buf->vb.width = vv->video_fmt.width; 1086 buf->vb.height = vv->video_fmt.height; 1087 buf->vb.size = size; 1088 buf->vb.field = field; 1089 buf->fmt = &vv->video_fmt; 1090 buf->vb.field = vv->video_fmt.field; 1091 1092 sfmt = saa7146_format_by_fourcc(dev,buf->fmt->pixelformat); 1093 1094 release_all_pagetables(dev, buf); 1095 if( 0 != IS_PLANAR(sfmt->trans)) { 1096 saa7146_pgtable_alloc(dev->pci, &buf->pt[0]); 1097 saa7146_pgtable_alloc(dev->pci, &buf->pt[1]); 1098 saa7146_pgtable_alloc(dev->pci, &buf->pt[2]); 1099 } else { 1100 saa7146_pgtable_alloc(dev->pci, &buf->pt[0]); 1101 } 1102 1103 err = videobuf_iolock(q,&buf->vb, &vv->ov_fb); 1104 if (err) 1105 goto oops; 1106 err = saa7146_pgtable_build(dev,buf); 1107 if (err) 1108 goto oops; 1109 } 1110 buf->vb.state = VIDEOBUF_PREPARED; 1111 buf->activate = buffer_activate; 1112 1113 return 0; 1114 1115 oops: 1116 DEB_D("error out\n"); 1117 saa7146_dma_free(dev,q,buf); 1118 1119 return err; 1120 } 1121 1122 static int buffer_setup(struct videobuf_queue *q, unsigned int *count, unsigned int *size) 1123 { 1124 struct file *file = q->priv_data; 1125 struct saa7146_fh *fh = file->private_data; 1126 struct saa7146_vv *vv = fh->dev->vv_data; 1127 1128 if (0 == *count || *count > MAX_SAA7146_CAPTURE_BUFFERS) 1129 *count = MAX_SAA7146_CAPTURE_BUFFERS; 1130 1131 *size = vv->video_fmt.sizeimage; 1132 1133 /* check if we exceed the "max_memory" parameter */ 1134 if( (*count * *size) > (max_memory*1048576) ) { 1135 *count = (max_memory*1048576) / *size; 1136 } 1137 1138 DEB_CAP("%d buffers, %d bytes each\n", *count, *size); 1139 1140 return 0; 1141 } 1142 1143 static void buffer_queue(struct videobuf_queue *q, struct videobuf_buffer *vb) 1144 { 1145 struct file *file = q->priv_data; 1146 struct saa7146_fh *fh = file->private_data; 1147 struct saa7146_dev *dev = fh->dev; 1148 struct saa7146_vv *vv = dev->vv_data; 1149 struct saa7146_buf *buf = (struct saa7146_buf *)vb; 1150 1151 DEB_CAP("vbuf:%p\n", vb); 1152 saa7146_buffer_queue(fh->dev, &vv->video_dmaq, buf); 1153 } 1154 1155 static void buffer_release(struct videobuf_queue *q, struct videobuf_buffer *vb) 1156 { 1157 struct file *file = q->priv_data; 1158 struct saa7146_fh *fh = file->private_data; 1159 struct saa7146_dev *dev = fh->dev; 1160 struct saa7146_buf *buf = (struct saa7146_buf *)vb; 1161 1162 DEB_CAP("vbuf:%p\n", vb); 1163 1164 saa7146_dma_free(dev,q,buf); 1165 1166 release_all_pagetables(dev, buf); 1167 } 1168 1169 static const struct videobuf_queue_ops video_qops = { 1170 .buf_setup = buffer_setup, 1171 .buf_prepare = buffer_prepare, 1172 .buf_queue = buffer_queue, 1173 .buf_release = buffer_release, 1174 }; 1175 1176 /********************************************************************************/ 1177 /* file operations */ 1178 1179 static void video_init(struct saa7146_dev *dev, struct saa7146_vv *vv) 1180 { 1181 INIT_LIST_HEAD(&vv->video_dmaq.queue); 1182 1183 timer_setup(&vv->video_dmaq.timeout, saa7146_buffer_timeout, 0); 1184 vv->video_dmaq.dev = dev; 1185 1186 /* set some default values */ 1187 vv->standard = &dev->ext_vv_data->stds[0]; 1188 1189 /* FIXME: what's this? */ 1190 vv->current_hps_source = SAA7146_HPS_SOURCE_PORT_A; 1191 vv->current_hps_sync = SAA7146_HPS_SYNC_PORT_A; 1192 } 1193 1194 1195 static int video_open(struct saa7146_dev *dev, struct file *file) 1196 { 1197 struct saa7146_fh *fh = file->private_data; 1198 1199 videobuf_queue_sg_init(&fh->video_q, &video_qops, 1200 &dev->pci->dev, &dev->slock, 1201 V4L2_BUF_TYPE_VIDEO_CAPTURE, 1202 V4L2_FIELD_INTERLACED, 1203 sizeof(struct saa7146_buf), 1204 file, &dev->v4l2_lock); 1205 1206 return 0; 1207 } 1208 1209 1210 static void video_close(struct saa7146_dev *dev, struct file *file) 1211 { 1212 struct saa7146_fh *fh = file->private_data; 1213 struct saa7146_vv *vv = dev->vv_data; 1214 struct videobuf_queue *q = &fh->video_q; 1215 1216 if (IS_CAPTURE_ACTIVE(fh) != 0) 1217 video_end(fh, file); 1218 else if (IS_OVERLAY_ACTIVE(fh) != 0) 1219 saa7146_stop_preview(fh); 1220 1221 videobuf_stop(q); 1222 /* hmm, why is this function declared void? */ 1223 } 1224 1225 1226 static void video_irq_done(struct saa7146_dev *dev, unsigned long st) 1227 { 1228 struct saa7146_vv *vv = dev->vv_data; 1229 struct saa7146_dmaqueue *q = &vv->video_dmaq; 1230 1231 spin_lock(&dev->slock); 1232 DEB_CAP("called\n"); 1233 1234 /* only finish the buffer if we have one... */ 1235 if( NULL != q->curr ) { 1236 saa7146_buffer_finish(dev,q,VIDEOBUF_DONE); 1237 } 1238 saa7146_buffer_next(dev,q,0); 1239 1240 spin_unlock(&dev->slock); 1241 } 1242 1243 static ssize_t video_read(struct file *file, char __user *data, size_t count, loff_t *ppos) 1244 { 1245 struct saa7146_fh *fh = file->private_data; 1246 struct saa7146_dev *dev = fh->dev; 1247 struct saa7146_vv *vv = dev->vv_data; 1248 ssize_t ret = 0; 1249 1250 DEB_EE("called\n"); 1251 1252 if ((vv->video_status & STATUS_CAPTURE) != 0) { 1253 /* fixme: should we allow read() captures while streaming capture? */ 1254 if (vv->video_fh == fh) { 1255 DEB_S("already capturing\n"); 1256 return -EBUSY; 1257 } 1258 DEB_S("already capturing in another open\n"); 1259 return -EBUSY; 1260 } 1261 1262 ret = video_begin(fh); 1263 if( 0 != ret) { 1264 goto out; 1265 } 1266 1267 ret = videobuf_read_one(&fh->video_q , data, count, ppos, 1268 file->f_flags & O_NONBLOCK); 1269 if (ret != 0) { 1270 video_end(fh, file); 1271 } else { 1272 ret = video_end(fh, file); 1273 } 1274 out: 1275 /* restart overlay if it was active before */ 1276 if (vv->ov_suspend != NULL) { 1277 saa7146_start_preview(vv->ov_suspend); 1278 vv->ov_suspend = NULL; 1279 } 1280 1281 return ret; 1282 } 1283 1284 const struct saa7146_use_ops saa7146_video_uops = { 1285 .init = video_init, 1286 .open = video_open, 1287 .release = video_close, 1288 .irq_done = video_irq_done, 1289 .read = video_read, 1290 }; 1291