예제 #1
0
/* BSTNodeFindNext
 *  find next element satisfying criteria
 */
LIB_EXPORT BSTNode* CC BSTNodeFindNext ( const BSTNode *p,
    bool ( CC * f ) ( const BSTNode *n ) )
{
    if ( p != NULL )
    {
        BSTNode *n = BSTNodeNext ( p );
        while ( n != NULL )
        {
            if ( ( * f ) ( n ) )
                return n;
            n = BSTNodeNext ( n );
        }
    }
    return NULL;
}
예제 #2
0
bool SRA_StatisticsNextPath ( const SRA_Statistics * self, ctx_t ctx, const char * path, const char** next )
{
    FUNC_ENTRY ( ctx, rcSRA, rcDatabase, rcAccessing );
    const DictionaryEntry * node = NULL;
    
    assert ( self );
    
    if ( path == NULL )
        INTERNAL_ERROR ( xcParamNull, "path is NULL" );
    else if ( path[0] == 0 )
    {
        node = ( const DictionaryEntry * ) BSTreeFirst ( & self -> dictionary );
    }
    else
    {
        node = ( const DictionaryEntry * ) BSTreeFind ( & self -> dictionary, ( const void * ) path, DictionaryEntryFind );
        if ( node == NULL )
        {
            INTERNAL_ERROR ( xcUnexpected, "dictionary item '%s' is not found", path );
        }
        else
        {
            node = ( const DictionaryEntry * ) BSTNodeNext ( & node -> dad );
        }
    }
    
    if ( node == NULL )
    {
        *next = NULL;
        return false;
    }
    *next = node -> path;
    return true;
}
예제 #3
0
rc_t make_column_namelist ( const BSTree *columns, KNamelist **names )
{
    VNamelist *list;
    rc_t rc = VNamelistMake ( & list, 8 );
    if ( rc == 0 )
    {
        const String *last = NULL;
        const VColumnRef *cref = ( const VColumnRef* )
            BSTreeFirst ( columns );
        while ( cref != NULL )
        {
            if ( last == NULL || ! StringEqual ( last, & cref -> name ) )
            {
                rc = VNamelistAppend ( list, cref -> name . addr );
                if ( rc != 0 )
                    break;

                last = & cref -> name;
            }

            cref = ( const VColumnRef* )
                BSTNodeNext ( & cref -> n );
        }

        if ( rc == 0 )
            rc = VNamelistToNamelist ( list, names );

        VNamelistRelease ( list );
    }

    return rc;
}
예제 #4
0
/* BSTreeDoUntil
 *  executes a function on each element
 *  until the function returns 1
 */
LIB_EXPORT bool CC BSTreeDoUntil ( const BSTree *bt, bool reverse,
    bool ( CC * f ) ( BSTNode *n, void *data ), void *data )
{
    if ( bt != NULL )
    {
        BSTNode *n, *next;
        if ( reverse )
        {
            n = LastNode ( bt );
            while ( n != NULL )
            {
                next = BSTNodePrev ( n );
                if ( ( * f ) ( n, data ) )
                    return true;
                n = next;
            }
        }
        else
        {
            n = FirstNode ( bt );
            while ( n != NULL )
            {
                next = BSTNodeNext ( n );
                if ( ( * f ) ( n, data ) )
                    return true;
                n = next;
            }
        }
    }
    return false;
}
예제 #5
0
/* BSTreeForEach
 *  executes a function on each tree element
 */
