From b72bfd530e4f72116586770ae418af7c994bbb56 Mon Sep 17 00:00:00 2001
From: Cedric Caffy <cedric.caffy@cern.ch>
Date: Tue, 1 Sep 2020 15:55:45 +0200
Subject: [PATCH] [rao_lto] Unit tested the InterpolationFilePositionEstimator

---
 .../InterpolationFilePositionEstimator.cpp    |  4 +-
 .../castor/tape/tapeserver/RAO/RAOHelpers.cpp |  2 +-
 .../castor/tape/tapeserver/RAO/RAOTest.cpp    | 87 ++++++++++++++++++-
 3 files changed, 87 insertions(+), 6 deletions(-)

diff --git a/tapeserver/castor/tape/tapeserver/RAO/InterpolationFilePositionEstimator.cpp b/tapeserver/castor/tape/tapeserver/RAO/InterpolationFilePositionEstimator.cpp
index 89362b9b9d..0e5809aa38 100644
--- a/tapeserver/castor/tape/tapeserver/RAO/InterpolationFilePositionEstimator.cpp
+++ b/tapeserver/castor/tape/tapeserver/RAO/InterpolationFilePositionEstimator.cpp
@@ -79,9 +79,9 @@ uint64_t InterpolationFilePositionEstimator::determineLPos(const uint64_t blockI
     fileBlockId -= previousWrapPositionInfos.blockId;
   }
   if(wrapNumber % 2 == 0){
-    fileLpos = minLpos + fileBlockId * (maxLpos - minLpos) / b_max;
+    fileLpos = minLpos + fileBlockId * (maxLpos - minLpos) / (double)b_max;
   } else {
-    fileLpos = maxLpos - fileBlockId * (maxLpos - minLpos) / b_max;
+    fileLpos = maxLpos - fileBlockId * (maxLpos - minLpos) / (double)b_max;
   }
   return fileLpos;
 }
