Example #1
0
bool CoinQBlockTreeSqlite3::insertHeader(const Coin::CoinBlockHeader& header)
{
    if (!db.isOpen()) {
        throw std::runtime_error("Database is not open.");
    }

    std::stringstream sql;
    SQLite3Stmt stmt;

    sql << "SELECT `height`, `chain_work`, `version`, `timestamp`, `bits`"
        << " FROM `block_headers` WHERE `hash` = '" << header.prevBlockHash.getHex() << "'";
    stmt.prepare(db, sql.str());
    if (stmt.step() != SQLITE_ROW) {
        throw std::runtime_error("Parent not found.");
    }

    // TODO: validate header

    ChainHeader chainHeader(header);
    chainHeader.height = stmt.getInt(0) + 1;
    chainHeader.chainWork.setDec((char*)stmt.getText(1));
    chainHeader.chainWork += chainHeader.getWork();
    std::string chainHeaderHashStr = chainHeader.getHashLittleEndian().getHex();

    SQLite3Tx sqliteTx(db, SQLite3Tx::Type::IMMEDIATE);
    stmt.finalize(); sql.str("");
    sql << "INSERT INTO `block_headers` (`hash`, `in_best_chain`, `height`, `chain_work`, `version`, `prev_block_hash`, `merkle_root`, `timestamp`, `bits`, `nonce`)"
        << " VALUES ('"
        << chainHeaderHashStr << "',0,"
        << chainHeader.height << ",'"
        << chainHeader.chainWork.getDec() << "',"
        << chainHeader.version << ",'"
        << chainHeader.prevBlockHash.getHex() << "','"
        << chainHeader.merkleRoot.getHex() << "',"
        << chainHeader.timestamp << ","
        << chainHeader.bits << ","
        << chainHeader.nonce << ")";
    stmt.prepare(db, sql.str());
    try {
        stmt.step();
        notifyInsert(chainHeader);
    }
    catch (const SQLite3Exception& e) {
        if (e.code() == SQLITE_CONSTRAINT) return false;
        throw e;
    }

    if (chainHeader.chainWork > getTotalWork()) {
        setBestChain(chainHeaderHashStr);
    }

    sqliteTx.commit();
    return true;
}
U_NAMESPACE_BEGIN

void MorphTableHeader::process(const LETableReference &base, LEGlyphStorage &glyphStorage, LEErrorCode &success) const
{
  le_uint32 chainCount = SWAPL(this->nChains);
  LEReferenceTo<ChainHeader> chainHeader(base, success, chains); // moving header
    LEReferenceToArrayOf<ChainHeader> chainHeaderArray(base, success, chains, chainCount);
    le_uint32 chain;

    for (chain = 0; LE_SUCCESS(success) && (chain < chainCount); chain += 1) {
        if (chain > 0) {
            le_uint32 chainLength = SWAPL(chainHeader->chainLength);
            if (chainLength & 0x03) { // incorrect alignment for 32 bit tables
                success = LE_MEMORY_ALLOCATION_ERROR; // as good a choice as any
                return;
            }
            chainHeader.addOffset(chainLength, success);
        }
        FeatureFlags defaultFlags = SWAPL(chainHeader->defaultFlags);
        le_int16 nFeatureEntries = SWAPW(chainHeader->nFeatureEntries);
        le_int16 nSubtables = SWAPW(chainHeader->nSubtables);
        LEReferenceTo<MorphSubtableHeader> subtableHeader =
          LEReferenceTo<MorphSubtableHeader>(chainHeader,success, &(chainHeader->featureTable[nFeatureEntries]));
        le_int16 subtable;

        for (subtable = 0; LE_SUCCESS(success) && (subtable < nSubtables); subtable += 1) {
            if (subtable > 0) {
                le_int16 length = SWAPW(subtableHeader->length);
                if (length & 0x03) { // incorrect alignment for 32 bit tables
                    success = LE_MEMORY_ALLOCATION_ERROR; // as good a choice as any
                    return;
                }
                subtableHeader.addOffset(length, success);
            }
            SubtableCoverage coverage = SWAPW(subtableHeader->coverage);
            FeatureFlags subtableFeatures = SWAPL(subtableHeader->subtableFeatures);

            // should check coverage more carefully...
            if ((coverage & scfVertical) == 0 && (subtableFeatures & defaultFlags) != 0  && LE_SUCCESS(success)) {
              subtableHeader->process(subtableHeader, glyphStorage, success);
            }
        }
    }
}
Example #3
0
U_NAMESPACE_BEGIN

