Changeset 2851


Ignore:
Timestamp:
16/01/2011 23:36:20 (16 months ago)
Author:
chris
Message:

Move code for comparing file data out of line for readability.

Add a new notification function for local file access errors, to distinguish them from download errors (remote server errors).

Location:
box/trunk/bin/bbackupquery
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • box/trunk/bin/bbackupquery/BackupQueries.cpp

    r2834 r2851  
    18801880} 
    18811881 
     1882void BackupQueries::CompareOneFile(int64_t DirID, 
     1883        BackupStoreDirectory::Entry *pEntry, 
     1884        const std::string& rLocalPath, 
     1885        const std::string& rStorePath, 
     1886        BoxBackupCompareParams &rParams) 
     1887{ 
     1888        int64_t fileId = pEntry->GetObjectID(); 
     1889        int64_t fileSize = 0; 
     1890 
     1891        EMU_STRUCT_STAT st; 
     1892        if(EMU_STAT(rLocalPath.c_str(), &st) == 0) 
     1893        { 
     1894                fileSize = st.st_size; 
     1895        } 
     1896 
     1897        try 
     1898        { 
     1899                // Files the same flag? 
     1900                bool equal = true; 
     1901                 
     1902                // File modified after last sync flag 
     1903                bool modifiedAfterLastSync = false; 
     1904                 
     1905                bool hasDifferentAttribs = false; 
     1906 
     1907                bool alreadyReported = false; 
     1908                         
     1909                if(rParams.QuickCompare()) 
     1910                { 
     1911                        // Compare file -- fetch it 
     1912                        mrConnection.QueryGetBlockIndexByID(fileId); 
     1913 
     1914                        // Stream containing block index 
     1915                        std::auto_ptr<IOStream> blockIndexStream(mrConnection.ReceiveStream()); 
     1916                         
     1917                        // Compare 
     1918                        equal = BackupStoreFile::CompareFileContentsAgainstBlockIndex( 
     1919                                rLocalPath.c_str(), *blockIndexStream, 
     1920                                mrConnection.GetTimeout()); 
     1921                } 
     1922                else 
     1923                { 
     1924                        // Compare file -- fetch it 
     1925                        mrConnection.QueryGetFile(DirID, pEntry->GetObjectID()); 
     1926 
     1927                        // Stream containing encoded file 
     1928                        std::auto_ptr<IOStream> objectStream(mrConnection.ReceiveStream()); 
     1929 
     1930                        // Decode it 
     1931                        std::auto_ptr<BackupStoreFile::DecodedStream> fileOnServerStream; 
     1932 
     1933                        // Got additional attributes? 
     1934                        if(pEntry->HasAttributes()) 
     1935                        { 
     1936                                // Use these attributes 
     1937                                const StreamableMemBlock &storeAttr(pEntry->GetAttributes()); 
     1938                                BackupClientFileAttributes attr(storeAttr); 
     1939                                fileOnServerStream.reset( 
     1940                                        BackupStoreFile::DecodeFileStream( 
     1941                                                *objectStream, 
     1942                                                mrConnection.GetTimeout(), 
     1943                                                &attr).release()); 
     1944                        } 
     1945                        else 
     1946                        { 
     1947                                // Use attributes stored in file 
     1948                                fileOnServerStream.reset(BackupStoreFile::DecodeFileStream(*objectStream, mrConnection.GetTimeout()).release()); 
     1949                        } 
     1950                         
     1951                        // Should always be something in the auto_ptr, it's how the interface is defined. But be paranoid. 
     1952                        if(!fileOnServerStream.get()) 
     1953                        { 
     1954                                THROW_EXCEPTION(BackupStoreException, Internal) 
     1955                        } 
     1956                         
     1957                        // Compare attributes 
     1958                        BackupClientFileAttributes localAttr; 
     1959                        box_time_t fileModTime = 0; 
     1960                        localAttr.ReadAttributes(rLocalPath.c_str(), false /* don't zero mod times */, &fileModTime);                                    
     1961                        modifiedAfterLastSync = (fileModTime > rParams.LatestFileUploadTime()); 
     1962                        bool ignoreAttrModTime = true; 
     1963 
     1964                        #ifdef WIN32 
     1965                        // attr mod time is really 
     1966                        // creation time, so check it 
     1967                        ignoreAttrModTime = false; 
     1968                        #endif 
     1969 
     1970                        if(!rParams.IgnoreAttributes() && 
     1971                        #ifdef PLATFORM_DISABLE_SYMLINK_ATTRIB_COMPARE 
     1972                           !fileOnServerStream->IsSymLink() && 
     1973                        #endif 
     1974                           !localAttr.Compare(fileOnServerStream->GetAttributes(), 
     1975                                        ignoreAttrModTime, 
     1976                                        fileOnServerStream->IsSymLink() /* ignore modification time if it's a symlink */)) 
     1977                        { 
     1978                                hasDifferentAttribs = true; 
     1979                        } 
     1980 
     1981                        // Compare contents, if it's a regular file not a link 
     1982                        // Remember, we MUST read the entire stream from the server. 
     1983                        SelfFlushingStream flushObject(*objectStream); 
     1984 
     1985                        if(!fileOnServerStream->IsSymLink()) 
     1986                        { 
     1987                                SelfFlushingStream flushFile(*fileOnServerStream); 
     1988                                // Open the local file 
     1989                                std::auto_ptr<FileStream> apLocalFile; 
     1990 
     1991                                try 
     1992                                { 
     1993                                        apLocalFile.reset(new FileStream(rLocalPath.c_str())); 
     1994                                } 
     1995                                catch(std::exception &e) 
     1996                                { 
     1997                                        rParams.NotifyLocalFileReadFailed(rLocalPath, 
     1998                                                rStorePath, fileSize, e); 
     1999                                        alreadyReported = true; 
     2000                                } 
     2001                                catch(...) 
     2002                                {        
     2003                                        rParams.NotifyLocalFileReadFailed(rLocalPath, 
     2004                                                rStorePath, fileSize); 
     2005                                        alreadyReported = true; 
     2006                                } 
     2007 
     2008                                if(apLocalFile.get()) 
     2009                                { 
     2010                                        equal = apLocalFile->CompareWith(*fileOnServerStream, 
     2011                                                mrConnection.GetTimeout()); 
     2012                                } 
     2013                        } 
     2014                } 
     2015 
     2016                rParams.NotifyFileCompared(rLocalPath, rStorePath, fileSize, 
     2017                        hasDifferentAttribs, !equal, modifiedAfterLastSync, 
     2018                        pEntry->HasAttributes()); 
     2019        } 
     2020        catch(BoxException &e) 
     2021        { 
     2022                rParams.NotifyDownloadFailed(rLocalPath, rStorePath, fileSize, 
     2023                        e); 
     2024        } 
     2025        catch(std::exception &e) 
     2026        { 
     2027                rParams.NotifyDownloadFailed(rLocalPath, rStorePath, fileSize, 
     2028                        e); 
     2029        } 
     2030        catch(...) 
     2031        {        
     2032                rParams.NotifyDownloadFailed(rLocalPath, rStorePath, fileSize); 
     2033        } 
     2034} 
    18822035 
    18832036// -------------------------------------------------------------------------- 
     
    21112264                        else 
    21122265                        {                                
    2113                                 int64_t fileSize = 0; 
    2114  
    2115                                 EMU_STRUCT_STAT st; 
    2116                                 if(EMU_STAT(localPath.c_str(), &st) == 0) 
    2117                                 { 
    2118                                         fileSize = st.st_size; 
    2119                                 } 
    2120  
    2121                                 try 
    2122                                 { 
    2123                                         // Files the same flag? 
    2124                                         bool equal = true; 
    2125                                          
    2126                                         // File modified after last sync flag 
    2127                                         bool modifiedAfterLastSync = false; 
    2128                                          
    2129                                         bool hasDifferentAttribs = false; 
    2130                                                  
    2131                                         if(rParams.QuickCompare()) 
    2132                                         { 
    2133                                                 // Compare file -- fetch it 
    2134                                                 mrConnection.QueryGetBlockIndexByID(i->second->GetObjectID()); 
    2135  
    2136                                                 // Stream containing block index 
    2137                                                 std::auto_ptr<IOStream> blockIndexStream(mrConnection.ReceiveStream()); 
    2138                                                  
    2139                                                 // Compare 
    2140                                                 equal = BackupStoreFile::CompareFileContentsAgainstBlockIndex(localPath.c_str(), *blockIndexStream, mrConnection.GetTimeout()); 
    2141                                         } 
    2142                                         else 
    2143                                         { 
    2144                                                 // Compare file -- fetch it 
    2145                                                 mrConnection.QueryGetFile(DirID, i->second->GetObjectID()); 
    2146          
    2147                                                 // Stream containing encoded file 
    2148                                                 std::auto_ptr<IOStream> objectStream(mrConnection.ReceiveStream()); 
    2149          
    2150                                                 // Decode it 
    2151                                                 std::auto_ptr<BackupStoreFile::DecodedStream> fileOnServerStream; 
    2152                                                 // Got additional attributes? 
    2153                                                 if(i->second->HasAttributes()) 
    2154                                                 { 
    2155                                                         // Use these attributes 
    2156                                                         const StreamableMemBlock &storeAttr(i->second->GetAttributes()); 
    2157                                                         BackupClientFileAttributes attr(storeAttr); 
    2158                                                         fileOnServerStream.reset(BackupStoreFile::DecodeFileStream(*objectStream, mrConnection.GetTimeout(), &attr).release()); 
    2159                                                 } 
    2160                                                 else 
    2161                                                 { 
    2162                                                         // Use attributes stored in file 
    2163                                                         fileOnServerStream.reset(BackupStoreFile::DecodeFileStream(*objectStream, mrConnection.GetTimeout()).release()); 
    2164                                                 } 
    2165                                                  
    2166                                                 // Should always be something in the auto_ptr, it's how the interface is defined. But be paranoid. 
    2167                                                 if(!fileOnServerStream.get()) 
    2168                                                 { 
    2169                                                         THROW_EXCEPTION(BackupStoreException, Internal) 
    2170                                                 } 
    2171                                                  
    2172                                                 // Compare attributes 
    2173                                                 BackupClientFileAttributes localAttr; 
    2174                                                 box_time_t fileModTime = 0; 
    2175                                                 localAttr.ReadAttributes(localPath.c_str(), false /* don't zero mod times */, &fileModTime);                                     
    2176                                                 modifiedAfterLastSync = (fileModTime > rParams.LatestFileUploadTime()); 
    2177                                                 bool ignoreAttrModTime = true; 
    2178  
    2179                                                 #ifdef WIN32 
    2180                                                 // attr mod time is really 
    2181                                                 // creation time, so check it 
    2182                                                 ignoreAttrModTime = false; 
    2183                                                 #endif 
    2184  
    2185                                                 if(!rParams.IgnoreAttributes() && 
    2186                                                 #ifdef PLATFORM_DISABLE_SYMLINK_ATTRIB_COMPARE 
    2187                                                    !fileOnServerStream->IsSymLink() && 
    2188                                                 #endif 
    2189                                                    !localAttr.Compare(fileOnServerStream->GetAttributes(), 
    2190                                                                 ignoreAttrModTime, 
    2191                                                                 fileOnServerStream->IsSymLink() /* ignore modification time if it's a symlink */)) 
    2192                                                 { 
    2193                                                         hasDifferentAttribs = true; 
    2194                                                 } 
    2195          
    2196                                                 // Compare contents, if it's a regular file not a link 
    2197                                                 // Remember, we MUST read the entire stream from the server. 
    2198                                                 SelfFlushingStream flushObject(*objectStream); 
    2199  
    2200                                                 if(!fileOnServerStream->IsSymLink()) 
    2201                                                 { 
    2202                                                         SelfFlushingStream flushFile(*fileOnServerStream); 
    2203                                                         // Open the local file 
    2204                                                         FileStream l(localPath.c_str()); 
    2205                                                         equal = l.CompareWith(*fileOnServerStream, 
    2206                                                                 mrConnection.GetTimeout()); 
    2207                                                 } 
    2208                                         } 
    2209  
    2210                                         rParams.NotifyFileCompared(localPath, 
    2211                                                 storePath, fileSize, 
    2212                                                 hasDifferentAttribs, !equal, 
    2213                                                 modifiedAfterLastSync, 
    2214                                                 i->second->HasAttributes()); 
    2215                                 } 
    2216                                 catch(BoxException &e) 
    2217                                 { 
    2218                                         rParams.NotifyDownloadFailed(localPath, 
    2219                                                 storePath, fileSize, e); 
    2220                                 } 
    2221                                 catch(std::exception &e) 
    2222                                 { 
    2223                                         rParams.NotifyDownloadFailed(localPath, 
    2224                                                 storePath, fileSize, e); 
    2225                                 } 
    2226                                 catch(...) 
    2227                                 {        
    2228                                         rParams.NotifyDownloadFailed(localPath, 
    2229                                                 storePath, fileSize); 
    2230                                 } 
     2266                                CompareOneFile(DirID, i->second, localPath, 
     2267                                        storePath, rParams); 
    22312268 
    22322269                                // Remove from set so that we know it's been compared 
  • box/trunk/bin/bbackupquery/BackupQueries.h

    r2760 r2851  
    1616#include "BoxTime.h" 
    1717#include "BoxBackupCompareParams.h" 
     18#include "BackupStoreDirectory.h" 
    1819 
    1920class BackupProtocolClient; 
     
    239240                } 
    240241 
     242                virtual void NotifyLocalFileReadFailed(const std::string& rLocalPath, 
     243                        const std::string& rRemotePath, int64_t NumBytes, 
     244                        std::exception& rException) 
     245                { 
     246                        BOX_ERROR("Failed to read local file '" << 
     247                                ConvertForConsole(rLocalPath) << "': " << 
     248                                rException.what()); 
     249                        mUncheckedFiles ++; 
     250                } 
     251 
     252                virtual void NotifyLocalFileReadFailed(const std::string& rLocalPath, 
     253                        const std::string& rRemotePath, int64_t NumBytes) 
     254                { 
     255                        BOX_ERROR("Failed to read local file '" << 
     256                                ConvertForConsole(rLocalPath)); 
     257                        mUncheckedFiles ++; 
     258                } 
     259 
    241260                virtual void NotifyExcludedFile(const std::string& rLocalPath, 
    242261                        const std::string& rRemotePath) 
     
    340359        void Compare(int64_t DirID, const std::string &rStoreDir, 
    341360                const std::string &rLocalDir, BoxBackupCompareParams &rParams); 
     361        void CompareOneFile(int64_t DirID, BackupStoreDirectory::Entry *pEntry, 
     362                const std::string& rLocalPath, const std::string& rStorePath, 
     363                BoxBackupCompareParams &rParams); 
    342364 
    343365public: 
  • box/trunk/bin/bbackupquery/BoxBackupCompareParams.h

    r2467 r2851  
    8383                const std::string& rRemotePath, int64_t NumBytes, 
    8484                BoxException& rException) = 0; 
     85        virtual void NotifyLocalFileReadFailed(const std::string& rLocalPath, 
     86                const std::string& rRemotePath, int64_t NumBytes, 
     87                std::exception& rException) = 0; 
     88        virtual void NotifyLocalFileReadFailed(const std::string& rLocalPath, 
     89                const std::string& rRemotePath, int64_t NumBytes) = 0; 
    8590        virtual void NotifyDownloadFailed(const std::string& rLocalPath, 
    8691                const std::string& rRemotePath, int64_t NumBytes, 
Note: See TracChangeset for help on using the changeset viewer.