[#74021] simplify file IO logic
This commit is contained in:
parent
2c677d90f7
commit
2499c71d12
|
|
@ -89,50 +89,26 @@ VerilatedSaifActivityBit& VerilatedSaifActivityVar::bit(const std::size_t index)
|
||||||
return m_bits[index];
|
return m_bits[index];
|
||||||
}
|
}
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//=============================================================================
|
|
||||||
//=============================================================================
|
|
||||||
// VerilatedSaifFile
|
|
||||||
|
|
||||||
bool VerilatedSaifFile::open(const std::string& name) VL_MT_UNSAFE {
|
|
||||||
m_fd = ::open(name.c_str(),
|
|
||||||
O_CREAT | O_WRONLY | O_TRUNC | O_LARGEFILE | O_NONBLOCK | O_CLOEXEC, 0666);
|
|
||||||
return m_fd >= 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
void VerilatedSaifFile::close() VL_MT_UNSAFE { ::close(m_fd); }
|
|
||||||
|
|
||||||
ssize_t VerilatedSaifFile::write(const char* bufp, ssize_t len) VL_MT_UNSAFE {
|
|
||||||
return ::write(m_fd, bufp, len);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
// Opening/Closing
|
// Opening/Closing
|
||||||
|
|
||||||
VerilatedSaif::VerilatedSaif(VerilatedSaifFile* filep) {
|
VerilatedSaif::VerilatedSaif(void* filep) {}
|
||||||
// Not in header to avoid link issue if header is included without this .cpp file
|
|
||||||
m_fileNewed = (filep == nullptr);
|
|
||||||
m_filep = m_fileNewed ? new VerilatedSaifFile : filep;
|
|
||||||
}
|
|
||||||
|
|
||||||
void VerilatedSaif::open(const char* filename) VL_MT_SAFE_EXCLUDES(m_mutex) {
|
void VerilatedSaif::open(const char* filename) VL_MT_SAFE_EXCLUDES(m_mutex) {
|
||||||
const VerilatedLockGuard lock{m_mutex};
|
const VerilatedLockGuard lock{m_mutex};
|
||||||
if (isOpen()) return;
|
if (isOpen()) return;
|
||||||
|
|
||||||
// Set member variables
|
|
||||||
m_filename = filename; // "" is ok, as someone may overload open
|
m_filename = filename; // "" is ok, as someone may overload open
|
||||||
|
m_filep = ::open(m_filename.c_str(), O_CREAT | O_WRONLY | O_TRUNC | O_LARGEFILE | O_NONBLOCK | O_CLOEXEC, 0666);
|
||||||
|
m_isOpen = true;
|
||||||
|
|
||||||
initializeSaifFileContents();
|
initializeSaifFileContents();
|
||||||
|
|
||||||
Super::traceInit();
|
Super::traceInit();
|
||||||
}
|
}
|
||||||
|
|
||||||
void VerilatedSaif::openNext(bool incFilename) VL_MT_SAFE_EXCLUDES(m_mutex) {
|
|
||||||
// noop, SAIF only needs one file per trace
|
|
||||||
}
|
|
||||||
|
|
||||||
void VerilatedSaif::initializeSaifFileContents() {
|
void VerilatedSaif::initializeSaifFileContents() {
|
||||||
printStr("// Generated by verilated_saif\n");
|
printStr("// Generated by verilated_saif\n");
|
||||||
printStr("(SAIFILE\n");
|
printStr("(SAIFILE\n");
|
||||||
|
|
@ -145,34 +121,9 @@ void VerilatedSaif::initializeSaifFileContents() {
|
||||||
printStr(")\n");
|
printStr(")\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
bool VerilatedSaif::preChangeDump() { return isOpen(); }
|
|
||||||
|
|
||||||
void VerilatedSaif::emitTimeChange(uint64_t timeui) { m_time = timeui; }
|
void VerilatedSaif::emitTimeChange(uint64_t timeui) { m_time = timeui; }
|
||||||
|
|
||||||
VerilatedSaif::~VerilatedSaif() {
|
VerilatedSaif::~VerilatedSaif() { close(); }
|
||||||
close();
|
|
||||||
if (m_filep && m_fileNewed) VL_DO_CLEAR(delete m_filep, m_filep = nullptr);
|
|
||||||
}
|
|
||||||
|
|
||||||
void VerilatedSaif::closePrev() {
|
|
||||||
// This function is on the flush() call path
|
|
||||||
if (!isOpen()) return;
|
|
||||||
|
|
||||||
Super::flushBase();
|
|
||||||
m_isOpen = false;
|
|
||||||
m_filep->close();
|
|
||||||
}
|
|
||||||
|
|
||||||
void VerilatedSaif::closeErr() {
|
|
||||||
// This function is on the flush() call path
|
|
||||||
// Close due to an error. We might abort before even getting here,
|
|
||||||
// depending on the definition of vl_fatal.
|
|
||||||
if (!isOpen()) return;
|
|
||||||
|
|
||||||
// No buffer flush, just fclose
|
|
||||||
m_isOpen = false;
|
|
||||||
m_filep->close(); // May get error, just ignore it
|
|
||||||
}
|
|
||||||
|
|
||||||
void VerilatedSaif::close() VL_MT_SAFE_EXCLUDES(m_mutex) {
|
void VerilatedSaif::close() VL_MT_SAFE_EXCLUDES(m_mutex) {
|
||||||
// This function is on the flush() call path
|
// This function is on the flush() call path
|
||||||
|
|
@ -182,9 +133,9 @@ void VerilatedSaif::close() VL_MT_SAFE_EXCLUDES(m_mutex) {
|
||||||
finalizeSaifFileContents();
|
finalizeSaifFileContents();
|
||||||
clearCurrentlyCollectedData();
|
clearCurrentlyCollectedData();
|
||||||
|
|
||||||
closePrev();
|
::close(m_filep);
|
||||||
// closePrev() called Super::flush(), so we just
|
m_isOpen = false;
|
||||||
// need to shut down the tracing thread here.
|
|
||||||
Super::closeBase();
|
Super::closeBase();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -298,9 +249,9 @@ void VerilatedSaif::clearCurrentlyCollectedData() {
|
||||||
m_activityArena.clear();
|
m_activityArena.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
void VerilatedSaif::printStr(const char* str) { m_filep->write(str, strlen(str)); }
|
void VerilatedSaif::printStr(const char* str) { ::write(m_filep, str, strlen(str)); }
|
||||||
|
|
||||||
void VerilatedSaif::printStr(const std::string& str) { m_filep->write(str.c_str(), str.size()); }
|
void VerilatedSaif::printStr(const std::string& str) { ::write(m_filep, str.c_str(), str.size()); }
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
// Definitions
|
// Definitions
|
||||||
|
|
|
||||||
|
|
@ -161,8 +161,7 @@ private:
|
||||||
//=========================================================================
|
//=========================================================================
|
||||||
// SAIF-specific internals
|
// SAIF-specific internals
|
||||||
|
|
||||||
VerilatedSaifFile* m_filep; // File we're writing to
|
int m_filep = 0; // File we're writing to
|
||||||
bool m_fileNewed; // m_filep needs destruction
|
|
||||||
bool m_isOpen = false; // True indicates open file
|
bool m_isOpen = false; // True indicates open file
|
||||||
std::string m_filename; // Filename we're writing to (if open)
|
std::string m_filename; // Filename we're writing to (if open)
|
||||||
|
|
||||||
|
|
@ -205,8 +204,6 @@ private:
|
||||||
|
|
||||||
void clearCurrentlyCollectedData();
|
void clearCurrentlyCollectedData();
|
||||||
|
|
||||||
void closePrev();
|
|
||||||
void closeErr();
|
|
||||||
void declare(uint32_t code, const char* name, const char* wirep, bool array, int arraynum,
|
void declare(uint32_t code, const char* name, const char* wirep, bool array, int arraynum,
|
||||||
bool bussed, int msb, int lsb);
|
bool bussed, int msb, int lsb);
|
||||||
|
|
||||||
|
|
@ -222,7 +219,7 @@ protected:
|
||||||
|
|
||||||
// Hooks called from VerilatedTrace
|
// Hooks called from VerilatedTrace
|
||||||
bool preFullDump() override { return isOpen(); }
|
bool preFullDump() override { return isOpen(); }
|
||||||
bool preChangeDump() override;
|
bool preChangeDump() override { return isOpen(); }
|
||||||
|
|
||||||
// Trace buffer management
|
// Trace buffer management
|
||||||
Buffer* getTraceBuffer(uint32_t fidx) override;
|
Buffer* getTraceBuffer(uint32_t fidx) override;
|
||||||
|
|
@ -236,7 +233,7 @@ public:
|
||||||
// External interface to client code
|
// External interface to client code
|
||||||
|
|
||||||
// CONSTRUCTOR
|
// CONSTRUCTOR
|
||||||
explicit VerilatedSaif(VerilatedSaifFile* filep = nullptr);
|
explicit VerilatedSaif(void* filep = nullptr);
|
||||||
~VerilatedSaif();
|
~VerilatedSaif();
|
||||||
|
|
||||||
// ACCESSORS
|
// ACCESSORS
|
||||||
|
|
@ -247,8 +244,6 @@ public:
|
||||||
// METHODS - All must be thread safe
|
// METHODS - All must be thread safe
|
||||||
// Open the file; call isOpen() to see if errors
|
// Open the file; call isOpen() to see if errors
|
||||||
void open(const char* filename) VL_MT_SAFE_EXCLUDES(m_mutex);
|
void open(const char* filename) VL_MT_SAFE_EXCLUDES(m_mutex);
|
||||||
// Open next data-only file
|
|
||||||
void openNext(bool incFilename) VL_MT_SAFE_EXCLUDES(m_mutex);
|
|
||||||
// Close the file
|
// Close the file
|
||||||
void close() VL_MT_SAFE_EXCLUDES(m_mutex);
|
void close() VL_MT_SAFE_EXCLUDES(m_mutex);
|
||||||
// Flush any remaining data to this file
|
// Flush any remaining data to this file
|
||||||
|
|
@ -329,28 +324,6 @@ class VerilatedSaifBuffer VL_NOT_FINAL {
|
||||||
VL_ATTR_ALWINLINE void emitDouble(uint32_t code, double newval);
|
VL_ATTR_ALWINLINE void emitDouble(uint32_t code, double newval);
|
||||||
};
|
};
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
// VerilatedFile
|
|
||||||
/// Class representing a file to write to. These virtual methods can be
|
|
||||||
/// overrode for e.g. socket I/O.
|
|
||||||
|
|
||||||
class VerilatedSaifFile VL_NOT_FINAL {
|
|
||||||
private:
|
|
||||||
int m_fd = 0; // File descriptor we're writing to
|
|
||||||
public:
|
|
||||||
// METHODS
|
|
||||||
/// Construct a (as yet) closed file
|
|
||||||
VerilatedSaifFile() = default;
|
|
||||||
/// Close and destruct
|
|
||||||
virtual ~VerilatedSaifFile() = default;
|
|
||||||
/// Open a file with given filename
|
|
||||||
virtual bool open(const std::string& name) VL_MT_UNSAFE;
|
|
||||||
/// Close object's file
|
|
||||||
virtual void close() VL_MT_UNSAFE;
|
|
||||||
/// Write data to file (if it is open)
|
|
||||||
virtual ssize_t write(const char* bufp, ssize_t len) VL_MT_UNSAFE;
|
|
||||||
};
|
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
// VerilatedSaifC
|
// VerilatedSaifC
|
||||||
/// Class representing a SAIF dump file in C standalone (no SystemC)
|
/// Class representing a SAIF dump file in C standalone (no SystemC)
|
||||||
|
|
@ -363,8 +336,8 @@ class VerilatedSaifC VL_NOT_FINAL : public VerilatedTraceBaseC {
|
||||||
VL_UNCOPYABLE(VerilatedSaifC);
|
VL_UNCOPYABLE(VerilatedSaifC);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
/// Construct the dump. Optional argument is a preconstructed file.
|
/// Construct the dump. Optional argument is ignored
|
||||||
explicit VerilatedSaifC(VerilatedSaifFile* filep = nullptr)
|
explicit VerilatedSaifC(void* filep = nullptr)
|
||||||
: m_sptrace{filep} {}
|
: m_sptrace{filep} {}
|
||||||
/// Destruct, flush, and close the dump
|
/// Destruct, flush, and close the dump
|
||||||
virtual ~VerilatedSaifC() { close(); }
|
virtual ~VerilatedSaifC() { close(); }
|
||||||
|
|
@ -377,13 +350,8 @@ public:
|
||||||
/// This includes a complete header dump each time it is called,
|
/// This includes a complete header dump each time it is called,
|
||||||
/// just as if this object was deleted and reconstructed.
|
/// just as if this object was deleted and reconstructed.
|
||||||
virtual void open(const char* filename) VL_MT_SAFE { m_sptrace.open(filename); }
|
virtual void open(const char* filename) VL_MT_SAFE { m_sptrace.open(filename); }
|
||||||
/// Continue a SAIF dump by rotating to a new file name
|
|
||||||
/// The header is only in the first file created, this allows
|
|
||||||
/// "cat" to be used to combine the header plus any number of data files.
|
|
||||||
void openNext(bool incFilename = true) VL_MT_SAFE { m_sptrace.openNext(incFilename); }
|
|
||||||
|
|
||||||
void rolloverSize(size_t size) VL_MT_SAFE { /* noop */
|
void rolloverSize(size_t size) VL_MT_SAFE { /* noop */ }
|
||||||
}
|
|
||||||
|
|
||||||
/// Close dump
|
/// Close dump
|
||||||
void close() VL_MT_SAFE {
|
void close() VL_MT_SAFE {
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue