HAMIGAKI_BJAM_DECL string_list search_for_target(context& ctx)
{
    frame& f = ctx.current_frame();
    const list_of_list& args = f.arguments();

    const string_list& targets = args[0];
    const string_list& path = args[1];

    const std::string& name = targets[0];

    path_components compo;
    split_path(compo, name);
    compo.grist.clear();
    compo.member.clear();

    bool found = false;
    std::string filename;

    for (std::size_t i = 0, size = path.size(); i < size; ++i)
    {
        compo.root = path[i];
        filename = make_path(compo);

        if (fs::exists(fs::path(filename)))
        {
            found = true;
            break;
        }
    }

    if (!found)
    {
        compo.root.clear();
        fs::path ph(make_path(compo));
        fs::path work(ctx.working_directory());
        filename = fs::complete(ph, work).file_string();
    }

    call_bind_rule(ctx, name, filename);

    return string_list(name);
}
Exemple #2
0
OBJECT *
search(
    OBJECT * target,
    time_t *time,
    OBJECT * * another_target,
    int file
)
{
    PATHNAME f[1];
    LIST   * varlist;
    string   buf[1];
    int      found = 0;
    /* Will be set to 1 if target location is specified via LOCATE. */
    int      explicitly_located = 0;
    OBJECT * boundname = 0;
    OBJECT * varname;

    if ( another_target )
        *another_target = 0;

    if (! explicit_bindings )
        explicit_bindings = hashinit( sizeof(BINDING),
                                      "explicitly specified locations");

    string_new( buf );
    /* Parse the filename */

    path_parse( object_str( target ), f );

    f->f_grist.ptr = 0;
    f->f_grist.len = 0;

    varname = object_new( "LOCATE" );
    varlist = var_get( varname );
    object_free( varname );
    if ( varlist )
    {
        OBJECT * key;
        f->f_root.ptr = object_str( varlist->value );
        f->f_root.len = strlen( object_str( varlist->value ) );

        path_build( f, buf, 1 );

        if ( DEBUG_SEARCH )
            printf( "locate %s: %s\n", object_str( target ), buf->value );

        explicitly_located = 1;

        key = object_new( buf->value );
        timestamp( key, time );
        object_free( key );
        found = 1;
    }
    else if ( ( varname = object_new( "SEARCH" ),
                varlist = var_get( varname ),
                object_free( varname ),
                varlist ) )
    {
        while ( varlist )
        {
            BINDING b, *ba = &b;
            file_info_t *ff;
            OBJECT * key;
            OBJECT * test_path;

            f->f_root.ptr = object_str( varlist->value );
            f->f_root.len = strlen( object_str( varlist->value ) );

            string_truncate( buf, 0 );
            path_build( f, buf, 1 );

            if ( DEBUG_SEARCH )
                printf( "search %s: %s\n", object_str( target ), buf->value );

            test_path = object_new( buf->value );
            key = path_as_key( test_path );
            object_free( test_path );
            ff = file_query( key );
            timestamp( key, time );

            b.binding = key;

            if ( hashcheck( explicit_bindings, (HASHDATA**)&ba ) )
            {
                if ( DEBUG_SEARCH )
                    printf(" search %s: found explicitly located target %s\n",
                           object_str( target ), object_str( ba->target ) );
                if ( another_target )
                    *another_target = ba->target;
                found = 1;
                object_free( key );
                break;
            }
            else if ( ff && ff->time )
            {
                if ( !file || ff->is_file )
                {
                    found = 1;
                    object_free( key );
                    break;
                }
            }
            object_free( key );

            varlist = list_next( varlist );
        }
    }

    if ( !found )
    {
        /* Look for the obvious */
        /* This is a questionable move.  Should we look in the */
        /* obvious place if SEARCH is set? */
        OBJECT * key;

        f->f_root.ptr = 0;
        f->f_root.len = 0;

        string_truncate( buf, 0 );
        path_build( f, buf, 1 );

        if ( DEBUG_SEARCH )
            printf( "search %s: %s\n", object_str( target ), buf->value );

        key = object_new( buf->value );
        timestamp( key, time );
        object_free( key );
    }

    boundname = object_new( buf->value );
    string_free( buf );

    if ( explicitly_located )
    {
        BINDING b;
        BINDING * ba = &b;
        OBJECT * key = path_as_key( boundname );
        b.binding = key;
        b.target = target;
        /* CONSIDER: we probably should issue a warning is another file
           is explicitly bound to the same location. This might break
           compatibility, though. */
        if ( !hashenter( explicit_bindings, (HASHDATA * *)&ba ) )
        {
            object_free( key );
        }
    }

    /* prepare a call to BINDRULE if the variable is set */
    call_bind_rule( target, boundname );

    return boundname;
}
Exemple #3
0
TARGET* search_for_target ( char * name, LIST* search_path )
{
    PATHNAME f[1];
    string buf[1];
    LOCATED_TARGET lt, *lta = &lt;
    time_t time;
    int found = 0;
    TARGET* result;

    string_new( buf );

	path_parse( name, f );

    f->f_grist.ptr = 0;
    f->f_grist.len = 0;

    while( search_path )
    {
        f->f_root.ptr = search_path->string;
        f->f_root.len = strlen( search_path->string );

        string_truncate( buf, 0 );
        path_build( f, buf, 1 );

        lt.file_name = buf->value ;

        if (! located_targets )
            located_targets = hashinit( sizeof(LOCATED_TARGET),
                                        "located targets" );


        if ( hashcheck( located_targets, (HASHDATA **)&lta ) )
        {
            return lta->target;
        }

        timestamp( buf->value, &time );
        if (time)
        {
            found = 1;
            break;
        }

        search_path = list_next( search_path );
    }

    if ( ! found )
    {
        f->f_root.ptr = 0;
        f->f_root.len = 0;

        string_truncate( buf, 0 );
        path_build( f, buf, 1 );

        timestamp( buf->value, &time );        
    }

    result = bindtarget( name );
    result->boundname = newstr( buf->value );
    result->time = time;
    result->binding = time ? T_BIND_EXISTS : T_BIND_MISSING;

    call_bind_rule( result->name, result->boundname );
    
    string_free( buf );

    return result;

}
Exemple #4
0
OBJECT *
search(
    OBJECT * target,
    time_t *time,
    OBJECT * * another_target,
    int file
)
{
    PATHNAME f[1];
    LIST   * varlist;
    string   buf[1];
    int      found = 0;
    /* Will be set to 1 if target location is specified via LOCATE. */
    int      explicitly_located = 0;
    OBJECT * boundname = 0;

    if ( another_target )
        *another_target = 0;

    if (! explicit_bindings )
        explicit_bindings = hashinit( sizeof(BINDING),
                                     "explicitly specified locations");

    string_new( buf );
    /* Parse the filename */

    path_parse( object_str( target ), f );

    f->f_grist.ptr = 0;
    f->f_grist.len = 0;

    varlist = var_get( root_module(), constant_LOCATE );
    if ( !list_empty( varlist ) )
    {
        OBJECT * key;
        f->f_root.ptr = object_str( list_front( varlist ) );
        f->f_root.len = strlen( object_str( list_front( varlist ) ) );

        path_build( f, buf, 1 );

        if ( DEBUG_SEARCH )
            printf( "locate %s: %s\n", object_str( target ), buf->value );

        explicitly_located = 1;

        key = object_new( buf->value );
        timestamp( key, time );
        object_free( key );
        found = 1;
    }
    else if ( varlist = var_get( root_module(), constant_SEARCH ), !list_empty( varlist ) )
    {
        LISTITER iter = list_begin( varlist ), end = list_end( varlist );
        for ( ; iter != end; iter = list_next( iter ) )
        {
            BINDING * ba;
            file_info_t *ff;
            OBJECT * key;
            OBJECT * test_path;

            f->f_root.ptr = object_str( list_item( iter ) );
            f->f_root.len = strlen( object_str( list_item( iter ) ) );

            string_truncate( buf, 0 );
            path_build( f, buf, 1 );

            if ( DEBUG_SEARCH )
                printf( "search %s: %s\n", object_str( target ), buf->value );

            test_path = object_new( buf->value );
            key = path_as_key( test_path );
            object_free( test_path );
            ff = file_query( key );
            timestamp( key, time );

            if ( ( ba = (BINDING *)hash_find( explicit_bindings, key ) ) )
            {
                if ( DEBUG_SEARCH )
                    printf(" search %s: found explicitly located target %s\n",
                           object_str( target ), object_str( ba->target ) );
                if ( another_target )
                    *another_target = ba->target;
                found = 1;
                object_free( key );
                break;
            }
            else if ( ff && ff->time )
            {
                if ( !file || ff->is_file )
                {
                    found = 1;
                    object_free( key );
                    break;
                }
            }
            object_free( key );
        }
    }

    if ( !found )
    {
        /* Look for the obvious */
        /* This is a questionable move.  Should we look in the */
        /* obvious place if SEARCH is set? */
        OBJECT * key;

        f->f_root.ptr = 0;
        f->f_root.len = 0;

        string_truncate( buf, 0 );
        path_build( f, buf, 1 );

        if ( DEBUG_SEARCH )
            printf( "search %s: %s\n", object_str( target ), buf->value );

        key = object_new( buf->value );
        timestamp( key, time );
        object_free( key );
    }

    boundname = object_new( buf->value );
    string_free( buf );

    if ( explicitly_located )
    {
        int found;
        BINDING * ba;
        OBJECT * key = path_as_key( boundname );
        /* CONSIDER: we probably should issue a warning is another file
           is explicitly bound to the same location. This might break
           compatibility, though. */
        ba = (BINDING *)hash_insert( explicit_bindings, key, &found );
        if ( !found )
        {
            ba->binding = key;
            ba->target = target;
        }
        else
        {
            object_free( key );
        }
    }

    /* prepare a call to BINDRULE if the variable is set */
    call_bind_rule( target, boundname );

    return boundname;
}
Exemple #5
0
OBJECT * search( OBJECT * target, timestamp * const time,
    OBJECT * * another_target, int const file )
{
    PATHNAME f[ 1 ];
    LIST * varlist;
    string buf[ 1 ];
    int found = 0;
    OBJECT * boundname = 0;

    if ( another_target )
        *another_target = 0;

    if ( !explicit_bindings )
        explicit_bindings = hashinit( sizeof( BINDING ), "explicitly specified "
            "locations" );

    string_new( buf );

    /* Parse the filename. */
    path_parse( object_str( target ), f );

    f->f_grist.ptr = 0;
    f->f_grist.len = 0;

    varlist = var_get( root_module(), constant_LOCATE );
    if ( !list_empty( varlist ) )
    {
        OBJECT * key;
        f->f_root.ptr = object_str( list_front( varlist ) );
        f->f_root.len = strlen( object_str( list_front( varlist ) ) );

        path_build( f, buf );

        if ( DEBUG_SEARCH )
            printf( "locate %s: %s\n", object_str( target ), buf->value );

        key = object_new( buf->value );
        timestamp_from_path( time, key );
        object_free( key );
        found = 1;
    }
    else if ( varlist = var_get( root_module(), constant_SEARCH ),
        !list_empty( varlist ) )
    {
        LISTITER iter = list_begin( varlist );
        LISTITER const end = list_end( varlist );
        for ( ; iter != end; iter = list_next( iter ) )
        {
            BINDING * ba;
            file_info_t * ff;
            OBJECT * key;
            OBJECT * test_path;

            f->f_root.ptr = object_str( list_item( iter ) );
            f->f_root.len = strlen( object_str( list_item( iter ) ) );

            string_truncate( buf, 0 );
            path_build( f, buf );

            if ( DEBUG_SEARCH )
                printf( "search %s: %s\n", object_str( target ), buf->value );

            test_path = object_new( buf->value );
            key = path_as_key( test_path );
            object_free( test_path );
            ff = file_query( key );
            timestamp_from_path( time, key );

            if ( ( ba = (BINDING *)hash_find( explicit_bindings, key ) ) )
            {
                if ( DEBUG_SEARCH )
                    printf(" search %s: found explicitly located target %s\n",
                        object_str( target ), object_str( ba->target ) );
                if ( another_target )
                    *another_target = ba->target;
                found = 1;
                object_free( key );
                break;
            }
            else if ( ff )
            {
                if ( !file || ff->is_file )
                {
                    found = 1;
                    object_free( key );
                    break;
                }
            }
            object_free( key );
        }
    }

    if ( !found )
    {
        /* Look for the obvious. */
        /* This is a questionable move. Should we look in the obvious place if
         * SEARCH is set?
         */
        OBJECT * key;

        f->f_root.ptr = 0;
        f->f_root.len = 0;

        string_truncate( buf, 0 );
        path_build( f, buf );

        if ( DEBUG_SEARCH )
            printf( "search %s: %s\n", object_str( target ), buf->value );

        key = object_new( buf->value );
        timestamp_from_path( time, key );
        object_free( key );
    }

    boundname = object_new( buf->value );
    string_free( buf );

    /* Prepare a call to BINDRULE if the variable is set. */
    call_bind_rule( target, boundname );

    return boundname;
}