DBResult MyBasicResults::CopyBlob(unsigned int columnId, void *buffer, size_t maxlength, size_t *written) { const void *addr; size_t length; DBResult res; if ((res = GetBlob(columnId, &addr, &length)) == DBVal_Error) { return DBVal_Error; } if (addr == NULL) { return DBVal_Null; } if (length > maxlength) { length = maxlength; } memcpy(buffer, addr, length); if (written) { *written = length; } return res; }
/* Update all blob models: */ void CvBlobTracker::Update(IplImage* pImg, IplImage* pImgFG) { int i; for(i=GetBlobNum();i>0;i--) { CvBlob* pB=GetBlob(i-1); UpdateBlob(i-1, pB, pImg, pImgFG); } }
/* Return pointer to blob by its unique ID: */ int CvBlobTracker::GetBlobIndexByID(int BlobID) { int i; for(i=GetBlobNum();i>0;i--) { CvBlob* pB=GetBlob(i-1); if(CV_BLOB_ID(pB) == BlobID) return i-1; } return -1; }
/* Process one blob (for multi hypothesis tracing): */ void CvBlobTracker::ProcessBlob(int BlobIndex, CvBlob* pBlob, IplImage* /*pImg*/, IplImage* /*pImgFG*/) { CvBlob* pB; int ID = 0; assert(pBlob); //pBlob->ID; pB = GetBlob(BlobIndex); if(pB) pBlob[0] = pB[0]; pBlob->ID = ID; }
/* - FUNCTION: GetNthBlob - FUNCTIONALITY: Gets the n-th blob ordering first the blobs with some criteria - PARAMETERS: - criteri: criteria to order the blob array - nBlob: index of the returned blob in the ordered blob array - dst: where to store the result - RESULT: - RESTRICTIONS: - AUTHOR: Ricard Borr�s - CREATION DATE: 25-05-2005. - MODIFICATION: Date. Author. Description. */ void CBlobResult::GetNthBlob( funcio_calculBlob* criteri, int nBlob, CBlob& dst ) const { // verifiquem que no estem accedint fora el vector de blobs if ( nBlob < 0 || nBlob >= GetNumBlobs() ) { //RaiseError( EXCEPTION_BLOB_OUT_OF_BOUNDS ); dst = CBlob(); return; } double_stl_vector avaluacioBlobs, avaluacioBlobsOrdenat; double valorEnessim; //avaluem els blobs amb la funci� pertinent avaluacioBlobs = GetSTLResult(criteri); avaluacioBlobsOrdenat = double_stl_vector( GetNumBlobs() ); // obtenim els nBlob primers resultats (en ordre descendent) std::partial_sort_copy( avaluacioBlobs.begin(), avaluacioBlobs.end(), avaluacioBlobsOrdenat.begin(), avaluacioBlobsOrdenat.end(), std::greater<double>() ); valorEnessim = avaluacioBlobsOrdenat[nBlob]; // busquem el primer blob que t� el valor n-ssim double_stl_vector::const_iterator itAvaluacio = avaluacioBlobs.begin(); bool trobatBlob = false; int indexBlob = 0; while ( itAvaluacio != avaluacioBlobs.end() && !trobatBlob ) { if ( *itAvaluacio == valorEnessim ) { trobatBlob = true; dst = CBlob( GetBlob(indexBlob)); } ++itAvaluacio; ++indexBlob; } }
/** - FUNCTION: Filter - FUNCTIONALITY: Get some blobs from the class based on conditions on measures of the blobs. - PARAMETERS: - dst: where to store the selected blobs - filterAction: B_INCLUDE: include the blobs which pass the filter in the result B_EXCLUDE: exclude the blobs which pass the filter in the result - evaluador: Object to evaluate the blob - Condition: How to decide if the result returned by evaluador on each blob is included or not. It can be: B_EQUAL,B_NOT_EQUAL,B_GREATER,B_LESS,B_GREATER_OR_EQUAL, B_LESS_OR_EQUAL,B_INSIDE,B_OUTSIDE - LowLimit: numerical value to evaluate the Condition on evaluador(blob) - HighLimit: numerical value to evaluate the Condition on evaluador(blob). Only useful for B_INSIDE and B_OUTSIDE - RESULT: - It returns on dst the blobs that accomplish (B_INCLUDE) or discards (B_EXCLUDE) the Condition on the result returned by evaluador on each blob - RESTRICTIONS: - AUTHOR: Ricard Borràs - CREATION DATE: 25-05-2005. - MODIFICATION: Date. Author. Description. */ void CBlobResult::Filter(CBlobResult &dst, int filterAction, funcio_calculBlob *evaluador, int condition, double lowLimit, double highLimit /*=0*/) { int i, numBlobs; bool resultavaluacio; double_stl_vector avaluacioBlobs; double_stl_vector::iterator itavaluacioBlobs; if( GetNumBlobs() <= 0 ) return; if( !evaluador ) return; //avaluem els blobs amb la funció pertinent avaluacioBlobs = GetSTLResult(evaluador); itavaluacioBlobs = avaluacioBlobs.begin(); numBlobs = GetNumBlobs(); switch(condition) { case B_EQUAL: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio= *itavaluacioBlobs == lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_NOT_EQUAL: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio = *itavaluacioBlobs != lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_GREATER: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio= *itavaluacioBlobs > lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_LESS: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio= *itavaluacioBlobs < lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_GREATER_OR_EQUAL: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio= *itavaluacioBlobs>= lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_LESS_OR_EQUAL: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio= *itavaluacioBlobs <= lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_INSIDE: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio=( *itavaluacioBlobs >= lowLimit) && ( *itavaluacioBlobs <= highLimit); if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_OUTSIDE: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio=( *itavaluacioBlobs < lowLimit) || ( *itavaluacioBlobs > highLimit); if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; } // en cas de voler filtrar un CBlobResult i deixar-ho en el mateix CBlobResult // ( operacio inline ) if( &dst == this ) { // esborrem els primers blobs ( que són els originals ) // ja que els tindrem replicats al final si passen el filtre blob_vector::iterator itBlobs = m_blobs.begin(); for( int i = 0; i < numBlobs; i++ ) { delete *itBlobs; itBlobs++; } m_blobs.erase( m_blobs.begin(), itBlobs ); } }
/** * check whether a directory object is ok. * * @param[in] file opaque pointer to directory object fid * * @return operation status * @retval 1 dir is fine, or something went wrong checking * @retval 0 we *know* that the dir is bad */ int DirOK(void *file) { struct DirHeader *dhp; struct PageHeader *pp; struct DirEntry *ep; int i, j, k, up; int havedot = 0, havedotdot = 0; int usedPages, count, entry; char eaMap[BIGMAXPAGES * EPP / 8]; /* Change eaSize initialization below, too. */ int eaSize; afs_int32 entcount, maxents; unsigned short ne; eaSize = BIGMAXPAGES * EPP / 8; /* Read the directory header */ dhp = (struct DirHeader *)DRead(file, 0); if (!dhp) { /* if DErrno is 0, then we know that the read worked, but was short, * and the damage is permanent. Otherwise, we got an I/O or programming * error. Claim the dir is OK, but log something. */ if (DErrno != 0) { printf("Could not read first page in directory (%d)\n", DErrno); Die("dirok1"); return 1; } printf("First page in directory does not exist.\n"); return 0; } /* Check magic number for first page */ if (dhp->header.tag != htons(1234)) { printf("Bad first pageheader magic number.\n"); DRelease(dhp, 0); return 0; } /* Verify that the number of free entries in each directory page * is within range (0-EPP). Also ensure directory is contiguous: * Once the first alloMap entry with EPP free entries is found, * the rest should match. */ up = 0; /* count of used pages if total pages < MAXPAGES */ k = 0; /* found last page */ for (i = 0; i < MAXPAGES; i++) { j = dhp->alloMap[i]; /* Check if in range */ if (i == 0) { if ((j < 0) || (j > EPP - (13 + 2))) { /* First page's dirheader uses 13 entries and at least * two must exist for "." and ".." */ printf("The dir header alloc map for page %d is bad.\n", i); DRelease(dhp, 0); return 0; } } else { if ((j < 0) || (j > EPP)) { printf("The dir header alloc map for page %d is bad.\n", i); DRelease(dhp, 0); return 0; } } /* Check if contiguous */ if (k) { /* last page found */ if (j != EPP) { /* remaining entries must be EPP */ printf ("A partially-full page occurs in slot %d, after the dir end.\n", i); DRelease(dhp, 0); return 0; } } else if (j == EPP) { /* is this the last page */ k = 1; /* yes */ } else { /* a used page */ up++; /* keep count */ } } /* Compute number of used directory pages and max entries in all ** those pages, the value of 'up' must be less than pgcount. The above ** loop only checks the first MAXPAGES in a directory. An alloMap does ** not exists for pages between MAXPAGES and BIGMAXPAGES */ usedPages = ComputeUsedPages(dhp); if (usedPages < up) { printf ("Count of used directory pages does not match count in directory header\n"); DRelease(dhp, 0); return 0; } /* For each directory page, check the magic number in each page * header, and check that number of free entries (from freebitmap) * matches the count in the alloMap from directory header. */ for (i = 0; i < usedPages; i++) { /* Read the page header */ pp = (struct PageHeader *)DRead(file, i); if (!pp) { DRelease(dhp, 0); if (DErrno != 0) { /* couldn't read page, but not because it wasn't there permanently */ printf("Failed to read dir page %d (errno %d)\n", i, DErrno); Die("dirok2"); return 1; } printf("Directory shorter than alloMap indicates (page %d)\n", i); return 0; } /* check the tag field */ if (pp->tag != htons(1234)) { printf("Directory page %d has a bad magic number.\n", i); DRelease(pp, 0); DRelease(dhp, 0); return 0; } /* Count the number of entries allocated in this single * directory page using the freebitmap in the page header. */ count = 0; for (j = 0; j < EPP / 8; j++) { k = pp->freebitmap[j]; if (k & 0x80) count++; if (k & 0x40) count++; if (k & 0x20) count++; if (k & 0x10) count++; if (k & 0x08) count++; if (k & 0x04) count++; if (k & 0x02) count++; if (k & 0x01) count++; } count = EPP - count; /* Change to count of free entries */ /* Now check that the count of free entries matches the count in the alloMap */ if ((i < MAXPAGES) && ((count & 0xff) != (dhp->alloMap[i] & 0xff))) { printf ("Header alloMap count doesn't match count in freebitmap for page %d.\n", i); DRelease(pp, 0); DRelease(dhp, 0); return 0; } DRelease(pp, 0); } /* Initialize the in-memory freebit map for all pages. */ for (i = 0; i < eaSize; i++) { eaMap[i] = 0; if (i < usedPages * (EPP / 8)) { if (i == 0) { eaMap[i] = 0xff; /* A dir header uses first 13 entries */ } else if (i == 1) { eaMap[i] = 0x1f; /* A dir header uses first 13 entries */ } else if ((i % 8) == 0) { eaMap[i] = 0x01; /* A page header uses only first entry */ } } } maxents = usedPages * EPP; /* Walk down all the hash lists, ensuring that each flag field has FFIRST * in it. Mark the appropriate bits in the in-memory freebit map. * Check that the name is in the right hash bucket. * Also check for loops in the hash chain by counting the entries. */ for (entcount = 0, i = 0; i < NHASHENT; i++) { for (entry = ntohs(dhp->hashTable[i]); entry; entry = ne) { /* Verify that the entry is within range */ if (entry < 0 || entry >= maxents) { printf("Out-of-range hash id %d in chain %d.\n", entry, i); DRelease(dhp, 0); return 0; } /* Read the directory entry */ DErrno = 0; ep = GetBlob(file, entry); if (!ep) { if (DErrno != 0) { /* something went wrong reading the page, but it wasn't * really something wrong with the dir that we can fix. */ printf("Could not get dir blob %d (errno %d)\n", entry, DErrno); DRelease(dhp, 0); Die("dirok3"); } printf("Invalid hash id %d in chain %d.\n", entry, i); DRelease(dhp, 0); return 0; } ne = ntohs(ep->next); /* There can't be more than maxents entries */ if (++entcount >= maxents) { printf("Directory's hash chain %d is circular.\n", i); DRelease(ep, 0); DRelease(dhp, 0); return 0; } /* A null name is no good */ if (ep->name[0] == '\000') { printf("Dir entry %x in chain %d has bogus (null) name.\n", (intptr_t)ep, i); DRelease(ep, 0); DRelease(dhp, 0); return 0; } /* The entry flag better be FFIRST */ if (ep->flag != FFIRST) { printf("Dir entry %x in chain %d has bogus flag field.\n", (intptr_t)ep, i); DRelease(ep, 0); DRelease(dhp, 0); return 0; } /* Check the size of the name */ j = strlen(ep->name); if (j >= MAXENAME) { /* MAXENAME counts the null */ printf("Dir entry %x in chain %d has too-long name.\n", (intptr_t)ep, i); DRelease(ep, 0); DRelease(dhp, 0); return 0; } /* The name used up k directory entries, set the bit in our in-memory * freebitmap for each entry used by the name. */ k = NameBlobs(ep->name); for (j = 0; j < k; j++) { eaMap[(entry + j) >> 3] |= (1 << ((entry + j) & 7)); } /* Hash the name and make sure it is in the correct name hash */ if ((j = DirHash(ep->name)) != i) { printf ("Dir entry %x should be in hash bucket %d but IS in %d.\n", (intptr_t)ep, j, i); DRelease(ep, 0); DRelease(dhp, 0); return 0; } /* Check that if this is entry 13 (the 1st entry), then name must be "." */ if (entry == 13) { if (strcmp(ep->name, ".") == 0) { havedot = 1; } else { printf ("Dir entry %x, index 13 has name '%s' should be '.'\n", (intptr_t)ep, ep->name); DRelease(ep, 0); DRelease(dhp, 0); return 0; } } /* Check that if this is entry 14 (the 2nd entry), then name must be ".." */ if (entry == 14) { if (strcmp(ep->name, "..") == 0) { havedotdot = 1; } else { printf ("Dir entry %x, index 14 has name '%s' should be '..'\n", (intptr_t)ep, ep->name); DRelease(ep, 0); DRelease(dhp, 0); return 0; } } /* CHECK FOR DUPLICATE NAMES? */ DRelease(ep, 0); } } /* Verify that we found '.' and '..' in the correct place */ if (!havedot || !havedotdot) { printf ("Directory entry '.' or '..' does not exist or is in the wrong index.\n"); DRelease(dhp, 0); return 0; } /* The in-memory freebit map has been computed. Check that it * matches the one in the page header. * Note that if this matches, alloMap has already been checked against it. */ for (i = 0; i < usedPages; i++) { pp = DRead(file, i); if (!pp) { printf ("Failed on second attempt to read dir page %d (errno %d)\n", i, DErrno); DRelease(dhp, 0); /* if DErrno is 0, then the dir is really bad, and we return dir *not* OK. * otherwise, we want to return true (1), meaning the dir isn't known * to be bad (we can't tell, since I/Os are failing. */ if (DErrno != 0) Die("dirok4"); else return 0; /* dir is really shorter */ } count = i * (EPP / 8); for (j = 0; j < EPP / 8; j++) { if (eaMap[count + j] != pp->freebitmap[j]) { printf ("Entry freebitmap error, page %d, map offset %d, %x should be %x.\n", i, j, pp->freebitmap[j], eaMap[count + j]); DRelease(pp, 0); DRelease(dhp, 0); return 0; } } DRelease(pp, 0); } /* Finally cleanup and return. */ DRelease(dhp, 0); return 1; }
/** * Salvage a directory object. * * @param[in] fromFile fid of original, currently suspect directory object * @param[in] toFile fid where salvager will place new, fixed directory * @param[in] vn vnode of currently suspect directory * @param[in] vu uniquifier of currently suspect directory * @param[in] pvn vnode of parent directory * @param[in] pvu uniquifier of parent directory * * @return operation status * @retval 0 success */ int DirSalvage(void *fromFile, void *toFile, afs_int32 vn, afs_int32 vu, afs_int32 pvn, afs_int32 pvu) { /* First do a MakeDir on the target. */ afs_int32 dot[3], dotdot[3], lfid[3], code, usedPages; char tname[256]; register int i; register char *tp; struct DirHeader *dhp; struct DirEntry *ep; int entry; memset(dot, 0, sizeof(dot)); memset(dotdot, 0, sizeof(dotdot)); dot[1] = vn; dot[2] = vu; dotdot[1] = pvn; dotdot[2] = pvu; MakeDir(toFile, dot, dotdot); /* Returns no error code. */ /* Find out how many pages are valid, using stupid heuristic since DRead * never returns null. */ dhp = (struct DirHeader *)DRead(fromFile, 0); if (!dhp) { printf("Failed to read first page of fromDir!\n"); /* if DErrno != 0, then our call failed and we should let our * caller know that there's something wrong with the new dir. If not, * then we return here anyway, with an empty, but at least good, directory. */ return DErrno; } usedPages = ComputeUsedPages(dhp); /* Finally, enumerate all the entries, doing a create on them. */ for (i = 0; i < NHASHENT; i++) { entry = ntohs(dhp->hashTable[i]); while (1) { if (!entry) break; if (entry < 0 || entry >= usedPages * EPP) { printf ("Warning: bogus hash table entry encountered, ignoring.\n"); break; } DErrno = 0; ep = GetBlob(fromFile, entry); if (!ep) { if (DErrno) { printf ("can't continue down hash chain (entry %d, errno %d)\n", entry, DErrno); DRelease(dhp, 0); return DErrno; } printf ("Warning: bogus hash chain encountered, switching to next.\n"); break; } strncpy(tname, ep->name, MAXENAME); tname[MAXENAME - 1] = '\000'; /* just in case */ tp = tname; entry = ntohs(ep->next); if ((strcmp(tp, ".") != 0) && (strcmp(tp, "..") != 0)) { lfid[1] = ntohl(ep->fid.vnode); lfid[2] = ntohl(ep->fid.vunique); code = Create(toFile, tname, lfid); if (code) { printf ("Create of %s returned code %d, skipping to next hash chain.\n", tname, code); DRelease(ep, 0); break; } } DRelease(ep, 0); } } /* Clean up things. */ DRelease(dhp, 0); return 0; }
//! Does the Filter method job void CBlobResult::DoFilter(CBlobResult &dst, int filterAction, funcio_calculBlob *evaluador, int condition, double lowLimit, double highLimit/* = 0*/) const { int i, numBlobs; bool resultavaluacio; double_stl_vector avaluacioBlobs; double_stl_vector::iterator itavaluacioBlobs; if( GetNumBlobs() <= 0 ) return; if( !evaluador ) return; //avaluem els blobs amb la funció pertinent avaluacioBlobs = GetSTLResult(evaluador); itavaluacioBlobs = avaluacioBlobs.begin(); numBlobs = GetNumBlobs(); switch(condition) { case B_EQUAL: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio= *itavaluacioBlobs == lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_NOT_EQUAL: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio = *itavaluacioBlobs != lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_GREATER: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio= *itavaluacioBlobs > lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_LESS: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio= *itavaluacioBlobs < lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_GREATER_OR_EQUAL: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio= *itavaluacioBlobs>= lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_LESS_OR_EQUAL: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio= *itavaluacioBlobs <= lowLimit; if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_INSIDE: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio=( *itavaluacioBlobs >= lowLimit) && ( *itavaluacioBlobs <= highLimit); if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; case B_OUTSIDE: for(i=0;i<numBlobs;i++, itavaluacioBlobs++) { resultavaluacio=( *itavaluacioBlobs < lowLimit) || ( *itavaluacioBlobs > highLimit); if( ( resultavaluacio && filterAction == B_INCLUDE ) || ( !resultavaluacio && filterAction == B_EXCLUDE )) { dst.m_blobs.push_back( new CBlob( GetBlob( i ) )); } } break; } }
/* Return pointer to specified blob hypothesis by index blob: */ CvBlob* CvBlobTracker::GetBlobHyp(int BlobIndex, int /*hypothesis*/) { return GetBlob(BlobIndex); }
/* Return pointer to blob by its unique ID: */ CvBlob* CvBlobTracker::GetBlobByID(int BlobID) { return GetBlob(GetBlobIndexByID(BlobID)); }