stk11xx-buf.c

Go to the documentation of this file.
00001 
00034 #include <linux/module.h>
00035 #include <linux/init.h>
00036 #include <linux/kernel.h>
00037 #include <linux/errno.h>
00038 #include <linux/slab.h>
00039 #include <linux/kref.h>
00040 #include <linux/vmalloc.h>
00041 
00042 #include <linux/usb.h>
00043 //#include <linux/videodev2.h>
00044 #include <media/v4l2-common.h>
00045 
00046 #include "stk11xx.h"
00047 
00048 
00053 static int default_nbrframebuf = 3;
00054 
00055 
00065 void * stk11xx_rvmalloc(unsigned long size)
00066 {
00067     void *mem;
00068     unsigned long addr;
00069 
00070     size = PAGE_ALIGN(size);
00071     mem = vmalloc_32(size);
00072 
00073     if (!mem)
00074         return NULL;
00075 
00076     memset(mem, 0, size);
00077 
00078     addr = (unsigned long) mem;
00079 
00080     while (size > 0) {
00081         SetPageReserved(vmalloc_to_page((void *) addr));
00082         addr += PAGE_SIZE;
00083         size -= PAGE_SIZE;
00084     }
00085 
00086     return mem;
00087 }
00088 
00089 
00098 void stk11xx_rvfree(void *mem, unsigned long size)
00099 {
00100     unsigned long addr;
00101 
00102     if (!mem)
00103         return;
00104 
00105     addr = (unsigned long) mem;
00106 
00107     while ((long) size > 0) {
00108         ClearPageReserved(vmalloc_to_page((void *) addr));
00109         addr += PAGE_SIZE;
00110         size -= PAGE_SIZE;
00111     }
00112 
00113     vfree(mem);
00114 }
00115 
00116 
00126 int stk11xx_allocate_buffers(struct usb_stk11xx *dev)
00127 {
00128     int i;
00129     void *kbuf;
00130 
00131     STK_DEBUG("Allocate video buffers\n");
00132 
00133     if (dev == NULL)
00134         return -ENXIO;
00135 
00136     // Allocate isochronous pipe buffers
00137     for (i=0; i<MAX_ISO_BUFS; i++) {
00138         if (dev->isobuf[i].data == NULL) {
00139             kbuf = kzalloc(ISO_BUFFER_SIZE, GFP_KERNEL);
00140 
00141             if (kbuf == NULL) {
00142                 STK_ERROR("Failed to allocate iso buffer %d\n", i);
00143                 return -ENOMEM;
00144             }
00145 
00146             STK_DEBUG("Allocated iso buffer at %p\n", kbuf);
00147 
00148             dev->isobuf[i].data = kbuf;
00149         }
00150     }
00151 
00152     // Allocate frame buffer structure
00153     if (dev->framebuf == NULL) {
00154         kbuf = kzalloc(default_nbrframebuf * sizeof(struct stk11xx_frame_buf), GFP_KERNEL);
00155 
00156         if (kbuf == NULL) {
00157             STK_ERROR("Failed to allocate frame buffer structure\n");
00158             return -ENOMEM;
00159         }
00160 
00161         STK_DEBUG("Allocated frame buffer structure at %p\n", kbuf);
00162 
00163         dev->framebuf = kbuf;
00164     }
00165 
00166     // Create frame buffers and make circular ring
00167     for (i=0; i<default_nbrframebuf; i++) {
00168         if (dev->framebuf[i].data == NULL) {
00169             kbuf = vmalloc(STK11XX_FRAME_SIZE);
00170 
00171             if (kbuf == NULL) {
00172                 STK_ERROR("Failed to allocate frame buffer %d\n", i);
00173                 return -ENOMEM;
00174             }
00175 
00176             STK_DEBUG("Allocated frame buffer %d at %p.\n", i, kbuf);
00177 
00178             dev->framebuf[i].data = kbuf;
00179             memset(kbuf, 0, STK11XX_FRAME_SIZE);
00180         }
00181     }
00182 
00183     // Allocate image buffer; double buffer for mmap()
00184     kbuf = stk11xx_rvmalloc(dev->nbuffers * dev->len_per_image);
00185 
00186     if (kbuf == NULL) {
00187         STK_ERROR("Failed to allocate image buffer(s). needed (%d)\n",
00188                 dev->nbuffers * dev->len_per_image);
00189         return -ENOMEM;
00190     }
00191 
00192     STK_DEBUG("Allocated image buffer at %p\n", kbuf);
00193 
00194     dev->image_data = kbuf;
00195 
00196     for (i = 0; i < dev->nbuffers; i++) {
00197         dev->images[i].offset = i * dev->len_per_image;
00198         dev->images[i].vma_use_count = 0;
00199     }
00200 
00201     for (; i < STK11XX_MAX_IMAGES; i++)
00202         dev->images[i].offset = 0;
00203 
00204     kbuf = NULL;
00205     
00206     return 0;
00207 }
00208 
00209 
00219 int stk11xx_reset_buffers(struct usb_stk11xx *dev)
00220 {
00221     int i;
00222     unsigned long flags;
00223 
00224     STK_DEBUG("Reset all buffers\n");
00225 
00226     spin_lock_irqsave(&dev->spinlock, flags);
00227 
00228     dev->full_frames = NULL;
00229     dev->full_frames_tail = NULL;
00230 
00231     for (i=0; i<dev->nbuffers; i++) {
00232         dev->framebuf[i].filled = 0;
00233         dev->framebuf[i].errors = 0;
00234 
00235         if (i > 0)
00236             dev->framebuf[i].next = &dev->framebuf[i - 1];
00237         else
00238             dev->framebuf->next = NULL;
00239     }
00240 
00241     dev->empty_frames = &dev->framebuf[dev->nbuffers - 1];
00242     dev->empty_frames_tail = dev->framebuf;
00243     dev->read_frame = NULL;
00244     dev->fill_frame = dev->empty_frames;
00245     dev->empty_frames = dev->empty_frames->next;
00246 
00247     dev->image_read_pos = 0;
00248     dev->fill_image = 0;
00249 
00250     spin_unlock_irqrestore(&dev->spinlock, flags);
00251 
00252     for (i=0; i<dev->nbuffers; i++)
00253         dev->image_used[i] = 0;
00254     
00255     return 0;
00256 }
00257 
00258 
00259 int stk11xx_clear_buffers(struct usb_stk11xx *dev)
00260 {
00261     memset(dev->image_data, 0x00, dev->nbuffers * dev->len_per_image);
00262 
00263     return 0;
00264 }
00265 
00266 
00276 int stk11xx_free_buffers(struct usb_stk11xx *dev)
00277 {
00278     int i;
00279 
00280     STK_DEBUG("Free buffers\n");
00281 
00282     if (dev == NULL)
00283         return -1;
00284 
00285     // Release iso pipe buffers
00286     for (i=0; i<MAX_ISO_BUFS; i++) {
00287         if (dev->isobuf[i].data != NULL) {
00288             kfree(dev->isobuf[i].data);
00289             dev->isobuf[i].data = NULL;
00290         }
00291     }
00292 
00293     // Release frame buffers
00294     if (dev->framebuf != NULL) {
00295         for (i=0; i<default_nbrframebuf; i++) {
00296             if (dev->framebuf[i].data != NULL) {
00297                 vfree(dev->framebuf[i].data);
00298                 dev->framebuf[i].data = NULL;
00299             }
00300         }
00301 
00302         kfree(dev->framebuf);
00303         dev->framebuf = NULL;
00304     }
00305 
00306     // Release image buffers
00307     if (dev->image_data != NULL)
00308         stk11xx_rvfree(dev->image_data, dev->nbuffers * dev->len_per_image);
00309 
00310     dev->image_data = NULL;
00311 
00312     return 0;
00313 }
00314 
00315 
00323 void stk11xx_next_image(struct usb_stk11xx *dev)
00324 {
00325     STK_STREAM("Select next image\n");
00326 
00327     dev->image_used[dev->fill_image] = 0;
00328     dev->fill_image = (dev->fill_image + 1) % dev->nbuffers;
00329 }
00330 
00331 
00341 int stk11xx_next_frame(struct usb_stk11xx *dev)
00342 {
00343     int ret = 0;
00344     unsigned long flags;
00345 
00346     STK_STREAM("Select next frame\n");
00347 
00348     spin_lock_irqsave(&dev->spinlock, flags);
00349 
00350     if (dev->fill_frame != NULL) {
00351         if (dev->full_frames == NULL) {
00352             dev->full_frames = dev->fill_frame;
00353             dev->full_frames_tail = dev->full_frames;
00354         }
00355         else {
00356             dev->full_frames_tail->next = dev->fill_frame;
00357             dev->full_frames_tail = dev->fill_frame;
00358         }
00359     }
00360 
00361     if (dev->empty_frames != NULL) {
00362         dev->fill_frame = dev->empty_frames;
00363         dev->empty_frames = dev->empty_frames->next;
00364     }
00365     else {
00366         if (dev->full_frames == NULL) {
00367             STK_ERROR("Neither empty or full frames available!\n");
00368             spin_unlock_irqrestore(&dev->spinlock, flags);
00369             return -EINVAL;
00370         }
00371 
00372         dev->fill_frame = dev->full_frames;
00373         dev->full_frames = dev->full_frames->next;
00374 
00375         ret = 1;
00376     }
00377 
00378     dev->fill_frame->next = NULL;
00379 
00380     spin_unlock_irqrestore(&dev->spinlock, flags);
00381 
00382     return ret;
00383 }
00384 
00385 
00396 int stk11xx_handle_frame(struct usb_stk11xx *dev)
00397 {
00398     int ret = 0;
00399     unsigned long flags;
00400 
00401     STK_STREAM("Sync Handle Frame\n");
00402 
00403     spin_lock_irqsave(&dev->spinlock, flags);
00404 
00405     if (dev->read_frame != NULL) {
00406         spin_unlock_irqrestore(&dev->spinlock, flags);
00407         return ret;
00408     }
00409 
00410     if (dev->full_frames == NULL) {
00411     }
00412     else {
00413         dev->read_frame = dev->full_frames;
00414         dev->full_frames = dev->full_frames->next;
00415         dev->read_frame->next = NULL;
00416     }
00417 
00418     if (dev->read_frame != NULL) {
00419         spin_unlock_irqrestore(&dev->spinlock, flags);
00420         ret = stk11xx_decompress(dev);
00421         spin_lock_irqsave(&dev->spinlock, flags);
00422 
00423         if (dev->empty_frames == NULL) {
00424             dev->empty_frames = dev->read_frame;
00425             dev->empty_frames_tail = dev->empty_frames;
00426         }
00427         else {
00428             dev->empty_frames_tail->next = dev->read_frame;
00429             dev->empty_frames_tail = dev->read_frame;
00430         }
00431 
00432         dev->read_frame = NULL;
00433     }
00434 
00435     spin_unlock_irqrestore(&dev->spinlock, flags);
00436 
00437     dev_stk11xx_watchdog_camera(dev);
00438 
00439     return ret;
00440 }
00441 

Generated on Tue Oct 2 06:18:12 2007 for SyntekUSBVideoCamera by  doxygen 1.5.3