Commit 325a13a7 authored by Dick Hollenbeck's avatar Dick Hollenbeck
Browse files

add makeFileName()

parent 02ba568c
Loading
Loading
Loading
Loading
+65 −31
Original line number Original line Diff line number Diff line
@@ -150,7 +150,7 @@ static const char* endsWithRev( const char* start, const char* tail, char separa
    {
    {
        tail -= 3;
        tail -= 3;


        if( tail[0]==separator && tail[1]=='r' && tail[2]=='e' && tail[2]=='v' )
        if( tail[0]==separator && tail[1]=='r' && tail[2]=='e' && tail[3]=='v' )
        {
        {
            return tail+1;  // omit separator, return "revN[N..]"
            return tail+1;  // omit separator, return "revN[N..]"
        }
        }
@@ -159,13 +159,14 @@ static const char* endsWithRev( const char* start, const char* tail, char separa
    return 0;
    return 0;
}
}



// see struct BY_REV
bool BY_REV::operator() ( const STRING& s1, const STRING& s2 ) const
bool BY_REV::operator() ( const STRING& s1, const STRING& s2 ) const
{
{
    // avoid instantiating new STRINGs, and thank goodness that c_str() is const.

    const char* rev1 = endsWithRev( s1.c_str(), s1.c_str()+s1.size(), '/' );
    const char* rev1 = endsWithRev( s1.c_str(), s1.c_str()+s1.size(), '/' );
    const char* rev2 = endsWithRev( s2.c_str(), s2.c_str()+s2.size(), '/' );
    const char* rev2 = endsWithRev( s2.c_str(), s2.c_str()+s2.size(), '/' );


    // avoid instantiating new STRINGs
    int rootLen1 =  rev1 ? rev1 - s1.c_str() : s1.size();
    int rootLen1 =  rev1 ? rev1 - s1.c_str() : s1.size();
    int rootLen2 =  rev2 ? rev2 - s2.c_str() : s2.size();
    int rootLen2 =  rev2 ? rev2 - s2.c_str() : s2.size();


@@ -181,7 +182,7 @@ bool BY_REV::operator() ( const STRING& s1, const STRING& s2 ) const
        return rootLen1 < rootLen2;
        return rootLen1 < rootLen2;
    }
    }


    // root strings match at this point, compare the revision number, numerically
    // root strings match at this point, compare the revision number numerically,
    // and chose the higher numbered version as "less", according to std::set lingo.
    // and chose the higher numbered version as "less", according to std::set lingo.


    if( bool(rev1) != bool(rev2) )
    if( bool(rev1) != bool(rev2) )
@@ -197,12 +198,12 @@ bool BY_REV::operator() ( const STRING& s1, const STRING& s2 ) const
        return rnum1 > rnum2;
        return rnum1 > rnum2;
    }
    }


    return false;   // strings are equal
    return false;   // strings are equal, and they don't have a rev
}
}




