1/* 2 * Copyright 2004-2008, Fran��ois Revol, <revol@free.fr>. 3 * Distributed under the terms of the MIT License. 4 */ 5 6#define CD_COL "31" 7#include "CamDeframer.h" 8#include "CamDevice.h" 9#include "CamDebug.h" 10#include <Autolock.h> 11#define MAX_TAG_LEN CAMDEFRAMER_MAX_TAG_LEN 12#define MAXFRAMEBUF CAMDEFRAMER_MAX_QUEUED_FRAMES 13 14 15CamDeframer::CamDeframer(CamDevice *device) 16 : CamFilterInterface(device), 17 fDevice(device), 18 fState(ST_SYNC), 19 fFrameSem(B_ERROR), 20 fLocker("CamDeframer Framelist lock", true), 21 fSOFTags(NULL), 22 fEOFTags(NULL), 23 fNumSOFTags(0), 24 fNumEOFTags(0), 25 fLenSOFTags(0), 26 fLenEOFTags(0), 27 fSkipSOFTags(0), 28 fSkipEOFTags(0) 29{ 30 fMinFrameSize = fDevice->MinRawFrameSize(); 31 fMaxFrameSize = fDevice->MaxRawFrameSize(); 32 fFrameSem = create_sem(0, "CamDeframer sem"); 33 fCurrentFrame = AllocFrame(); 34} 35 36 37CamDeframer::~CamDeframer() 38{ 39 delete_sem(fFrameSem); 40 BAutolock l(fLocker); 41 delete fCurrentFrame; 42} 43 44 45ssize_t 46CamDeframer::Read(void *buffer, size_t size) 47{ 48 BAutolock l(fLocker); 49 CamFrame *f = (CamFrame *)fFrames.ItemAt(0); 50 if (!f) 51 return EIO; 52 return f->Read(buffer, size); 53} 54 55 56ssize_t 57CamDeframer::ReadAt(off_t pos, void *buffer, size_t size) 58{ 59 BAutolock l(fLocker); 60 CamFrame *f = (CamFrame *)fFrames.ItemAt(0); 61 if (!f) 62 return EIO; 63 return f->ReadAt(pos, buffer, size); 64} 65 66 67off_t 68CamDeframer::Seek(off_t position, uint32 seek_mode) 69{ 70 BAutolock l(fLocker); 71 CamFrame *f = (CamFrame *)fFrames.ItemAt(0); 72 if (!f) 73 return EIO; 74 return f->Seek(position, seek_mode); 75} 76 77 78off_t 79CamDeframer::Position() const 80{ 81 BAutolock l((BLocker &)fLocker); // need to get rid of const here 82 CamFrame *f = (CamFrame *)fFrames.ItemAt(0); 83 if (!f) 84 return EIO; 85 return f->Position(); 86} 87 88 89status_t 90CamDeframer::SetSize(off_t size) 91{ 92 (void)size; 93 return EINVAL; 94} 95 96 97ssize_t 98CamDeframer::Write(const void *buffer, size_t size) 99{ 100 (void)buffer; 101 (void)size; 102 return EINVAL; 103} 104 105 106ssize_t 107CamDeframer::WriteAt(off_t pos, const void *buffer, size_t size) 108{ 109 (void)pos; 110 (void)buffer; 111 (void)size; 112 return EINVAL; 113} 114 115 116status_t 117CamDeframer::WaitFrame(bigtime_t timeout) 118{ 119 return acquire_sem_etc(fFrameSem, 1, B_RELATIVE_TIMEOUT, timeout); 120} 121 122 123status_t 124CamDeframer::GetFrame(CamFrame **frame, bigtime_t *stamp) 125{ 126 PRINT((CH "()" CT)); 127 BAutolock l(fLocker); 128 CamFrame *f = (CamFrame *)fFrames.RemoveItem((int32)0); 129 if (!f) 130 return ENOENT; 131 *frame = f; 132 *stamp = f->Stamp(); 133 return B_OK; 134} 135 136 137status_t 138CamDeframer::DropFrame() 139{ 140 PRINT((CH "()" CT)); 141 BAutolock l(fLocker); 142 CamFrame *f = (CamFrame *)fFrames.RemoveItem((int32)0); 143 if (!f) 144 return ENOENT; 145 delete f; 146 return B_OK; 147} 148 149 150status_t 151CamDeframer::RegisterSOFTags(const uint8 **tags, int count, size_t len, size_t skip) 152{ 153 if (fSOFTags) 154 return EALREADY; 155 if (len > MAX_TAG_LEN) 156 return EINVAL; 157 if (count > 16) 158 return EINVAL; 159 fSOFTags = tags; 160 fNumSOFTags = count; 161 fLenSOFTags = len; 162 fSkipSOFTags = skip; 163 return B_OK; 164} 165 166 167status_t 168CamDeframer::RegisterEOFTags(const uint8 **tags, int count, size_t len, size_t skip) 169{ 170 if (fEOFTags) 171 return EALREADY; 172 if (len > MAX_TAG_LEN) 173 return EINVAL; 174 if (count > 16) 175 return EINVAL; 176 fEOFTags = tags; 177 fNumEOFTags = count; 178 fLenEOFTags = len; 179 fSkipEOFTags = skip; 180 return B_OK; 181} 182 183 184int 185CamDeframer::FindTags(const uint8 *buf, size_t buflen, const uint8 **tags, int tagcount, size_t taglen, size_t skiplen, int *which) 186{ 187 int i, t; 188 for (i = 0; i < (int)(buflen - skiplen + 1); i++) { 189 for (t = 0; t < tagcount; t++) { 190 if (!memcmp(buf+i, tags[t], taglen)) { 191 if (which) 192 *which = t; 193 return i; 194 } 195 } 196 } 197 return -1; 198} 199 200 201int 202CamDeframer::FindSOF(const uint8 *buf, size_t buflen, int *which) 203{ 204 return FindTags(buf, buflen, fSOFTags, fNumSOFTags, fLenSOFTags, fSkipSOFTags, which); 205} 206 207 208int 209CamDeframer::FindEOF(const uint8 *buf, size_t buflen, int *which) 210{ 211 return FindTags(buf, buflen, fEOFTags, fNumEOFTags, fLenEOFTags, fSkipEOFTags, which); 212} 213 214 215CamFrame * 216CamDeframer::AllocFrame() 217{ 218 return new CamFrame(); 219} 220