Coverage for /Syzygy/core/file_util.cc

CoverageLines executed / instrumented / missingexe / inst / missLanguageGroup
78.9%30380.C++source

Line-by-line coverage:

   1    :  // Copyright 2011 Google Inc. All Rights Reserved.
   2    :  //
   3    :  // Licensed under the Apache License, Version 2.0 (the "License");
   4    :  // you may not use this file except in compliance with the License.
   5    :  // You may obtain a copy of the License at
   6    :  //
   7    :  //     http://www.apache.org/licenses/LICENSE-2.0
   8    :  //
   9    :  // Unless required by applicable law or agreed to in writing, software
  10    :  // distributed under the License is distributed on an "AS IS" BASIS,
  11    :  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12    :  // See the License for the specific language governing permissions and
  13    :  // limitations under the License.
  14    :  
  15    :  #include "syzygy/core/file_util.h"
  16    :  
  17    :  #include "base/file_util.h"
  18    :  #include "base/win/scoped_handle.h"
  19    :  #include "sawbuck/common/com_utils.h"
  20    :  
  21    :  namespace core {
  22    :  
  23    :  namespace {
  24    :  
  25    :  enum FileInformationResult {
  26    :    kFileNotFound,
  27    :    kSuccess,
  28    :    kFailure
  29    :  };
  30    :  
  31    :  // Gets a handle to a file, and the file information for it. Leaves the handle
  32    :  // open.
  33    :  FileInformationResult GetFileInformation(
  34    :      const base::FilePath& path,
  35    :      base::win::ScopedHandle* handle,
  36  E :      BY_HANDLE_FILE_INFORMATION* file_info) {
  37    :    // Open the file in the least restrictive possible way.
  38    :    handle->Set(
  39    :        ::CreateFile(path.value().c_str(),
  40    :                     SYNCHRONIZE,
  41    :                     FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE,
  42    :                     NULL,
  43    :                     OPEN_EXISTING,
  44    :                     FILE_ATTRIBUTE_NORMAL,
  45  E :                     NULL));
  46  E :    if (!handle->IsValid()) {
  47    :      // The file not being found is a special case.
  48  E :      DWORD error = ::GetLastError();
  49  E :      if (error == ERROR_FILE_NOT_FOUND || error == ERROR_PATH_NOT_FOUND)
  50  E :        return kFileNotFound;
  51    :  
  52  i :      LOG(ERROR) << "Unable to open \"" << path.value() << "\": "
  53    :                 << com::LogWe(error);
  54  i :      return kFailure;
  55    :    }
  56    :  
  57  E :    if (!::GetFileInformationByHandle(handle->Get(), file_info)) {
  58  i :      DWORD error = ::GetLastError();
  59  i :      LOG(ERROR) << "GetFileInformationByHandle failed for \"" << path.value()
  60    :                 << "\": " << com::LogWe(error);
  61  i :      return kFailure;
  62    :    }
  63    :  
  64  E :    return kSuccess;
  65  E :  }
  66    :  
  67    :  }  // namespace
  68    :  
  69    :  FilePathCompareResult CompareFilePaths(const base::FilePath& path1,
  70  E :                                         const base::FilePath& path2) {
  71    :    // Now we try opening both files for reading to see if they point to the same
  72    :    // underlying volume and file index. We open both files simultaneously to
  73    :    // avoid a race condition whereby the file could be moved/removed in between
  74    :    // the two calls to GetFileInformation.
  75    :  
  76  E :    base::win::ScopedHandle handle1;
  77  E :    BY_HANDLE_FILE_INFORMATION info1 = {};
  78  E :    FileInformationResult result1 = GetFileInformation(path1, &handle1, &info1);
  79  E :    if (result1 == kFailure)
  80  i :      return kFilePathCompareError;
  81    :  
  82  E :    base::win::ScopedHandle handle2;
  83  E :    BY_HANDLE_FILE_INFORMATION info2 = {};
  84  E :    FileInformationResult result2 = GetFileInformation(path2, &handle2, &info2);
  85  E :    if (result2 == kFailure)
  86  i :      return kFilePathCompareError;
  87    :  
  88    :    // If neither file exists we can't really compare them based on anything
  89    :    // other than the path itself.
  90  E :    if (result1 == kFileNotFound && result2 == kFileNotFound) {
  91  E :      base::FilePath abs1(MakeAbsoluteFilePath(path1));
  92  E :      base::FilePath abs2(MakeAbsoluteFilePath(path2));
  93    :  
  94  E :      if (abs1.empty() || abs2.empty())
  95  i :        return kUnableToCompareFilePaths;
  96    :  
  97  E :      if (abs1 == abs2)
  98  E :        return kEquivalentFilePaths;
  99    :  
 100  E :      return kUnableToCompareFilePaths;
 101    :    }
 102    :  
 103    :    // If only one of them exists, then they can't possibly be the same file.
 104  E :    if (result1 == kFileNotFound || result2 == kFileNotFound)
 105  E :      return kDistinctFilePaths;
 106    :  
 107    :    // If they both exist we compare the details of where they live on disk.
 108    :    bool identical = info1.dwVolumeSerialNumber == info2.dwVolumeSerialNumber &&
 109    :        info1.nFileIndexLow == info2.nFileIndexLow &&
 110  E :        info1.nFileIndexHigh == info2.nFileIndexHigh;
 111    :  
 112  E :    return identical ? kEquivalentFilePaths : kDistinctFilePaths;
 113  E :  }
 114    :  
 115    :  }  // namespace core

Coverage information generated Tue Jun 25 13:56:24 2013.