bool DIR_LIB_SOURCE::makePartFileName( const char* aEntry,
bool DIR_LIB_SOURCE::makePartName( STRING* aPartName, const char* aEntry,
                        const STRING& aCategory, STRING* aPartName )
                        const STRING& aCategory )
{
{
    const char* cp = strrstr( aEntry, ".part" );
    const char* cp = strrstr( aEntry, ".part" );


@@ -211,8 +212,11 @@ bool DIR_LIB_SOURCE::makePartFileName( const char* aEntry,
    {
    {
        const char* limit = cp + strlen( cp );
        const char* limit = cp + strlen( cp );


        // if file extension is exactly ".part", and no rev
        // If versioning, then must find a trailing "revN.." type of string.
        if( cp==limit-5 )
        if( useVersioning )
        {
            const char* rev = endsWithRev( cp + sizeof(".part") - 1, limit, '.' );
            if( rev )
            {
            {
                if( aCategory.size() )
                if( aCategory.size() )
                    *aPartName = aCategory + "/";
                    *aPartName = aCategory + "/";
@@ -220,14 +224,18 @@ bool DIR_LIB_SOURCE::makePartFileName( const char* aEntry,
                    aPartName->clear();
                    aPartName->clear();


                aPartName->append( aEntry, cp - aEntry );
                aPartName->append( aEntry, cp - aEntry );
                aPartName->append( "/" );
                aPartName->append( rev );
                return true;
                return true;
            }
            }
        }


        // if versioning, test for a trailing "revN.." type of string
        // If using versioning, then all valid partnames must have a rev string,
        if( useVersioning )
        // so we don't even bother to try and load any other partfile down here.
        else
        {
        {
            const char* rev = endsWithRev( cp + sizeof(".part") - 1, limit, '.' );
            // if file extension is exactly ".part", and no rev
            if( rev )
            if( cp==limit-5 )
            {
            {
                if( aCategory.size() )
                if( aCategory.size() )
                    *aPartName = aCategory + "/";
                    *aPartName = aCategory + "/";
@@ -235,8 +243,6 @@ bool DIR_LIB_SOURCE::makePartFileName( const char* aEntry,
                    aPartName->clear();
                    aPartName->clear();


                aPartName->append( aEntry, cp - aEntry );
                aPartName->append( aEntry, cp - aEntry );
                aPartName->append( "/" );
                aPartName->append( rev );
                return true;
                return true;
            }
            }
        }
        }
@@ -245,9 +251,30 @@ bool DIR_LIB_SOURCE::makePartFileName( const char* aEntry,
    return false;
    return false;
}
}


static bool isCategoryName( const char* aName )

STRING DIR_LIB_SOURCE::makeFileName( const STRING& aPartName )
{
{
    return true;
    // create a fileName for the sweet string, using a reversible
    // partname <-> fileName conversion protocol:

    STRING  fileName = sourceURI + "/";

    const char* rev = endsWithRev( aPartName.c_str(), aPartName.c_str()+aPartName.size(), '/' );

    if( rev )
    {
        int basePartLen = rev - aPartName.c_str() - 1;  // omit '/' separator
        fileName.append( aPartName, 0,  basePartLen );
        fileName += ".part.";    // add '.' separator before rev
        fileName += rev;
    }
    else
    {
        fileName += aPartName;
        fileName += ".part";
    }

    return fileName;
}
}




@@ -342,10 +369,14 @@ void DIR_LIB_SOURCE::GetCategoricalPartNames( STRINGS* aResults, const STRING& a


        for( PART_CACHE::const_iterator it = partnames.lower_bound( lower );  it!=limit;  ++it )
        for( PART_CACHE::const_iterator it = partnames.lower_bound( lower );  it!=limit;  ++it )
        {
        {
            /*
            const char* start = it->c_str();
            const char* start = it->c_str();
            size_t      len   = it->size();
            size_t      len   = it->size();


            if( !endsWithRev( start, start+len, '/' ) )
            if( endsWithRev( start, start+len, '/' ) )
                continue;
            */

            aResults->push_back( *it );
            aResults->push_back( *it );
        }
        }
    }
    }
@@ -353,10 +384,14 @@ void DIR_LIB_SOURCE::GetCategoricalPartNames( STRINGS* aResults, const STRING& a
    {
    {
        for( PART_CACHE::const_iterator it = partnames.begin();  it!=partnames.end();  ++it )
        for( PART_CACHE::const_iterator it = partnames.begin();  it!=partnames.end();  ++it )
        {
        {
            /*
            const char* start = it->c_str();
            const char* start = it->c_str();
            size_t      len   = it->size();
            size_t      len   = it->size();


            if( !endsWithRev( start, start+len, '/' ) )
            if( !endsWithRev( start, start+len, '/' ) )
                continue;
            */

            aResults->push_back( *it );
            aResults->push_back( *it );
        }
        }
    }
    }
@@ -379,13 +414,12 @@ void DIR_LIB_SOURCE::ReadPart( STRING* aResult, const STRING& aPartName, const S
        throw IO_ERROR( partname.c_str() );
        throw IO_ERROR( partname.c_str() );
    }
    }


    // create a filename for the sweet string
    // create a fileName for the sweet string
    STRING  filename = sourceURI + "/" + aPartName + ".part";
    STRING  fileName = makeFileName( aPartName );


    if( aRev.size() )
    // @todo what about aRev?, and define the public API wrt to aRev better.
        filename += "." + aRev;


    readSExpression( aResult, filename );
    readSExpression( aResult, fileName );
}
}




@@ -464,7 +498,7 @@ void DIR_LIB_SOURCE::cacheOneDir( const STRING& aCategory ) throw( IO_ERROR )
        if( !stat( fileName.c_str(), &fs ) )
        if( !stat( fileName.c_str(), &fs ) )
        {
        {
            // is this a valid part name?
            // is this a valid part name?
            if( S_ISREG( fs.st_mode ) && makePartFileName( entry->d_name, aCategory, &partName ) )
            if( S_ISREG( fs.st_mode ) && makePartName( &partName, entry->d_name, aCategory ) )
            {
            {
                std::pair<NAME_CACHE::iterator, bool> pair = partnames.insert( partName );
                std::pair<NAME_CACHE::iterator, bool> pair = partnames.insert( partName );


+15 −7
Original line number Original line Diff line number Diff line
@@ -89,22 +89,24 @@ class DIR_LIB_SOURCE : public LIB_SOURCE
    void cache() throw( IO_ERROR );
    void cache() throw( IO_ERROR );


    /**
    /**
     * Function isPartFileName
     * Function isCategoryName
     * returns true iff aName is a valid part file name.
     * returns true iff aName is a valid category name.
     */
     */
    bool  isPartFileName( const char* aName );
    bool isCategoryName( const char* aName )
    {
        return true;
    }


    /**
    /**
     * Function makePartFileName
     * Function makePartName
     * returns true iff aEntry holds a valid part filename, in the form of
     * returns true iff aEntry holds a valid part filename, in the form of
     * "someroot.part[.revNNNN]"  where NNN are number characters [0-9]
     * "someroot.part[.revNNNN]"  where NNN are number characters [0-9]
     * @param aEntry is the raw directory entry without path information.
     * @param aEntry is the raw directory entry without path information.
     * @param aCategory is the last portion of the directory path.
     * @param aCategory is the last portion of the directory path.
     * @param aPartName is where to put a part name, assuming aEntry is legal.
     * @param aPartName is where to put a part name, assuming @a aEntry is legal.
     * @return bool - true only if aEntry is a legal part file name.
     * @return bool - true only if aEntry is a legal part file name.
     */
     */
    bool makePartFileName( const char* aEntry,
    bool makePartName( STRING* aPartName, const char* aEntry, const STRING& aCategory );
                           const STRING& aCategory, STRING* aPartName );


    /**
    /**
     * Function readSExpression
     * Function readSExpression
@@ -123,6 +125,12 @@ class DIR_LIB_SOURCE : public LIB_SOURCE
     */
     */
    void cacheOneDir( const STRING& aCategory ) throw( IO_ERROR );
    void cacheOneDir( const STRING& aCategory ) throw( IO_ERROR );


    /**
     * Function makeFileName
     * converts a part name into a filename and returns it.
     */
    STRING makeFileName( const STRING& aPartName );

//protected:
//protected:
public:
public: