void Clone_Current_Record_Light( vuint16 inFieldCount, I_Table_Ptr inpSourceTable, I_Table_Ptr inpTargetTable ) { // For each field in target: // for( vuint16 j = 1; j <= inFieldCount; ++j ) { I_Field_Ptr pTargetFld = inpTargetTable->get_Field( j ); FBL_CHECK( pTargetFld ); FBL_CHECK( pTargetFld->get_IsMethod() == false ); // Skip identity: if( pTargetFld->get_Identity() ) continue; I_Field_Ptr pSourceFld = inpSourceTable->get_Field( j ); FBL_CHECK( pSourceFld ); // // Clone DATA: // VALUE_TYPE fldType = pTargetFld->get_Type(); Clone_Current_Value( fldType, pSourceFld, pTargetFld ); } }
void SimpleUnion( ArraySet_Ptr ioSet, ArraySet_Ptr inSet ) { FBL_CHECK( ioSet ); FBL_CHECK( inSet ); vuint32 count = inSet->get_Count(); for( vuint32 i = 0; i < count; ++i ) { REC_ID* p = (REC_ID*) (inSet->begin()+i); ioSet->Append( *p ); } }
// Execute current operation on lists pResList and inListPtr. // It make (pResList op= inListPtr), i.e it don't create additional ArraySet. // ArraySet_Ptr ArraySet::MakeOperation( ArraySet_Ptr inLeftSet, SetOperation inOperation, ArraySet_Ptr inRightSet ) { FBL_CHECK( inLeftSet && inRightSet ); ArraySet_Ptr pNewRes; switch( inOperation ) { case kIntersection: pNewRes = inLeftSet->Intersection( inRightSet ); break; case kUnion: pNewRes = inLeftSet->Union( inRightSet ); break; case kMinus: pNewRes = inLeftSet->Difference( inRightSet ); break; case kXOR: pNewRes = inLeftSet->SymmetricDifference( inRightSet ); break; } return pNewRes; }
flength FileWin::DoGetLengthOfOpened( void ) const { FBL_CHECK(mHandle); #if FBL_LENGTH <= 32 DWORD dw; if(!::GetFileSize(mHandle, &dw)) throw(xOSFileError( (ERROR_TYPE) ::GetLastError() )); return (static_cast<flength>(dw)); #else // IS: 03.03.2008 // http://valentina-db.com/bt/view.php?id=3056 // Commented because GetFileSize returns zero in case file is zero-length. // /* DWORD dwh, dwl; if(!(dwl = ::GetFileSize(mHandle, &dwh))) throw(xOSFileError( (ERROR_TYPE) ::GetLastError() )); return (flength(dwh) << 32) | flength(dwl); */ LARGE_INTEGER res; if( ::GetFileSizeEx(mHandle, &res) == false ) throw(xOSFileError( (ERROR_TYPE) ::GetLastError() )); return (flength(res.HighPart) << 32) | flength(res.LowPart); #endif }
FBL_THREAD_ROUTINE( FBL_Thread_Main_Function, inFBL_Thread_Args ) { // Extract data from parameter: FBL_Thread_Args* pArgs = (FBL_Thread_Args*) inFBL_Thread_Args; FBL_CHECK( pArgs && pArgs->mpStartRoutine ); // "Prepare" steps: // ValentinaThreadInit(); // Run thread routine: // try { pArgs->mpStartRoutine( pArgs->mpArgs ); } catch(...) { // Silently catch any exception since not cautgh exception in the thread cause // application abort. } // "Clearing" steps: // ValentinaThreadShutDown(); return 0; }
int Value_money_null::Compare( const I_Value& inOther, COMPARE_TYPE inCompareType ) const { argused1( inCompareType ); FBL_CHECK( get_Type() == inOther.get_Type() ); // If one of values (this or inOther) have null... if( get_IsNull() ) { if( inOther.get_IsNull() ) return 0; // Both are NULL else return -1; // Any NULL is less then NOT NULL } else { if( inOther.get_IsNull() ) return 1; // Any NOT NULL is greater then NULL else { // ... have not null values - compare them. return Value_money::Compare( inOther ); } } }
StChangeBuildDateForTests::StChangeBuildDateForTests( const char* inNewBuildDate ) { // Simplest -- no nested calls. FBL_CHECK( *gTest_BuildDate == 0 ); strncpy( gTest_BuildDate, inNewBuildDate, 11 ); }
StChangeSpecialBuildForTests::StChangeSpecialBuildForTests( bool inIsBeta ) { // Simplest -- no nested calls. FBL_CHECK( gTest_SpecialBuild == 0 ); gTest_SpecialBuild = inIsBeta ? 2 : 1; }
I_Value* CreateValue_Enum( I_Type_Enumerated_Ptr inpType, vuint16 inFlags, bool inIsRemote ) { FBL_CHECK( inpType ); I_Value* pValue = nullptr; switch( inpType->get_MaxIdentCount() ) { case ENUM_8_IDENT_COUNT: { pValue = (bool(inFlags & fNullable)) ? new Value_enum_null8( inpType ) : new Value_enum8( inpType ); } break; case ENUM_16_IDENT_COUNT: { pValue = (bool(inFlags & fNullable)) ? new Value_enum_null16( inpType ) : new Value_enum16( inpType ); } break; default: { FBL_Throw( xFeatureError( ERR_FEATURE_NOT_SUPPORTED, "Not enum8 or enum16" ) ); } } if( inIsRemote ) pValue->put_IsRemote( inIsRemote ); return pValue; }
void ResourceMonitor::Wait( void ) { // Waiting for a semaphore (no monitored resources state). // mSemaphore.Wait(); // Wait until last task Unregistered. FBL_CHECK( mCount == 0 ); mSemaphore.Post(); // To restore state of monitor. }
void ArraySet::AppendSorted_321( ID_TYPE* inLeftFixedPtr, ID_TYPE* inRightDecrementedPtr ) { ID_TYPE ItemsToAppend = ID_TYPE(inRightDecrementedPtr - inLeftFixedPtr); ID_TYPE ItemsFree = ID_TYPE(mpStorageEnd - mpFinish); if( ItemsToAppend > ItemsFree ) // there is no place, reallocate. { // we have // we need more of that ID_TYPE NewSize = ID_TYPE((mpStorageEnd - mpStart) + (ItemsToAppend - ItemsFree)); Resize( NewSize ); } // COPY data: while( inLeftFixedPtr < inRightDecrementedPtr ) { #if 0 // TODO FIXME. RZ 215-03-03 I have try to add this check, but it is not such simple... Oops // PROBLEM is that we appending SORTED items, but ArraySet can be not sorted itself, so we cannot just compare. // // If we will try do this only if ArraySet is sorted it will work, but another PROBLEM. // I see that Empty ArraySet must have mIsSorted = true. Why not? Now it is false. // So this check will not work anyway if we starting AppendSorted() into empty ArraySet. Ops. // // And when it have one item it is still sorted. // But when we appending OTHER itmes using OTHER not AppendSorted_ algs, then may be // we can check if array is still sorted... #if _FBL_CHECK // in DEBUG MODE, we checking that the next value to append is bigger of prev. if( mIsSorted && mpFinish > mpStart ) // if we have at least one item in ArraySet { FBL_CHECK( *(mpFinish - 1) < *inRightDecrementedPtr ); } #endif // _FBL_CHECK #endif // 0 *mpFinish++ = *inRightDecrementedPtr--; } FBL_CHECK( mpFinish <= mpStorageEnd ); }
void* Thread_Posix::thread_entry_point( void* inArg ) { Thread_Posix* p = reinterpret_cast<Thread_Posix*>(inArg); FBL_CHECK(p); // Since POSIX threads API do not support // natively creation of suspended threads // we need to suspend it by hand ::pthread_mutex_lock(&p->mLock); bool suspend_self = p->mSuspended; ::pthread_mutex_unlock(&p->mLock); if( suspend_self ) { p->Suspend(); } int LocalResult = 0xFFFFFFFF; try { LocalResult = (int) p->ThreadMain(); } catch(...) { // Something is going wrong :( ... FBL_CHECK(0); } ::pthread_mutex_lock(&p->mLock); // Store result p->mExitCode = (vuint32) LocalResult; // Thread identifier has no meaning // from here since thread is exiting. // So null it. p->mThrID = 0; ::pthread_mutex_unlock(&p->mLock); // exit the thread ::pthread_exit( &LocalResult ); return nullptr; }
void Location_Disk_FSSpec::put_FSSpec( const FSSpec* inSpec ) { FBL_CHECK( inSpec != NULL ); mFSSpec = *inSpec; // copy structures here. mSpecExists = true; ForgetObject( mpFullPath ); }
void ArraySet::RemoveAt ( vuint32 inIndex, vuint32 inCount ) { FBL_CHECK( 1 <= inIndex && inIndex <= get_Count() ); // range is 1.. ID_TYPE* p = mpStart + inIndex - 1; memmove( p, p + inCount, (get_Count() - inIndex - inCount + 1) * sizeof(ID_TYPE) ); mpFinish -= inCount; }
StChangeCurrentDateForTests::StChangeCurrentDateForTests( vint32 inY, vuint16 inM, vuint16 inD ) { // Simplest -- no nested calls. // But it is possible implement them if to use private data members. FBL_CHECK( gTest_Year == 0 ); gTest_Year = inY; gTest_Month = inM; gTest_Day = inD; }
FBL_Begin_Namespace /**********************************************************************************************/ void Clone_Current_Value( VALUE_TYPE inFldType, I_Field_Ptr inSourceFld, I_Field_Ptr inTargetFld ) { switch( inFldType ) { case kTypeSound: case kTypeMovie: case kTypeBLOB: // Commented because this way we must read/write TEXT as STRING to avoid // double read/write (we use FirstRecord()/NextRecord() for source table and therefore // src TEXT field already has its value). // case kTypeText: case kTypePicture: { try { if( inSourceFld->get_IsNull() == false ) { I_FldBlob_Ptr sourceBlobFld = QI( inSourceFld, I_FldBlob ); FBL_CHECK( sourceBlobFld ); vuint32 datasize = sourceBlobFld->get_DataSize(); if( datasize ) { MemPtr<char> theData( datasize ); sourceBlobFld->ReadData( theData, datasize ); I_FldBlob_Ptr targetBlobFld = QI( inTargetFld, I_FldBlob ); targetBlobFld->WriteData( theData, datasize ); } else { // Zero data but not sql-NULL. I_FldBlob_Ptr targetBlobFld = QI( inTargetFld, I_FldBlob ); targetBlobFld->WriteData( nullptr, 0 ); } } } catch(...) { } } break; default: { // Common case: inTargetFld->put_Value( inSourceFld->get_Value() ); } break; } }
void ValentinaThreadShutDown( void ) { #if FBL_INTERNAL_THREADSAFE || FBL_EXTERNAL_THREADSAFE vuint64* threadInitCounter = (vuint64*)tlsInitCounter.get(); if( threadInitCounter ) { if( (*threadInitCounter) > 1 ) { // ValentinaThreadShutDown is called, but we just register this fact // instead of real job. (*threadInitCounter)--; } else { // (*threadInitCounter) == 1 // #if FBL_TEST_CODE { StLockGuard<True_Thread_Mutex> lock(gThreadIDArrayMutex); FBL_CHECK( gThreadIDArray ); if( gThreadIDArray ) { #if FBL_WIN gThreadIDArray->RemoveItem( (fbl::vuint64)GetCurrentThreadId() ); #else gThreadIDArray->RemoveItem( (fbl::vuint64)( pthread_self() ) ); #endif //FBL_WIN } } #endif // FBL_TEST_CODE // vKernel stuff. if( pValentinaThreadShutDownEx ) pValentinaThreadShutDownEx(); // "Free" TLS objects (safe even if this thread did not "create" tlsSysLocalizable ). tlsSysLocalizable.SafeRelease(); // "Free" tlsInitCounter object ForgetObject( threadInitCounter ); } tlsInitCounter.set( threadInitCounter ); } else { // Silently ignore - ValentinaThreadShutDown is called before any ValentinaThreadInit. } #endif // FBL_INTERNAL_THREADSAFE || FBL_EXTERNAL_THREADSAFE }
void ResourceMonitor::UnRegister( void ) { StLockGuard<True_Thread_Mutex> g(mMutex); --mCount; FBL_CHECK( mCount >= 0 ); // If no more waitable tasks - switch the semaphore to signaled state (free). // if( mCount == 0 ) mSemaphore.Post(); }
void Thread_Posix::Destroy( Thread_Posix* inThreads[], vuint32 inSize ) { FBL_CHECK(inThreads); if( !inThreads ) return; // spawn it for( vuint32 i = 0; i < inSize; ++i ) { delete inThreads[i]; } }
void ArraySet::InsertItem ( vuint32 inPos, ID_TYPE inItem ) { /*if( mpFinish + 1 >= mpStorageEnd ) // must be place { ID_TYPE NewSize = (mpStorageEnd - mpStart) ? (ID_TYPE)2 * (mpStorageEnd - mpStart) : (ID_TYPE)100; Resize( NewSize ); }*/ vuint32 theCount = get_Count(); FBL_CHECK( mpFinish < mpStorageEnd ); // must be place FBL_CHECK( inPos <= theCount ); ID_TYPE* p = mpStart + inPos; memmove( p + 1, p, (theCount - inPos) * sizeof(ID_TYPE) ); *p = inItem; mpFinish++; mIsSorted = false; }
ArrayOfValues_Ptr GetNotBLOBValues( I_Table_Ptr inTable ) { FBL_CHECK( inTable ); ArrayOfValues_Ptr result; vuint16 fldCount = inTable->get_FieldCount(); if( fldCount ) result = new ArrayOfValues(); for( vuint16 i = 1; i <= fldCount; ++i ) { I_Field_Ptr pField = inTable->get_Field( i ); I_Value_Ptr pValue; switch( pField->get_Type() ) { case kTypeBLOB: case kTypePicture: { ; } break; default: { // IS: 25.02.2008 // http://valentina-db.com/bt/view.php?id=3048 //pValue = pField->get_Value(forAdd); pValue = fbl_const_cast( pField->get_Value() ); FBL_CHECK(pValue); } break; } result->AddItem( pValue ); } return result; }
const char* Value_Raw::AllocCopy( const char* inStart, const char* inEnd ) { FBL_CHECK( inStart <= inEnd ); vuint32 size = vuint32(inEnd - inStart); if( size ) { Alloc( size ); memcpy( m_pStart, inStart, size ); m_pEnd = m_pStart + size; } return m_pStart; }
vuint32 FileWin::DoRead( char* inBuffer, flength inFrom, vuint32 inHowMuch ) { FBL_CHECK(inBuffer); /* pre: read existing information */ FBL_CHECK( inFrom + inHowMuch <= get_Length() ); /* Set file marker to right position */ Seek(inFrom, begin); DWORD Read; if (!::ReadFile(mHandle, inBuffer, inHowMuch, &Read, NULL)) { ERROR_TYPE err = (ERROR_TYPE) ::GetLastError(); throw xOSFileError( err ); } return Read; }
FBL_Begin_Namespace /**********************************************************************************************/ void ResourceMonitor::Register( void ) { StLockGuard<True_Thread_Mutex> g(mMutex); ++mCount; FBL_CHECK( mCount >= 0 ); // First waitable resource switch semaphore to the blocked state. if( mCount == 1 ) mSemaphore.Wait(); }
void SplitHostPort( char* inpSrc, MemPtr<char>* outpHost, vint32& outPort ) { // Caller have to allocate strlen(inpSrc) + 1 bytes for outpHost. // FBL_CHECK( inpSrc ); FBL_CHECK( strlen(inpSrc) == strlen(*outpHost) ); FBL_CHECK( strlen(inpSrc) + 1 == (*outpHost).get_Size() ); size_t buffSize = (*outpHost).get_Size(); memset( (*outpHost).begin(), 0 , buffSize ); // Looking for the last position of ':' in inpString char* pSrcDelim = (char*) strrchr( inpSrc, ':' ); if( pSrcDelim ) { memcpy( (*outpHost).begin(), inpSrc, pSrcDelim - inpSrc ); outPort = atol( pSrcDelim + 1 ); } else { memcpy( (*outpHost).begin(), inpSrc, buffSize ); } }
void Value_Raw::Init( void ) { if( vuint32 Len = get_Allocated() ) { memset( m_pStart, 'a', Len ); m_pEnd = m_pStart + Len; put_IsNull( false ); } else { // We don't go on this way!!! FBL_CHECK( false ); put_IsNull( true ); } }
DirData::DirData( Const_I_Disk_Location_Ptr inDirLocation ) { Const_Location_Disk_FSSpec_Ptr pLocSpec = fbl_dynamic_cast<const Location_Disk_FSSpec>(inDirLocation); const FSSpec* pSpec = pLocSpec->get_FSSpec(); m_CPB.hFileInfo.ioVRefNum = pSpec->vRefNum; m_CPB.hFileInfo.ioNamePtr = m_name; m_index = 0; m_flags = DIR_FILES | DIR_DIRS; OSErr err = FBL::FSpGetDirectoryID( pSpec, &m_dirId , &m_isDir ); FBL_CHECK( err == noErr ); }
FBL_Begin_Namespace /**********************************************************************************************/ Text_Stream_OnFile::Text_Stream_OnFile( I_File_Ptr inFile ) : TBase( inFile ) { // еее // FIXME // mSignatureSize = WriteUnicodeSignature( "UTF-16", inFile ); // signature must be on start of the file. FBL_CHECK( inFile->get_Pos() == 0 ); const vuint8* pSignature = Get_FileSignature_UTF_16( &mSignatureSize ); inFile->Write( (const char*) pSignature, mSignatureSize ); inFile->Flush(); }
ArrayOfSerializable_Ptr GetSerializables( ArrayOfValues_Ptr inpValues ) { FBL_CHECK( inpValues ); ArrayOfSerializable_Ptr result; vuint32 valCount = inpValues->get_Count(); if( valCount ) result = new ArrayOfSerializable(); for( vuint32 i = 1; i <= valCount; ++i ) { I_Value_Ptr pValue = inpValues->get_ItemAt( i ); I_Serializable_Ptr pSerial = (pValue) ? QI(pValue, I_Serializable) : nullptr; result->AddItem( pSerial ); } return result; }
// Can both grow and reduse the size of ArraySet. // Can truncate exisitng data !! // If NewItemsCount is 0 then free memory. // Note, that it requires additional memory buffer during work. // void ArraySet::Resize( vuint32 inNewItemsCount ) { if( inNewItemsCount == 0 && mpStart ) // we want to free memory { FBL_CHECK( get_Size() <= sTotalSize ); sTotalSize -= get_Size(); delete [] mpStart; mpStart = nullptr; mpFinish = nullptr; mpStorageEnd = nullptr; } else { ID_TYPE* pTmp = new ID_TYPE[inNewItemsCount]; // vuint32 MaxCount = get_MaxCount(); vuint32 Count = get_Count(); // Choose a min value: // IF NewItemsCount is less THEN we trucate existing data. Count = (Count < inNewItemsCount) ? Count : inNewItemsCount; if( mpStart ) { memcpy( (char*)pTmp, (char*)mpStart, Count * sizeof(ID_TYPE) ); delete [] mpStart; } // fill by zero rest items if any. memset( pTmp + Count, 0, inNewItemsCount - Count ); mpStart = pTmp; mpFinish = mpStart + Count; mpStorageEnd = mpStart + inNewItemsCount; // CORRECT counter using +/- diff value. vint32 diff = (inNewItemsCount > Count) ? + (vint32)(inNewItemsCount - Count) : - (vint32)(Count - inNewItemsCount); sTotalSize += diff * sizeof(ID_TYPE); } }