LIB_EXPORT void CC BSTreeForEach ( const BSTree *bt, bool reverse,
    void ( CC * f ) ( BSTNode *n, void *data ), void *data )
{
    if ( bt != NULL )
    {
        BSTNode *n, *next;
        if ( reverse )
        {
            n = LastNode ( bt );
            while ( n != NULL )
            {
                next = BSTNodePrev ( n );
                ( * f ) ( n, data );
                n = next;
            }
        }
        else
        {
            n = FirstNode ( bt );
            while ( n != NULL )
            {
                next = BSTNodeNext ( n );
                ( * f ) ( n, data );
                n = next;
            }
        }
    }
}
예제 #6
0
static 
rc_t SaveObjects ( const ObjectTable* data,  VDatabase* db )
{
    VTable* tbl;
    rc_t rc = VDatabaseCreateTable(db, &tbl, "object_inst", kcmCreate | kcmMD5, "OBJECTS");
    if (rc == 0)
    {
        rc_t rc2;
        VCursor *cur;
        rc = VTableCreateCursorWrite( tbl, &cur, kcmInsert );
        if (rc == 0)
        {
            uint32_t id_idx, name_idx, proj_idx, dname_idx, size_idx, csum_idx, enc_idx;
            if (rc == 0) rc = VCursorAddColumn( cur, &id_idx,    "id" );
            if (rc == 0) rc = VCursorAddColumn( cur, &name_idx,  "name" );
            if (rc == 0) rc = VCursorAddColumn( cur, &proj_idx,    "project" );
            if (rc == 0) rc = VCursorAddColumn( cur, &dname_idx, "display_name" );
            if (rc == 0) rc = VCursorAddColumn( cur, &size_idx,  "size" );
            if (rc == 0) rc = VCursorAddColumn( cur, &csum_idx,  "checksum" );
            if (rc == 0) rc = VCursorAddColumn( cur, &enc_idx,   "encryption_key" );

            if (rc == 0)
            {
                rc = VCursorOpen( cur );
                if (rc == 0)
                {
                    const Object* obj = (const Object*)BSTreeFirst(data);
                    while (rc == 0 && obj != NULL)
                    {
                        rc = VCursorOpenRow( cur );
                        
                        if (rc == 0) rc = VCursorWrite( cur, id_idx,    sizeof(obj->id) * 8,                   &obj->id,                  0, 1);
                        if (rc == 0) rc = VCursorWrite( cur, name_idx,  StringLength(obj->name) * 8,           obj->name->addr,           0, 1);
                        if (rc == 0) rc = VCursorWrite( cur, proj_idx,  StringLength(obj->project) * 8,        obj->project->addr,        0, 1);
                        if (rc == 0) rc = VCursorWrite( cur, dname_idx, StringLength(obj->display_name) * 8,   obj->display_name->addr,   0, 1);
                        if (rc == 0) rc = VCursorWrite( cur, size_idx,  sizeof(obj->size) * 8,                 &obj->size,                0, 1);
                        if (rc == 0) rc = VCursorWrite( cur, csum_idx,  StringLength(obj->encryption_key) * 8, obj->encryption_key->addr, 0, 1);
                        if (rc == 0) rc = VCursorWrite( cur, enc_idx,   StringLength(obj->encryption_key) * 8, obj->encryption_key->addr, 0, 1);
                        
                        if (rc == 0) rc = VCursorCommitRow( cur );
                        if (rc == 0) rc = VCursorCloseRow( cur );
                        
                        obj = (const Object*)BSTNodeNext(&obj->dad);
                    }
                    if (rc == 0) rc = VCursorCommit( cur );
                }
            }
            rc2 = VCursorRelease(cur);
            if (rc == 0)
                rc = rc2;
        }
        
        rc2 = VTableRelease(tbl);
        if (rc == 0)
            rc = rc2;
    }
    return rc;
}
예제 #7
0
static 
rc_t SaveProjects( const ProjectTable* data, VDatabase* db )
{
    VTable* tbl;
    rc_t rc = VDatabaseCreateTable(db, &tbl, "project_inst", kcmCreate | kcmMD5, "PROJECTS");
    if (rc == 0)
    {
        rc_t rc2;
        VCursor *cur;
        rc = VTableCreateCursorWrite( tbl, &cur, kcmInsert );
        if (rc == 0)
        {
            uint32_t id_idx, name_idx, dl_idx, enc_idx;
            rc = VCursorAddColumn( cur, &id_idx, "id" );
            rc = VCursorAddColumn( cur, &name_idx, "name" );
            rc = VCursorAddColumn( cur, &dl_idx, "download_ticket" );
            rc = VCursorAddColumn( cur, &enc_idx, "encryption_key" );
            if (rc == 0)
            {
                rc = VCursorOpen( cur );
                if (rc == 0)
                {
                    const Project* p = (const Project*)BSTreeFirst(data);
                    while (rc == 0 && p != NULL)
                    {
                        rc = VCursorOpenRow( cur );
                        
                        if (rc == 0) rc = VCursorWrite( cur, id_idx,    sizeof(p->id) * 8,                      &p->id,                     0, 1);
                        if (rc == 0) rc = VCursorWrite( cur, name_idx,  StringLength(p->name) * 8,              p->name->addr,              0, 1);
                        if (rc == 0) rc = VCursorWrite( cur, dl_idx,    StringLength(p->download_ticket) * 8,   p->download_ticket->addr,   0, 1);
                        if (rc == 0) rc = VCursorWrite( cur, enc_idx,   StringLength(p->encryption_key) * 8,    p->encryption_key->addr,    0, 1);
                        
                        if (rc == 0) rc = VCursorCommitRow( cur );
                        if (rc == 0) rc = VCursorCloseRow( cur );
                        
                        p = (const Project*)BSTNodeNext(&p->dad);
                    }
                    if (rc == 0)
                        rc = VCursorCommit( cur );
                }
            }
            rc2 = VCursorRelease(cur);
            if (rc == 0)
                rc = rc2;
        }
        
        rc2 = VTableRelease(tbl);
        if (rc == 0)
            rc = rc2;
    }
    return rc;
}
예제 #8
0
rc_t make_column_typelist ( const BSTree *columns,
    const char *col, uint32_t *dflt_idx, KNamelist **typedecls )
{
    VNamelist *list;
    rc_t rc = VNamelistMake ( & list, 8 );
    if ( rc == 0 )
    {
        uint32_t idx;
        const VColumnRef *first;

        String col_name;
        StringInitCString ( & col_name, col );

        first = ( const VColumnRef* )
            BSTreeFind ( columns, & col_name, VColumnRefCmpString );
        if ( first != NULL )
        {
            const VColumnRef *cref = ( const VColumnRef* ) BSTNodePrev ( & first -> n );
            while ( cref != NULL && StringEqual ( & first -> name, & cref -> name ) )
            {
                first = cref;
                cref = ( const VColumnRef* ) BSTNodePrev ( & cref -> n );
            }

            for ( cref = first, idx = 0; ; ++ idx )
            {
                rc = VNamelistAppend ( list, cref -> typedecl );
                if ( rc != 0 )
                    break;

                if ( cref -> dflt )
                    * dflt_idx = idx;

                cref = ( const VColumnRef* ) BSTNodeNext ( & cref -> n );
                if ( cref == NULL || ! StringEqual ( & first -> name, & cref -> name ) )
                    break;
            }
        }

        if ( rc == 0 )
            rc = VNamelistToNamelist ( list, typedecls );

        VNamelistRelease ( list );
    }

    return rc;
}
예제 #9
0
/* BSTreeDepth
 *  returns number of layers in b-tree
 *
 *  if "exact" is 1, then the maximum
 *  depth is returned. otherwise, the depth of
 *  an arbitrary leaf node is returned
 */
