From 013514de827750426d95d3e91b0186647c2e9363 Mon Sep 17 00:00:00 2001 From: Andreas Joachim Peters Date: Fri, 7 Jun 2024 15:13:21 +0200 Subject: [PATCH] XrdApps::JCache: restructure source directories - make readV,read/pgRead completely asynchronous functions using response handlers --- src/XrdApps.cmake | 12 ++- .../{ => app}/CacheCleaner.py | 0 .../{ => app}/XrdClCacheCleaner.cc | 0 .../{ => file}/XrdClJCacheFile.cc | 102 +++++++----------- .../{ => file}/XrdClJCacheFile.hh | 64 ++++++++++- .../handler/XrdClJCacheReadHandler.hh | 72 +++++++++++++ .../handler/XrdClJCacheReadVHandler.hh | 92 ++++++++++++++++ .../{ => plugin}/XrdClJCachePlugin.cc | 2 +- .../{ => plugin}/XrdClJCachePlugin.hh | 9 +- .../{ => vector}/XrdClVectorCache.cc | 8 +- .../{ => vector}/XrdClVectorCache.hh | 4 + 11 files changed, 288 insertions(+), 77 deletions(-) rename src/XrdApps/XrdClJCachePlugin/{ => app}/CacheCleaner.py (100%) rename src/XrdApps/XrdClJCachePlugin/{ => app}/XrdClCacheCleaner.cc (100%) rename src/XrdApps/XrdClJCachePlugin/{ => file}/XrdClJCacheFile.cc (84%) rename src/XrdApps/XrdClJCachePlugin/{ => file}/XrdClJCacheFile.hh (80%) create mode 100644 src/XrdApps/XrdClJCachePlugin/handler/XrdClJCacheReadHandler.hh create mode 100644 src/XrdApps/XrdClJCachePlugin/handler/XrdClJCacheReadVHandler.hh rename src/XrdApps/XrdClJCachePlugin/{ => plugin}/XrdClJCachePlugin.cc (97%) rename src/XrdApps/XrdClJCachePlugin/{ => plugin}/XrdClJCachePlugin.hh (90%) rename src/XrdApps/XrdClJCachePlugin/{ => vector}/XrdClVectorCache.cc (99%) rename src/XrdApps/XrdClJCachePlugin/{ => vector}/XrdClVectorCache.hh (98%) diff --git a/src/XrdApps.cmake b/src/XrdApps.cmake index 9cce4573531..d990636d079 100644 --- a/src/XrdApps.cmake +++ b/src/XrdApps.cmake @@ -208,7 +208,7 @@ target_link_libraries( add_executable( xrdclcacheclean - XrdApps/XrdClJCachePlugin/XrdClCacheCleaner.cc ) + XrdApps/XrdClJCachePlugin/app/XrdClCacheCleaner.cc ) target_link_libraries( xrdclcacheclean @@ -221,16 +221,18 @@ target_link_libraries( add_library( ${LIB_XRDCL_JCACHE_PLUGIN} MODULE - XrdApps/XrdClJCachePlugin/XrdClJCachePlugin.cc - XrdApps/XrdClJCachePlugin/XrdClJCacheFile.cc - XrdApps/XrdClJCachePlugin/XrdClVectorCache.cc - XrdApps/XrdClJCachePlugin/XrdClVectorCache.hh + XrdApps/XrdClJCachePlugin/plugin/XrdClJCachePlugin.cc + XrdApps/XrdClJCachePlugin/file/XrdClJCacheFile.cc + XrdApps/XrdClJCachePlugin/vector/XrdClVectorCache.cc + XrdApps/XrdClJCachePlugin/vector/XrdClVectorCache.hh XrdApps/XrdClJCachePlugin/cache/Journal.cc XrdApps/XrdClJCachePlugin/cache/Journal.hh XrdApps/XrdClJCachePlugin/cache/IntervalTree.hh XrdApps/XrdClJCachePlugin/cache/RbTree.hh ) +target_include_directories( ${LIB_XRDCL_JCACHE_PLUGIN} PRIVATE "${CMAKE_SOURCE_DIR}/src/XrdApps/XrdClJCachePlugin/" ) + target_link_libraries(${LIB_XRDCL_JCACHE_PLUGIN} PRIVATE XrdCl stdc++fs) diff --git a/src/XrdApps/XrdClJCachePlugin/CacheCleaner.py b/src/XrdApps/XrdClJCachePlugin/app/CacheCleaner.py similarity index 100% rename from src/XrdApps/XrdClJCachePlugin/CacheCleaner.py rename to src/XrdApps/XrdClJCachePlugin/app/CacheCleaner.py diff --git a/src/XrdApps/XrdClJCachePlugin/XrdClCacheCleaner.cc b/src/XrdApps/XrdClJCachePlugin/app/XrdClCacheCleaner.cc similarity index 100% rename from src/XrdApps/XrdClJCachePlugin/XrdClCacheCleaner.cc rename to src/XrdApps/XrdClJCachePlugin/app/XrdClCacheCleaner.cc diff --git a/src/XrdApps/XrdClJCachePlugin/XrdClJCacheFile.cc b/src/XrdApps/XrdClJCachePlugin/file/XrdClJCacheFile.cc similarity index 84% rename from src/XrdApps/XrdClJCachePlugin/XrdClJCacheFile.cc rename to src/XrdApps/XrdClJCachePlugin/file/XrdClJCacheFile.cc index 168cae744aa..cc560764453 100644 --- a/src/XrdApps/XrdClJCachePlugin/XrdClJCacheFile.cc +++ b/src/XrdApps/XrdClJCachePlugin/file/XrdClJCacheFile.cc @@ -27,10 +27,23 @@ #include "XrdCl/XrdClMessageUtils.hh" /*----------------------------------------------------------------------------*/ -std::string JCacheFile::sCachePath=""; -bool JCacheFile::sEnableJournalCache = true; -bool JCacheFile::sEnableVectorCache = true; +std::string XrdCl::JCacheFile::sCachePath=""; +bool XrdCl::JCacheFile::sEnableJournalCache = true; +bool XrdCl::JCacheFile::sEnableVectorCache = true; +namespace XrdCl +{ + +//------------------------------------------------------------------------------ +// Constructor +//------------------------------------------------------------------------------ +JCacheFile::JCacheFile(const std::string& url): + mIsOpen(false), + pFile(0) +{ + mAttachedForRead = false; + mLog = DefaultEnv::GetLog(); +} //------------------------------------------------------------------------------ // Constructor //------------------------------------------------------------------------------ @@ -39,6 +52,7 @@ JCacheFile::JCacheFile(): pFile(0) { mAttachedForRead = false; + mLog = DefaultEnv::GetLog(); } @@ -47,7 +61,7 @@ JCacheFile::JCacheFile(): //------------------------------------------------------------------------------ JCacheFile::~JCacheFile() { - + LogStats(); if (pFile) { delete pFile; } @@ -158,6 +172,8 @@ JCacheFile::Read(uint64_t offset, if (sEnableJournalCache && AttachForRead()) { auto rb = pJournal.pread(buffer, size, offset); if (rb == size) { + pStats.bytesCached += rb; + pStats.readOps++; // we can only serve success full reads from the cache for now XRootDStatus* ret_st = new XRootDStatus(st); ChunkInfo* chunkInfo = new ChunkInfo(offset, rb, buffer); @@ -169,20 +185,9 @@ JCacheFile::Read(uint64_t offset, } } - // run a synchronous read - uint32_t bytesRead = 0; - st = pFile->Read(offset, size, buffer, bytesRead, timeout); - if (st.IsOK()) { - if (sEnableJournalCache) { - pJournal.pwrite(buffer, size, offset); - } - // emit a chunk - XRootDStatus* ret_st = new XRootDStatus(st); - ChunkInfo* chunkInfo = new ChunkInfo(offset, bytesRead, buffer); - AnyObject* obj = new AnyObject(); - obj->Set(chunkInfo); - handler->HandleResponse(ret_st, obj); - } + auto jhandler = new JCacheReadHandler(handler, &pStats.bytesRead,sEnableJournalCache?&pJournal:nullptr); + pStats.readOps++; + st = pFile->PgRead(offset, size, buffer, jhandler, timeout); } else { st = XRootDStatus(stError, errInvalidOp); } @@ -227,6 +232,8 @@ JCacheFile::PgRead( uint64_t offset, if (sEnableJournalCache && AttachForRead()) { auto rb = pJournal.pread(buffer, size, offset); if (rb == size) { + pStats.bytesCached += rb; + pStats.readOps++; // we can only serve success full reads from the cache for now XRootDStatus* ret_st = new XRootDStatus(st); ChunkInfo* chunkInfo = new ChunkInfo(offset, rb, buffer); @@ -238,25 +245,9 @@ JCacheFile::PgRead( uint64_t offset, } } - std::vector cksums; - uint32_t bytesRead = 0; - - // run a synchronous read - st = pFile->PgRead(offset, size, buffer, cksums, bytesRead, timeout); - if (st.IsOK()) { - if (sEnableJournalCache) { - if (bytesRead) { - // store into journal - pJournal.pwrite(buffer, size, offset); - } - } - // emit a chunk - XRootDStatus* ret_st = new XRootDStatus(st); - ChunkInfo* chunkInfo = new ChunkInfo(offset, bytesRead, buffer); - AnyObject* obj = new AnyObject(); - obj->Set(chunkInfo); - handler->HandleResponse(ret_st, obj); - } + auto jhandler = new JCacheReadHandler(handler, &pStats.bytesRead,sEnableJournalCache?&pJournal:nullptr); + pStats.readOps++; + st = pFile->PgRead(offset, size, buffer, jhandler, timeout); } else { st = XRootDStatus(stError, errInvalidOp); } @@ -358,33 +349,12 @@ JCacheFile::VectorRead(const ChunkList& chunks, } } - // run a synchronous vector read + auto jhandler = new JCacheReadVHandler(handler, &pStats.bytesReadV,sEnableJournalCache?&pJournal:nullptr, buffer, sEnableVectorCache?sCachePath:"", pUrl); + pStats.readVOps++; + pStats.readVreadOps += chunks.size(); - VectorReadInfo* vReadInfo; - st = pFile->VectorRead(chunks, buffer, vReadInfo, timeout); + st = pFile->VectorRead(chunks, buffer, jhandler, timeout); - if (st.IsOK()) { - if (sEnableVectorCache) { - // store into cache - cache.store(); - } - // emit a chunk - XRootDStatus* ret_st = new XRootDStatus(st); - AnyObject* obj = new AnyObject(); - ChunkList vResp = vReadInfo->GetChunks(); - vResp = chunks; - obj->Set(vReadInfo); - - if (sEnableJournalCache && !sEnableVectorCache) { - // if we run with journal cache but don't cache vectors, we need to - // copy the vector data into the journal cache - for (auto it = chunks.begin(); it != chunks.end(); ++it) { - pJournal.pwrite(it->buffer, it->GetLength(), it->GetOffset()); - } - } - handler->HandleResponse(ret_st, obj); - return st; - } } else { st = XRootDStatus(stError, errInvalidOp); } @@ -485,10 +455,12 @@ JCacheFile::AttachForRead() auto st = pFile->Stat(false, sinfo); if (sinfo) { if (pJournal.attach(pJournalPath,sinfo->GetSize(),sinfo->GetModTime(),0)) { - std::cerr << "error: unable to attach to journal: " << pJournalPath << std::endl; + mLog->Error(1, "JCache : failed to attach to cache directory: %s", pJournalPath.c_str()); mAttachedForRead = true; return false; - } + } else { + mLog->Info(1, "JCache : attached to cache directory: %s", pJournalPath.c_str()); + } } } } @@ -496,3 +468,5 @@ JCacheFile::AttachForRead() return true; } +} // namespace XrdCl + diff --git a/src/XrdApps/XrdClJCachePlugin/XrdClJCacheFile.hh b/src/XrdApps/XrdClJCachePlugin/file/XrdClJCacheFile.hh similarity index 80% rename from src/XrdApps/XrdClJCachePlugin/XrdClJCacheFile.hh rename to src/XrdApps/XrdClJCachePlugin/file/XrdClJCacheFile.hh index c553e48768b..053abe1baa1 100644 --- a/src/XrdApps/XrdClJCachePlugin/XrdClJCacheFile.hh +++ b/src/XrdApps/XrdClJCachePlugin/file/XrdClJCacheFile.hh @@ -25,13 +25,19 @@ /*----------------------------------------------------------------------------*/ #include "XrdCl/XrdClPlugInInterface.hh" +#include "XrdCl/XrdClDefaultEnv.hh" +#include "XrdCl/XrdClLog.hh" +/*----------------------------------------------------------------------------*/ #include "cache/Journal.hh" -#include "XrdClVectorCache.hh" +#include "vector/XrdClVectorCache.hh" +#include "handler/XrdClJCacheReadHandler.hh" +#include "handler/XrdClJCacheReadVHandler.hh" /*----------------------------------------------------------------------------*/ #include /*----------------------------------------------------------------------------*/ -using namespace XrdCl; +namespace XrdCl +{ //---------------------------------------------------------------------------- //! RAIN file plugin //---------------------------------------------------------------------------- @@ -43,7 +49,7 @@ public: //! Constructor //---------------------------------------------------------------------------- JCacheFile(); - + JCacheFile(const std::string& url); //---------------------------------------------------------------------------- //! Destructor @@ -196,10 +202,54 @@ public: static std::string sCachePath; static bool sEnableVectorCache; static bool sEnableJournalCache; + + void LogStats() { + mLog->Info(1, "JCache : read:readv-ops:readv-read-ops: %lu:%lu:%lus hit-rate: total [read/readv]=%.02f%% [%.02f%%/%.02f%%] remote-bytes-read/readv: %lu / %lu cached-bytes-read/readv: %lu / %lu", + pStats.readOps.load(), + pStats.readVOps.load(), + pStats.readVreadOps.load(), + pStats.CombinedHitRate(), + pStats.HitRate(), + pStats.HitRateV(), + pStats.bytesRead.load(), + pStats.bytesReadV.load(), + pStats.bytesCached.load(), + pStats.bytesCachedV.load()); + } + //! structure about cache hit statistics + struct CacheStats { + CacheStats() : + bytesRead(0), + bytesReadV(0), + bytesCached(0), + bytesCachedV(0), + readOps(0), + readVOps(0), + readVreadOps(0) + {} + + double HitRate() { + return 100.0*(this->bytesCached.load()+1) /(this->bytesCached.load()+this->bytesRead.load()+1); + } + double HitRateV() { + return 100.0*(this->bytesCachedV.load()+1) /(this->bytesCachedV.load()+this->bytesReadV.load()+1); + } + double CombinedHitRate() { + return 100.0*(this->bytesCached.load()+this->bytesCachedV.load()+1) /(this->bytesCached.load()+this->bytesRead.load()+this->bytesCachedV.load()+this->bytesReadV.load()+1); + } + + std::atomic bytesRead; + std::atomic bytesReadV; + std::atomic bytesCached; + std::atomic bytesCachedV; + std::atomic readOps; + std::atomic readVOps; + std::atomic readVreadOps; + }; private: bool AttachForRead(); - + std::atomic mAttachedForRead; std::mutex mAttachMutex; OpenFlags::Flags mFlags; @@ -208,5 +258,11 @@ private: std::string pUrl; Journal pJournal; std::string pJournalPath; + Log* mLog; + + CacheStats pStats; + + std::vector mReadHandlers; }; +} // namespace XrdCl \ No newline at end of file diff --git a/src/XrdApps/XrdClJCachePlugin/handler/XrdClJCacheReadHandler.hh b/src/XrdApps/XrdClJCachePlugin/handler/XrdClJCacheReadHandler.hh new file mode 100644 index 00000000000..f2a2727a6a4 --- /dev/null +++ b/src/XrdApps/XrdClJCachePlugin/handler/XrdClJCacheReadHandler.hh @@ -0,0 +1,72 @@ +//------------------------------------------------------------------------------ +// Copyright (c) 2024 by European Organization for Nuclear Research (CERN) +// Author: Andreas-Joachim Peters +//------------------------------------------------------------------------------ +// This file is part of the XRootD software suite. +// +// XRootD is free software: you can redistribute it and/or modify +// it under the terms of the GNU Lesser General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// XRootD is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public License +// along with XRootD. If not, see . +// +// In applying this licence, CERN does not waive the privileges and immunities +// granted to it by virtue of its status as an Intergovernmental Organization +// or submit itself to any jurisdiction. + +#pragma once +/*----------------------------------------------------------------------------*/ +#include "XrdCl/XrdClFile.hh" +#include "XrdCl/XrdClXRootDResponses.hh" +/*----------------------------------------------------------------------------*/ +#include "cache/Journal.hh" +/*----------------------------------------------------------------------------*/ + +namespace XrdCl { + +class JCacheReadHandler : public XrdCl::ResponseHandler + // ---------------------------------------------------------------------- // +{ +public: + JCacheReadHandler() { } + + JCacheReadHandler(JCacheReadHandler* other) { + rbytes = other->rbytes; + journal = other->journal; + } + + JCacheReadHandler(XrdCl::ResponseHandler* handler, + std::atomic* rbytes, + Journal* journal) : handler(handler), rbytes(rbytes), journal(journal) {} + + virtual ~JCacheReadHandler() {} + + virtual void HandleResponse(XrdCl::XRootDStatus* pStatus, + XrdCl::AnyObject* pResponse) { + + XrdCl::PageInfo* pageInfo; + if (pStatus->IsOK()) { + if (pResponse) { + pResponse->Get(pageInfo); + // store successfull reads in the journal + if (journal) journal->pwrite(pageInfo->GetBuffer(), pageInfo->GetLength(), pageInfo->GetOffset()); + *rbytes+= pageInfo->GetLength(); + } + } + handler->HandleResponse(pStatus, pResponse); + } + + XrdCl::ResponseHandler* handler; + std::atomic* rbytes; + Journal* journal; + +}; + +} // namespace XrdCl diff --git a/src/XrdApps/XrdClJCachePlugin/handler/XrdClJCacheReadVHandler.hh b/src/XrdApps/XrdClJCachePlugin/handler/XrdClJCacheReadVHandler.hh new file mode 100644 index 00000000000..ed7518d9670 --- /dev/null +++ b/src/XrdApps/XrdClJCachePlugin/handler/XrdClJCacheReadVHandler.hh @@ -0,0 +1,92 @@ +//------------------------------------------------------------------------------ +// Copyright (c) 2024 by European Organization for Nuclear Research (CERN) +// Author: Andreas-Joachim Peters +//------------------------------------------------------------------------------ +// This file is part of the XRootD software suite. +// +// XRootD is free software: you can redistribute it and/or modify +// it under the terms of the GNU Lesser General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// XRootD is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public License +// along with XRootD. If not, see . +// +// In applying this licence, CERN does not waive the privileges and immunities +// granted to it by virtue of its status as an Intergovernmental Organization +// or submit itself to any jurisdiction. + +#pragma once +/*----------------------------------------------------------------------------*/ +#include "XrdCl/XrdClFile.hh" +#include "XrdCl/XrdClXRootDResponses.hh" +/*----------------------------------------------------------------------------*/ +#include "cache/Journal.hh" +#include "vector/XrdClVectorCache.hh" +/*----------------------------------------------------------------------------*/ + +namespace XrdCl { + +class JCacheReadVHandler : public XrdCl::ResponseHandler + // ---------------------------------------------------------------------- // +{ +public: + JCacheReadVHandler() { } + + JCacheReadVHandler(JCacheReadVHandler* other) { + + journal = other->journal; + buffer = other->buffer; + rvbytes = other->rvbytes; + vcachepath = other->vcachepath; + url = other->url; + } + + JCacheReadVHandler(XrdCl::ResponseHandler* handler, + std::atomic* rvbytes, + Journal* journal, + void* buffer, + const std::string& vcachepath, + const std::string& url) : handler(handler), rvbytes(rvbytes), journal(journal), buffer(buffer), vcachepath(vcachepath), url(url) {} + + virtual ~JCacheReadVHandler() {} + + virtual void HandleResponse(XrdCl::XRootDStatus* pStatus, + XrdCl::AnyObject* pResponse) { + if (pStatus->IsOK()) { + if (pResponse) { + ChunkList* chunks; + pResponse->Get(chunks); + // store successfull reads in the journal if there is no vector cache + if (journal) { + if (vcachepath.empty()) { + for (auto it = chunks->begin(); it != chunks->end(); ++it) { + journal->pwrite(it->GetBuffer(), it->GetLength(), it->GetOffset()); + } + } else { + VectorCache cache(*chunks, url, (const char*)buffer, vcachepath); + cache.store(); + } + } + for (auto it = chunks->begin(); it != chunks->end(); ++it) { + *rvbytes += it->GetLength(); + } + } + } + handler->HandleResponse(pStatus, pResponse); + } + + XrdCl::ResponseHandler* handler; + std::atomic* rvbytes; + Journal* journal; + void* buffer; + std::string vcachepath; + std::string url; +}; + +} // namespace XrdCl diff --git a/src/XrdApps/XrdClJCachePlugin/XrdClJCachePlugin.cc b/src/XrdApps/XrdClJCachePlugin/plugin/XrdClJCachePlugin.cc similarity index 97% rename from src/XrdApps/XrdClJCachePlugin/XrdClJCachePlugin.cc rename to src/XrdApps/XrdClJCachePlugin/plugin/XrdClJCachePlugin.cc index 85f2a93b319..a065303b5f5 100644 --- a/src/XrdApps/XrdClJCachePlugin/XrdClJCachePlugin.cc +++ b/src/XrdApps/XrdClJCachePlugin/plugin/XrdClJCachePlugin.cc @@ -22,7 +22,7 @@ // or submit itself to any jurisdiction. //------------------------------------------------------------------------------ -#include "XrdClJCachePlugin.hh" +#include "plugin/XrdClJCachePlugin.hh" XrdVERSIONINFO(XrdClGetPlugIn, XrdClGetPlugIn) diff --git a/src/XrdApps/XrdClJCachePlugin/XrdClJCachePlugin.hh b/src/XrdApps/XrdClJCachePlugin/plugin/XrdClJCachePlugin.hh similarity index 90% rename from src/XrdApps/XrdClJCachePlugin/XrdClJCachePlugin.hh rename to src/XrdApps/XrdClJCachePlugin/plugin/XrdClJCachePlugin.hh index 4bffbcdde8d..71f3a1a4e01 100644 --- a/src/XrdApps/XrdClJCachePlugin/XrdClJCachePlugin.hh +++ b/src/XrdApps/XrdClJCachePlugin/plugin/XrdClJCachePlugin.hh @@ -22,10 +22,17 @@ // or submit itself to any jurisdiction. #pragma once +/*----------------------------------------------------------------------------*/ #include "XrdCl/XrdClPlugInInterface.hh" -#include "XrdClJCacheFile.hh" #include "XrdCl/XrdClDefaultEnv.hh" #include "XrdCl/XrdClLog.hh" +/*----------------------------------------------------------------------------*/ +#include "../file/XrdClJCacheFile.hh" +/*----------------------------------------------------------------------------*/ +#include +#include +#include +/*----------------------------------------------------------------------------*/ namespace XrdCl { diff --git a/src/XrdApps/XrdClJCachePlugin/XrdClVectorCache.cc b/src/XrdApps/XrdClJCachePlugin/vector/XrdClVectorCache.cc similarity index 99% rename from src/XrdApps/XrdClJCachePlugin/XrdClVectorCache.cc rename to src/XrdApps/XrdClJCachePlugin/vector/XrdClVectorCache.cc index 9d26a138e56..7b4d076269f 100644 --- a/src/XrdApps/XrdClJCachePlugin/XrdClVectorCache.cc +++ b/src/XrdApps/XrdClJCachePlugin/vector/XrdClVectorCache.cc @@ -22,12 +22,14 @@ // or submit itself to any jurisdiction. /*----------------------------------------------------------------------------*/ -#include "XrdClVectorCache.hh" +#include "vector/XrdClVectorCache.hh" #include /*----------------------------------------------------------------------------*/ namespace fs = std::filesystem; - + +namespace XrdCl { + //---------------------------------------------------------------------------- //! serialize a vector into a buffer //---------------------------------------------------------------------------- @@ -224,3 +226,5 @@ bool VectorCache::retrieve() const { return false; } } + +} // namespace XrdCl \ No newline at end of file diff --git a/src/XrdApps/XrdClJCachePlugin/XrdClVectorCache.hh b/src/XrdApps/XrdClJCachePlugin/vector/XrdClVectorCache.hh similarity index 98% rename from src/XrdApps/XrdClJCachePlugin/XrdClVectorCache.hh rename to src/XrdApps/XrdClJCachePlugin/vector/XrdClVectorCache.hh index 1c71e10f0c3..673eee32335 100644 --- a/src/XrdApps/XrdClJCachePlugin/XrdClVectorCache.hh +++ b/src/XrdApps/XrdClJCachePlugin/vector/XrdClVectorCache.hh @@ -40,6 +40,8 @@ //! VectorCache class caching readv buffers on a filesystem //---------------------------------------------------------------------------- +namespace XrdCl { + class VectorCache { public: VectorCache(const XrdCl::ChunkList chunks, const std::string& name, const char* data, const std::string& prefix, bool verbose=false) @@ -62,3 +64,5 @@ private: std::vector serializeVector() const; }; + +} // namespace XrdCl \ No newline at end of file