You've already forked mariadb-columnstore-engine
mirror of
https://github.com/mariadb-corporation/mariadb-columnstore-engine.git
synced 2025-12-13 23:02:14 +03:00
Finished initial cut of the Cache class
This commit is contained in:
@@ -103,22 +103,26 @@ void Cache::read(const vector<string> &keys)
|
|||||||
else
|
else
|
||||||
// not in the cache, put it in the list to download
|
// not in the cache, put it in the list to download
|
||||||
keysToFetch.push_back(&key);
|
keysToFetch.push_back(&key);
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: get the sizes of the objects to download and make space
|
|
||||||
// For now using an estimate
|
|
||||||
makeSpace(keys.size() * objectSize);
|
|
||||||
|
|
||||||
s.unlock();
|
s.unlock();
|
||||||
|
|
||||||
// start downloading the keys to fetch
|
// start downloading the keys to fetch
|
||||||
int dl_err;
|
int dl_err;
|
||||||
vector<int> dl_errnos;
|
vector<int> dl_errnos;
|
||||||
|
vector<size_t> sizes;
|
||||||
if (!keysToFetch.empty())
|
if (!keysToFetch.empty())
|
||||||
dl_err = downloader.download(keysToFetch, &dl_errnos);
|
dl_err = downloader.download(keysToFetch, &dl_errnos, &sizes);
|
||||||
|
|
||||||
|
size_t sum_sizes = 0;
|
||||||
|
for (size_t &size : sizes)
|
||||||
|
sum_sizes += size;
|
||||||
|
|
||||||
s.lock();
|
s.lock();
|
||||||
|
// do makespace() before downloading. Problem is, until the download is finished, this fcn can't tell which
|
||||||
|
// downloads it was responsible for. Need Downloader to make the call...?
|
||||||
|
makeSpace(sum_sizes);
|
||||||
|
currentCacheSize += sum_sizes;
|
||||||
|
|
||||||
// move all keys to the back of the LRU
|
// move all keys to the back of the LRU
|
||||||
for (i = 0; i < keys.size(); i++)
|
for (i = 0; i < keys.size(); i++)
|
||||||
{
|
{
|
||||||
@@ -131,7 +135,8 @@ void Cache::read(const vector<string> &keys)
|
|||||||
else if (dl_errnos[i] == 0) // successful download
|
else if (dl_errnos[i] == 0) // successful download
|
||||||
{
|
{
|
||||||
lru.push_back(keys[i]);
|
lru.push_back(keys[i]);
|
||||||
m_lru.insert(M_LRU_element_t(&(lru.back()), lru.end()--));
|
LRU_t::iterator it = lru.end();
|
||||||
|
m_lru.insert(M_LRU_element_t(--it));
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@@ -189,14 +194,31 @@ void Cache::exists(const vector<string> &keys, vector<bool> *out)
|
|||||||
|
|
||||||
void Cache::newObject(const string &key, size_t size)
|
void Cache::newObject(const string &key, size_t size)
|
||||||
{
|
{
|
||||||
|
boost::unique_lock<boost::mutex> s(lru_mutex);
|
||||||
|
assert(m_lru.find(key) == m_lru.end());
|
||||||
|
makeSpace(size);
|
||||||
|
lru.push_back(key);
|
||||||
|
LRU_t::iterator back = lru.end();
|
||||||
|
m_lru.insert(--back);
|
||||||
|
currentCacheSize += size;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Cache::deletedObject(const string &key, size_t size)
|
void Cache::deletedObject(const string &key, size_t size)
|
||||||
{
|
{
|
||||||
|
boost::unique_lock<boost::mutex> s(lru_mutex);
|
||||||
|
M_LRU_t::iterator mit = m_lru.find(key);
|
||||||
|
assert(mit != m_lru.end());
|
||||||
|
assert(doNotEvict.find(mit->lit) == doNotEvict.end());
|
||||||
|
lru.erase(mit->lit);
|
||||||
|
m_lru.erase(mit);
|
||||||
|
currentCacheSize -= size;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Cache::setMaxCacheSize(size_t size)
|
void Cache::setMaxCacheSize(size_t size)
|
||||||
{
|
{
|
||||||
|
if (size < maxCacheSize)
|
||||||
|
makeSpace(maxCacheSize - size);
|
||||||
|
maxCacheSize = size;
|
||||||
}
|
}
|
||||||
|
|
||||||
// call this holding lru_mutex
|
// call this holding lru_mutex
|
||||||
@@ -251,7 +273,7 @@ Cache::M_LRU_element_t::M_LRU_element_t(const string *k) : key(k)
|
|||||||
Cache::M_LRU_element_t::M_LRU_element_t(const string &k) : key(&k)
|
Cache::M_LRU_element_t::M_LRU_element_t(const string &k) : key(&k)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
Cache::M_LRU_element_t::M_LRU_element_t(const string *k, const LRU_t::iterator &i) : key(k), lit(i)
|
Cache::M_LRU_element_t::M_LRU_element_t(const LRU_t::iterator &i) : key(&(*i)), lit(i)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
inline size_t Cache::KeyHasher::operator()(const M_LRU_element_t &l) const
|
inline size_t Cache::KeyHasher::operator()(const M_LRU_element_t &l) const
|
||||||
|
|||||||
@@ -52,7 +52,7 @@ class Cache : public boost::noncopyable
|
|||||||
{
|
{
|
||||||
M_LRU_element_t(const std::string &);
|
M_LRU_element_t(const std::string &);
|
||||||
M_LRU_element_t(const std::string *);
|
M_LRU_element_t(const std::string *);
|
||||||
M_LRU_element_t(const std::string *, const LRU_t::iterator &);
|
M_LRU_element_t(const LRU_t::iterator &);
|
||||||
const std::string *key;
|
const std::string *key;
|
||||||
LRU_t::iterator lit;
|
LRU_t::iterator lit;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -11,7 +11,7 @@ class CloudStorage
|
|||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
/* These behave like syscalls. return code -1 means an error, and errno is set */
|
/* These behave like syscalls. return code -1 means an error, and errno is set */
|
||||||
virtual int getObject(const std::string &sourceKey, const std::string &destFile) = 0;
|
virtual int getObject(const std::string &sourceKey, const std::string &destFile, size_t *size = NULL) = 0;
|
||||||
virtual int putObject(const std::string &sourceFile, const std::string &destKey) = 0;
|
virtual int putObject(const std::string &sourceFile, const std::string &destKey) = 0;
|
||||||
virtual void deleteObject(const std::string &key) = 0;
|
virtual void deleteObject(const std::string &key) = 0;
|
||||||
virtual int copyObject(const std::string &sourceKey, const std::string &destKey) = 0;
|
virtual int copyObject(const std::string &sourceKey, const std::string &destKey) = 0;
|
||||||
|
|||||||
@@ -36,9 +36,10 @@ inline boost::mutex & Downloader::getDownloadMutex()
|
|||||||
return download_mutex;
|
return download_mutex;
|
||||||
}
|
}
|
||||||
|
|
||||||
int Downloader::download(const vector<const string *> &keys, vector<int> *errnos)
|
int Downloader::download(const vector<const string *> &keys, vector<int> *errnos, vector<size_t> *sizes)
|
||||||
{
|
{
|
||||||
volatile uint counter = keys.size();
|
//volatile uint counter = keys.size();
|
||||||
|
uint counter = keys.size();
|
||||||
boost::condition condvar;
|
boost::condition condvar;
|
||||||
boost::mutex m;
|
boost::mutex m;
|
||||||
DownloadListener listener(&counter, &condvar, &m);
|
DownloadListener listener(&counter, &condvar, &m);
|
||||||
@@ -71,19 +72,27 @@ int Downloader::download(const vector<const string *> &keys, vector<int> *errnos
|
|||||||
(*iterators[i])->listeners.push_back(&listener);
|
(*iterators[i])->listeners.push_back(&listener);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
s.unlock();
|
|
||||||
|
|
||||||
// wait for the downloads to finish
|
// wait for the downloads to finish
|
||||||
boost::unique_lock<boost::mutex> dl_lock(m);
|
boost::unique_lock<boost::mutex> dl_lock(m);
|
||||||
|
s.unlock();
|
||||||
while (counter > 0)
|
while (counter > 0)
|
||||||
condvar.wait(dl_lock);
|
condvar.wait(dl_lock);
|
||||||
dl_lock.unlock();
|
dl_lock.unlock();
|
||||||
|
|
||||||
// remove the entries inserted by this call
|
// remove the entries inserted by this call
|
||||||
|
sizes->resize(keys.size());
|
||||||
s.lock();
|
s.lock();
|
||||||
for (i = 0; i < keys.size(); i++)
|
for (i = 0; i < keys.size(); i++)
|
||||||
|
{
|
||||||
if (inserted[i])
|
if (inserted[i])
|
||||||
|
{
|
||||||
|
(*sizes)[i] = (*iterators[i])->size;
|
||||||
downloads.erase(iterators[i]);
|
downloads.erase(iterators[i]);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
(*sizes)[i] = 0;
|
||||||
|
}
|
||||||
s.unlock();
|
s.unlock();
|
||||||
|
|
||||||
// check for errors & propagate
|
// check for errors & propagate
|
||||||
@@ -113,14 +122,14 @@ inline const string & Downloader::getDownloadPath() const
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* The helper fcns */
|
/* The helper fcns */
|
||||||
Downloader::Download::Download(const string *source, Downloader *dl) : key(source), dler(dl), dl_errno(0)
|
Downloader::Download::Download(const string *source, Downloader *dl) : key(source), dler(dl), dl_errno(0), size(0)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void Downloader::Download::operator()()
|
void Downloader::Download::operator()()
|
||||||
{
|
{
|
||||||
CloudStorage *storage = CloudStorage::get();
|
CloudStorage *storage = CloudStorage::get();
|
||||||
int err = storage->getObject(*key, dler->getDownloadPath() + "/" + *key);
|
int err = storage->getObject(*key, dler->getDownloadPath() + "/" + *key, &size);
|
||||||
if (err != 0)
|
if (err != 0)
|
||||||
dl_errno = errno;
|
dl_errno = errno;
|
||||||
|
|
||||||
@@ -129,7 +138,8 @@ void Downloader::Download::operator()()
|
|||||||
listener->downloadFinished();
|
listener->downloadFinished();
|
||||||
}
|
}
|
||||||
|
|
||||||
Downloader::DownloadListener::DownloadListener(volatile uint *counter, boost::condition *condvar, boost::mutex *m) : count(counter), cond(condvar), mutex(m)
|
//Downloader::DownloadListener::DownloadListener(volatile uint *counter, boost::condition *condvar, boost::mutex *m) : count(counter), cond(condvar), mutex(m)
|
||||||
|
Downloader::DownloadListener::DownloadListener(uint *counter, boost::condition *condvar, boost::mutex *m) : count(counter), cond(condvar), mutex(m)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ class Downloader
|
|||||||
|
|
||||||
// returns 0 on success. If != 0, errnos will contains the errno associated with the failure
|
// returns 0 on success. If != 0, errnos will contains the errno associated with the failure
|
||||||
// caller owns the memory for the strings.
|
// caller owns the memory for the strings.
|
||||||
int download(const std::vector<const std::string *> &keys, std::vector<int> *errnos);
|
int download(const std::vector<const std::string *> &keys, std::vector<int> *errnos, std::vector<size_t> *sizes);
|
||||||
void setDownloadPath(const std::string &path);
|
void setDownloadPath(const std::string &path);
|
||||||
const std::string & getDownloadPath() const;
|
const std::string & getDownloadPath() const;
|
||||||
|
|
||||||
@@ -35,10 +35,12 @@ class Downloader
|
|||||||
class DownloadListener
|
class DownloadListener
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
DownloadListener(volatile uint *counter, boost::condition *condvar, boost::mutex *m);
|
DownloadListener(uint *counter, boost::condition *condvar, boost::mutex *m);
|
||||||
|
//DownloadListener(volatile uint *counter, boost::condition *condvar, boost::mutex *m);
|
||||||
void downloadFinished();
|
void downloadFinished();
|
||||||
private:
|
private:
|
||||||
volatile uint *count;
|
uint *count;
|
||||||
|
//volatile uint *count;
|
||||||
boost::condition *cond;
|
boost::condition *cond;
|
||||||
boost::mutex *mutex;
|
boost::mutex *mutex;
|
||||||
};
|
};
|
||||||
@@ -50,6 +52,7 @@ class Downloader
|
|||||||
Downloader *dler;
|
Downloader *dler;
|
||||||
const std::string *key;
|
const std::string *key;
|
||||||
int dl_errno; // to propagate errors from the download job to the caller
|
int dl_errno; // to propagate errors from the download job to the caller
|
||||||
|
size_t size;
|
||||||
std::vector<DownloadListener *> listeners;
|
std::vector<DownloadListener *> listeners;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -43,7 +43,7 @@ int LocalStorage::copy(const path &source, const path &dest)
|
|||||||
{
|
{
|
||||||
boost::system::error_code err;
|
boost::system::error_code err;
|
||||||
copy_file(source, dest, copy_option::fail_if_exists, err);
|
copy_file(source, dest, copy_option::fail_if_exists, err);
|
||||||
if (!err)
|
if (err)
|
||||||
{
|
{
|
||||||
errno = err.value();
|
errno = err.value();
|
||||||
return -1;
|
return -1;
|
||||||
@@ -58,9 +58,14 @@ path operator+(const path &p1, const path &p2)
|
|||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int LocalStorage::getObject(const string &source, const string &dest)
|
int LocalStorage::getObject(const string &source, const string &dest, size_t *size)
|
||||||
{
|
{
|
||||||
return copy(prefix + source, dest);
|
int ret = copy(prefix + source, dest);
|
||||||
|
if (ret)
|
||||||
|
return ret;
|
||||||
|
if (size)
|
||||||
|
*size = boost::filesystem::file_size(dest);
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int LocalStorage::putObject(const string &source, const string &dest)
|
int LocalStorage::putObject(const string &source, const string &dest)
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ class LocalStorage : public CloudStorage
|
|||||||
LocalStorage();
|
LocalStorage();
|
||||||
virtual ~LocalStorage();
|
virtual ~LocalStorage();
|
||||||
|
|
||||||
int getObject(const std::string &sourceKey, const std::string &destFile);
|
int getObject(const std::string &sourceKey, const std::string &destFile, size_t *size = NULL);
|
||||||
int putObject(const std::string &sourceFile, const std::string &destKey);
|
int putObject(const std::string &sourceFile, const std::string &destKey);
|
||||||
void deleteObject(const std::string &key);
|
void deleteObject(const std::string &key);
|
||||||
int copyObject(const std::string &sourceKey, const std::string &destKey);
|
int copyObject(const std::string &sourceKey, const std::string &destKey);
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ S3Storage::~S3Storage()
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
int S3Storage::getObject(const string &sourceKey, const string &destFile)
|
int S3Storage::getObject(const string &sourceKey, const string &destFile, size_t *size)
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ class S3Storage : public CloudStorage
|
|||||||
S3Storage();
|
S3Storage();
|
||||||
virtual ~S3Storage();
|
virtual ~S3Storage();
|
||||||
|
|
||||||
int getObject(const std::string &sourceKey, const std::string &destFile);
|
int getObject(const std::string &sourceKey, const std::string &destFile, size_t *size = NULL);
|
||||||
int putObject(const std::string &sourceFile, const std::string &destKey);
|
int putObject(const std::string &sourceFile, const std::string &destKey);
|
||||||
void deleteObject(const std::string &key);
|
void deleteObject(const std::string &key);
|
||||||
int copyObject(const std::string &sourceKey, const std::string &destKey);
|
int copyObject(const std::string &sourceKey, const std::string &destKey);
|
||||||
|
|||||||
Reference in New Issue
Block a user