LIB_EXPORT uint32_t CC BSTreeDepth ( const BSTree *bt, bool exact )
{
    BSTNode *p;
    uint32_t depth;

    if ( bt == NULL || bt -> root == NULL )
        return 0;

    depth = 1;

    if ( exact )
    {
        for ( p = FirstNode ( bt ); p != NULL; p = BSTNodeNext ( p ) )
        {
            BSTNode *q;
            unsigned int ndepth;

            if ( p -> child [ 0 ] != NULL || p -> child [ 1 ] != NULL )
                continue;

            for ( ndepth = 1, q = PARENT ( p ); q != NULL; q = PARENT ( q ) )
                ++ ndepth;

            if ( ndepth > depth )
                depth = ndepth;
        }
    }
    else
    {
        for ( p = bt -> root;; ++ depth )
        {
            if ( p -> child [ 0 ] != NULL )
                p = p -> child [ 0 ];
            else if ( p -> child [ 1 ] != NULL )
                p = p -> child [ 1 ];
            else
                break;
        }
    }

    return depth;
}
예제 #10
0
static
rc_t VProdResolveBestColumn ( const VProdResolve *self,
    VProduction **out, const BSTree *ordered, bool alt )
{
    rc_t rc;

    /* walk all candidtes */
    const SColumnBestFit *n = ( const SColumnBestFit* ) BSTreeFirst ( ordered );
    for ( rc = 0; n != NULL; n = ( const SColumnBestFit* ) BSTNodeNext ( & n -> n ) )
    {
        /* look for open column */
        const SColumn *scol = n -> scol;

        /* resolve the column as appropriate */
        rc = VProdResolveColumn ( self, out, scol, alt );
        if ( rc != 0 || * out != NULL )
            break;
    }

    return rc;
}
예제 #11
0
static
rc_t mark_type_sensitivity ( const BSTree *stype_tbl, const VSchema *schema,
    const VTypedecl *td, vtblcp_column_map *cm )
{
    const stype_id *node;

    /* simple case - look for exact matches */
    if ( BSTreeFind ( stype_tbl, td, stype_id_cmp ) != NULL )
    {
        cm -> sensitive = true;
        return 0;
    }

    /* exhaustive case - perform one by one ancestry test */
    for ( node = ( const stype_id* ) BSTreeFirst ( stype_tbl );
          node != NULL;
          node = ( const stype_id* ) BSTNodeNext ( & node -> n ) )
    {
        cm -> redact_value = NULL;
        if ( td -> type_id > node -> type_id )
        {
            VTypedecl cast;

            /* test for our type being a subtype */
            if ( VTypedeclToType ( td, schema, node -> type_id, & cast, NULL ) )
            {
                cm -> redact_value = node -> redact_value;
                cm -> sensitive = true;
                return 0;
            }
        }
    }

    /* doesn't appear to be sensitive */
    cm -> sensitive = false;
    return 0;
}
예제 #12
0
const struct reference_region * get_next_ref_node( const struct reference_region * node )
{
    return ( const struct reference_region * ) BSTNodeNext( ( const BSTNode * ) node );
}