diff --git a/tapeserver/castor/tape/tapeserver/RAO/RAOHelpers.cpp b/tapeserver/castor/tape/tapeserver/RAO/RAOHelpers.cpp
index 06ab695de8..7353378282 100644
--- a/tapeserver/castor/tape/tapeserver/RAO/RAOHelpers.cpp
+++ b/tapeserver/castor/tape/tapeserver/RAO/RAOHelpers.cpp
@@ -28,7 +28,7 @@ namespace castor { namespace tape { namespace tapeserver { namespace rao {
       //No improvement possible
       return;
     }
-    for(uint64_t i = 0; i < nbEndOfWrapPositions - 1; ++i){
+    for(uint64_t i = 1; i < nbEndOfWrapPositions; ++i){
       nbBlocksPerWrap += (endOfWrapPositions.at(i).blockId - endOfWrapPositions.at(i-1).blockId);
     }
     uint64_t meanNbBlocksPerWrap = nbBlocksPerWrap / nbEndOfWrapPositions;
diff --git a/tapeserver/castor/tape/tapeserver/RAO/RAOTest.cpp b/tapeserver/castor/tape/tapeserver/RAO/RAOTest.cpp
index 5287a77ac5..5307fc1163 100644
--- a/tapeserver/castor/tape/tapeserver/RAO/RAOTest.cpp
+++ b/tapeserver/castor/tape/tapeserver/RAO/RAOTest.cpp
@@ -21,6 +21,8 @@
 #include <map>
 
 #include "InterpolationFilePositionEstimator.hpp"
+#include "common/make_unique.hpp"
+#include "RAOHelpers.hpp"
 
 namespace unitTests {
   
@@ -33,6 +35,7 @@ namespace unitTests {
       ret.push_back({0,208310,0});
       ret.push_back({1,416271,0});
       ret.push_back({2,624562,0});
+      ret.push_back({3,633521,0});
       return ret;
     }
     
@@ -43,6 +46,28 @@ namespace unitTests {
       mediaType.maxLPos = 171097;
       return mediaType;
     }
+    
+    static std::unique_ptr<cta::RetrieveJob> createRetrieveJobForRAOTests(const uint64_t blockId, const uint8_t copyNb, const uint64_t fseq, const uint64_t fileSize){
+      std::unique_ptr<cta::RetrieveJob> ret;
+      cta::common::dataStructures::ArchiveFile archiveFile;
+      cta::common::dataStructures::TapeFile tapeFile;
+      tapeFile.blockId = blockId;
+      tapeFile.copyNb = copyNb;
+      tapeFile.fSeq = fseq;
+      tapeFile.fileSize = fileSize;
+      archiveFile.tapeFiles.push_back(tapeFile);
+       cta::common::dataStructures::RetrieveRequest retrieveRequest;
+      ret.reset(new cta::RetrieveJob(nullptr,retrieveRequest,archiveFile,1,cta::PositioningMethod::ByBlock));
+      return ret;
+    }
+    
+    static std::vector<std::unique_ptr<cta::RetrieveJob>> generateRetrieveJobs() {
+      std::vector<std::unique_ptr<cta::RetrieveJob>> ret;
+      ret.emplace_back(createRetrieveJobForRAOTests(0,1,1,10));
+      return ret;
+    }
+    
+    
   };
   
   class RAOTest: public ::testing::Test {
@@ -57,16 +82,72 @@ namespace unitTests {
 
   }; 
 
-  TEST_F(RAOTest,InterpolationFilePositionEstimatorTest){
+  TEST_F(RAOTest,InterpolationFilePositionEstimatorWrap0Test){
+    /**
+     * This test tests the InterpolationFilePositionEstimator::getFilePosition() method
+     */
     
+    std::vector<drive::endOfWrapPosition> eowPositions = RAOTestEnvironment::getEndOfWrapPositions();
+    cta::catalogue::MediaType mediaType = RAOTestEnvironment::getLTO7MMediaType();
     
+    rao::InterpolationFilePositionEstimator estimator(eowPositions,mediaType);
+    {
+      cta::RetrieveJob & retrieveJob = *RAOTestEnvironment::createRetrieveJobForRAOTests(0,1,1,10);
+      rao::FilePosition positionFile = estimator.getFilePosition(retrieveJob);
+      //The LPOS start position of the file should be equal to the minLPos of the LTO7 media type
+      rao::Position startPositionFile = positionFile.getStartPosition();
+      ASSERT_EQ(0,startPositionFile.getWrap());
+      ASSERT_EQ(mediaType.minLPos.value(), startPositionFile.getLPos());
+    }
+    
+    {
+      cta::RetrieveJob & retrieveJob = *RAOTestEnvironment::createRetrieveJobForRAOTests(11,1,2,25);
+      rao::FilePosition positionFile = estimator.getFilePosition(retrieveJob);
+      rao::Position startPositionFile = positionFile.getStartPosition();
+      ASSERT_EQ(0,startPositionFile.getWrap());
+      double b_max = (double) eowPositions.at(0).blockId;
+      uint64_t expectedLPos = mediaType.minLPos.value() + retrieveJob.selectedTapeFile().blockId * (mediaType.maxLPos.value() - mediaType.minLPos.value()) / b_max;
+      ASSERT_EQ(expectedLPos,positionFile.getStartPosition().getLPos());
+    }
+  }
+  
+  TEST_F(RAOTest,InterpolationFilePositionEstimatorWrap1Test){
     std::vector<drive::endOfWrapPosition> eowPositions = RAOTestEnvironment::getEndOfWrapPositions();
     cta::catalogue::MediaType mediaType = RAOTestEnvironment::getLTO7MMediaType();
+    
+    rao::InterpolationFilePositionEstimator estimator(eowPositions,mediaType);
+    
+    {
+      //Now create a retrieve job that has a blockId greater than the first wrap end of wrap position
+      cta::RetrieveJob & retrieveJob = *RAOTestEnvironment::createRetrieveJobForRAOTests(210000,1,1,10);
+      rao::FilePosition positionFile = estimator.getFilePosition(retrieveJob);
+      double b_max = (double) eowPositions.at(1).blockId - (double) eowPositions.at(0).blockId; 
+      uint64_t fileBlockId = retrieveJob.selectedTapeFile().blockId - eowPositions.at(0).blockId;
+      uint64_t expectedLPos = mediaType.maxLPos.value() - fileBlockId * (mediaType.maxLPos.value() - mediaType.minLPos.value()) / b_max;
+      ASSERT_EQ(1,positionFile.getStartPosition().getWrap());
+      ASSERT_EQ(expectedLPos,positionFile.getStartPosition().getLPos());
+    }
+  }
   
+  TEST_F(RAOTest,InterpolationFilePositionEstimatorThrowsExceptionIfBlockIdGreaterThanLastEOWP){
+    std::vector<drive::endOfWrapPosition> eowPositions = RAOTestEnvironment::getEndOfWrapPositions();
+    cta::catalogue::MediaType mediaType = RAOTestEnvironment::getLTO7MMediaType();
+    
     rao::InterpolationFilePositionEstimator estimator(eowPositions,mediaType);
-    //TODO : GENERATE vector of cta::RetrieveJob
     
-    ASSERT_TRUE(true);
+    {
+      cta::RetrieveJob & retrieveJob = *RAOTestEnvironment::createRetrieveJobForRAOTests(100000000,1,3,30);
+      ASSERT_THROW(estimator.getFilePosition(retrieveJob),cta::exception::Exception);
+    }
+  }
+  
+  TEST_F(RAOTest,ImproveLastEOWPIfPossible){
+    std::vector<drive::endOfWrapPosition> eowPositions = RAOTestEnvironment::getEndOfWrapPositions();
+    drive::endOfWrapPosition eowpBeforeImprovement = eowPositions.at(eowPositions.size()-1);
+    rao::RAOHelpers::improveEndOfLastWrapPositionIfPossible(eowPositions);
+    drive::endOfWrapPosition eowpAfterImprovement = eowPositions.at(eowPositions.size()-1);
+    ASSERT_LT(eowpBeforeImprovement.blockId,eowpAfterImprovement.blockId);
+    
   }
   
 }
-- 
GitLab