API: removed file size limitation

This commit is contained in:
SChernykh 2023-09-16 19:38:16 +02:00
parent a9d39f0803
commit 0b544bf55a
6 changed files with 105 additions and 14 deletions

View file

@ -38,9 +38,18 @@ struct Stream
enum params : int { BUF_SIZE = 1024 - 1 }; enum params : int { BUF_SIZE = 1024 - 1 };
template<size_t N> template<size_t N>
explicit FORCEINLINE Stream(char (&buf)[N]) : m_pos(0), m_numberWidth(1), m_buf(buf), m_bufSize(N - 1) {} explicit FORCEINLINE Stream(char (&buf)[N]) : m_pos(0), m_numberWidth(1), m_buf(buf), m_bufSize(N - 1), m_spilled(0) {}
FORCEINLINE Stream(void* buf, size_t size) : m_pos(0), m_numberWidth(1), m_buf(reinterpret_cast<char*>(buf)), m_bufSize(static_cast<int>(size) - 1) {} FORCEINLINE Stream(void* buf, size_t size) { reset(buf, size); }
FORCEINLINE void reset(void* buf, size_t size)
{
m_pos = 0;
m_numberWidth = 1;
m_buf = reinterpret_cast<char*>(buf);
m_bufSize = static_cast<int>(size) - 1;
m_spilled = 0;
}
template<typename T> template<typename T>
struct Entry struct Entry
@ -70,9 +79,7 @@ struct Stream
{ {
static_assert(1 < base && base <= 64, "Invalid base"); static_assert(1 < base && base <= 64, "Invalid base");
const T data_with_sign = data; const bool negative = is_negative(data);
data = abs(data);
const bool negative = (data != data_with_sign);
char buf[32]; char buf[32];
size_t k = sizeof(buf); size_t k = sizeof(buf);
@ -98,6 +105,7 @@ struct Stream
const int n = static_cast<int>(n0); const int n = static_cast<int>(n0);
const int pos = m_pos; const int pos = m_pos;
if (pos + n > m_bufSize) { if (pos + n > m_bufSize) {
m_spilled += n;
return; return;
} }
memcpy(m_buf + pos, buf, n); memcpy(m_buf + pos, buf, n);
@ -111,6 +119,7 @@ struct Stream
int m_numberWidth; int m_numberWidth;
char* m_buf; char* m_buf;
int m_bufSize; int m_bufSize;
int m_spilled;
}; };
struct Writer : public Stream struct Writer : public Stream

View file

@ -1348,10 +1348,6 @@ void P2PServer::api_update_local_stats()
<< static_cast<char*>(client->m_addrString) << static_cast<char*>(client->m_addrString)
<< '"'; << '"';
if (s.m_pos + 128 >= s.m_bufSize) {
break;
}
first = false; first = false;
} }
} }

View file

@ -106,9 +106,18 @@ void p2pool_api::on_stop()
void p2pool_api::dump_to_file_async_internal(Category category, const char* filename, Callback<void, log::Stream&>::Base&& callback) void p2pool_api::dump_to_file_async_internal(Category category, const char* filename, Callback<void, log::Stream&>::Base&& callback)
{ {
std::vector<char> buf(16384); std::vector<char> buf(1024);
log::Stream s(buf.data(), buf.size()); log::Stream s(buf.data(), buf.size());
callback(s); callback(s);
// If the buffer was too small, try again with big enough buffer
if (s.m_spilled) {
// Assume that the second call will use no more than 2X bytes
buf.resize((static_cast<ptrdiff_t>(s.m_pos) + s.m_spilled) * 2 + 1);
s.reset(buf.data(), buf.size());
callback(s);
}
buf.resize(s.m_pos); buf.resize(s.m_pos);
std::string path; std::string path;

View file

@ -91,11 +91,11 @@ static FORCEINLINE bool from_hex(char c, T& out_value) {
return false; return false;
} }
template<typename T, bool is_signed> struct abs_helper {}; template<typename T, bool is_signed> struct is_negative_helper {};
template<typename T> struct abs_helper<T, false> { static FORCEINLINE T value(T x) { return x; } }; template<typename T> struct is_negative_helper<T, false> { static FORCEINLINE bool value(T) { return false; } };
template<typename T> struct abs_helper<T, true> { static FORCEINLINE T value(T x) { return (x >= 0) ? x : -x; } }; template<typename T> struct is_negative_helper<T, true> { static FORCEINLINE bool value(T x) { return (x < 0); } };
template<typename T> FORCEINLINE T abs(T x) { return abs_helper<T, std::is_signed<T>::value>::value(x); } template<typename T> FORCEINLINE bool is_negative(T x) { return is_negative_helper<T, std::is_signed<T>::value>::value(x); }
template<typename T, typename U> template<typename T, typename U>
FORCEINLINE void writeVarint(T value, U&& callback) FORCEINLINE void writeVarint(T value, U&& callback)

View file

@ -33,6 +33,7 @@ set(SOURCES
src/difficulty_type_tests.cpp src/difficulty_type_tests.cpp
src/hash_tests.cpp src/hash_tests.cpp
src/keccak_tests.cpp src/keccak_tests.cpp
src/log_tests.cpp
src/main.cpp src/main.cpp
src/pool_block_tests.cpp src/pool_block_tests.cpp
src/util_tests.cpp src/util_tests.cpp

76
tests/src/log_tests.cpp Normal file
View file

@ -0,0 +1,76 @@
/*
* This file is part of the Monero P2Pool <https://github.com/SChernykh/p2pool>
* Copyright (c) 2021-2023 SChernykh <https://github.com/SChernykh>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, version 3.
*
* This program 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 General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include "common.h"
#include "gtest/gtest.h"
namespace p2pool {
TEST(log, stream)
{
constexpr int N = 63;
char buf[N + 1] = {};
log::Stream s(buf);
for (int iter = 0; iter < 2; ++iter) {
ASSERT_EQ(s.m_bufSize, N);
for (int i = 0; i < N; ++i) {
s << ' ';
ASSERT_EQ(s.m_pos, i + 1);
ASSERT_EQ(s.m_spilled, 0);
}
s << ' ';
ASSERT_EQ(s.m_pos, N);
ASSERT_EQ(s.m_spilled, 1);
for (int i = 0; i < N; ++i) {
ASSERT_EQ(buf[i], ' ');
}
ASSERT_EQ(buf[N], '\0');
s.reset(buf, N + 1);
}
}
TEST(log, pad_right)
{
constexpr int N = 63;
char buf[N + 1] = {};
log::Stream s(buf);
s << log::pad_right('1', N);
ASSERT_EQ(s.m_pos, N);
ASSERT_EQ(s.m_spilled, 0);
ASSERT_EQ(buf[0], '1');
for (int i = 1; i < N; ++i) {
ASSERT_EQ(buf[i], ' ');
}
ASSERT_EQ(buf[N], '\0');
}
}