void MorphTableHeader2::process(const LEReferenceTo<MorphTableHeader2> &base, LEGlyphStorage &glyphStorage, 
                                le_int32 typoFlags, LEErrorCode &success) const
{
  if(LE_FAILURE(success)) return;

  le_uint32 chainCount = SWAPL(this->nChains);
  LEReferenceTo<ChainHeader2> chainHeader(base, success, &chains[0]); 
  /* chainHeader and subtableHeader are implemented as a moving pointer rather than an array dereference
   * to (slightly) reduce code churn. However, must be careful to preincrement them the 2nd time through.
   * We don't want to increment them at the end of the loop, as that would attempt to dereference
   * out of range memory. 
   */
  le_uint32 chain;

  for (chain = 0; LE_SUCCESS(success) && (chain < chainCount); chain++) {
        if (chain>0) {
          le_uint32 chainLength = SWAPL(chainHeader->chainLength);
          chainHeader.addOffset(chainLength, success); // Don't increment the first time
        }
        FeatureFlags flag = SWAPL(chainHeader->defaultFlags);
        le_uint32 nFeatureEntries = SWAPL(chainHeader->nFeatureEntries);
        le_uint32 nSubtables = SWAPL(chainHeader->nSubtables);
        LEReferenceTo<MorphSubtableHeader2> subtableHeader(chainHeader,
              success, (const MorphSubtableHeader2 *)&chainHeader->featureTable[nFeatureEntries]);
        le_uint32 subtable;
        if(LE_FAILURE(success)) break; // malformed table
        
        if (typoFlags != 0) {
           le_uint32 featureEntry;
           LEReferenceToArrayOf<FeatureTableEntry> featureTableRef(chainHeader, success, &chainHeader->featureTable[0], nFeatureEntries);
           if(LE_FAILURE(success)) break;
            // Feature subtables
            for (featureEntry = 0; featureEntry < nFeatureEntries; featureEntry++) {
                const FeatureTableEntry &featureTableEntry = featureTableRef(featureEntry, success);
                le_int16 featureType = SWAPW(featureTableEntry.featureType);
                le_int16 featureSetting = SWAPW(featureTableEntry.featureSetting);
                le_uint32 enableFlags = SWAPL(featureTableEntry.enableFlags);
                le_uint32 disableFlags = SWAPL(featureTableEntry.disableFlags);
                switch (featureType) {
                    case ligaturesType:
                        if ((typoFlags & LE_Ligatures_FEATURE_ENUM ) && (featureSetting ^ 0x1)){
                            flag &= disableFlags;
                            flag |= enableFlags;
                        } else {
                            if (((typoFlags & LE_RLIG_FEATURE_FLAG) && featureSetting == requiredLigaturesOnSelector) ||
                                ((typoFlags & LE_CLIG_FEATURE_FLAG) && featureSetting == contextualLigaturesOnSelector) ||
                                ((typoFlags & LE_HLIG_FEATURE_FLAG) && featureSetting == historicalLigaturesOnSelector) ||
                                ((typoFlags & LE_LIGA_FEATURE_FLAG) && featureSetting == commonLigaturesOnSelector)) {
                                flag &= disableFlags;
                                flag |= enableFlags;
                            }
                        }
                        break;
                    case letterCaseType:
                        if ((typoFlags & LE_SMCP_FEATURE_FLAG) && featureSetting == smallCapsSelector) {
                            flag &= disableFlags;
                            flag |= enableFlags;
                        }
                        break;
                    case verticalSubstitutionType:
                        break;
                    case linguisticRearrangementType:
                        break;
                    case numberSpacingType:
                        break;
                    case smartSwashType:
                        if ((typoFlags & LE_SWSH_FEATURE_FLAG) && (featureSetting ^ 0x1)){
                            flag &= disableFlags;
                            flag |= enableFlags;
                        }
                        break;
                    case diacriticsType:
                        break;
                    case verticalPositionType:
                        break;
                    case fractionsType:
                        if (((typoFlags & LE_FRAC_FEATURE_FLAG) && featureSetting == diagonalFractionsSelector) ||
                            ((typoFlags & LE_AFRC_FEATURE_FLAG) && featureSetting == verticalFractionsSelector)) {
                            flag &= disableFlags;
                            flag |= enableFlags;
                        } else {
                            flag &= disableFlags;
                        }
                        break;
                    case typographicExtrasType:
                        if ((typoFlags & LE_ZERO_FEATURE_FLAG) && featureSetting == slashedZeroOnSelector) {
                            flag &= disableFlags;
                            flag |= enableFlags;
                        }
                        break;
                    case mathematicalExtrasType:
                        break;
                    case ornamentSetsType:
                        break;
                    case characterAlternativesType:
                        break;
                    case designComplexityType:
                        if (((typoFlags & LE_SS01_FEATURE_FLAG) && featureSetting == designLevel1Selector) ||
                            ((typoFlags & LE_SS02_FEATURE_FLAG) && featureSetting == designLevel2Selector) ||
                            ((typoFlags & LE_SS03_FEATURE_FLAG) && featureSetting == designLevel3Selector) ||
                            ((typoFlags & LE_SS04_FEATURE_FLAG) && featureSetting == designLevel4Selector) ||
                            ((typoFlags & LE_SS05_FEATURE_FLAG) && featureSetting == designLevel5Selector) ||
                            ((typoFlags & LE_SS06_FEATURE_FLAG) && featureSetting == designLevel6Selector) ||
                            ((typoFlags & LE_SS07_FEATURE_FLAG) && featureSetting == designLevel7Selector)) {

                            flag &= disableFlags;
                            flag |= enableFlags;
                        }
                        break;
                    case styleOptionsType:
                        break;
                    case characterShapeType:
                        break;
                    case numberCaseType:
                        break;
                    case textSpacingType:
                        break;
                    case transliterationType:
                        break;
                    case annotationType:
                        if ((typoFlags & LE_NALT_FEATURE_FLAG) && featureSetting == circleAnnotationSelector) {
                            flag &= disableFlags;
                            flag |= enableFlags;
                        }
                        break;
                    case kanaSpacingType:
                        break;
                    case ideographicSpacingType:
                        break;
                    case rubyKanaType:
                        if ((typoFlags & LE_RUBY_FEATURE_FLAG) && featureSetting == rubyKanaOnSelector) {
                            flag &= disableFlags;
                            flag |= enableFlags;
                        }
                        break;
                    case cjkRomanSpacingType:
                        break;
                    default:
                        break;
                }
            }
        }
        
        for (subtable = 0;  LE_SUCCESS(success) && subtable < nSubtables; subtable++) {
            if(subtable>0)  {
              le_uint32 length = SWAPL(subtableHeader->length);
              subtableHeader.addOffset(length, success); // Don't addOffset for the last entry.
            }
            le_uint32 coverage = SWAPL(subtableHeader->coverage);
            FeatureFlags subtableFeatures = SWAPL(subtableHeader->subtableFeatures);
            // should check coverage more carefully...
            if (((coverage & scfIgnoreVt2) || !(coverage & scfVertical2)) && (subtableFeatures & flag) != 0) {
              subtableHeader->process(subtableHeader, glyphStorage, success);
            }
        }
    }    
}