diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-28 07:24:57 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-28 07:24:57 +0000 |
commit | 070852d8604cece0c31f28ff3eb8d21d9ba415fb (patch) | |
tree | 9097175a6a5b8b7e37af9a96269ac0b61a0189cd /decoder/include/mem_acc | |
parent | Initial commit. (diff) | |
download | libopencsd-070852d8604cece0c31f28ff3eb8d21d9ba415fb.tar.xz libopencsd-070852d8604cece0c31f28ff3eb8d21d9ba415fb.zip |
Adding upstream version 1.3.3.upstream/1.3.3upstream
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'decoder/include/mem_acc')
-rw-r--r-- | decoder/include/mem_acc/trc_mem_acc.h | 47 | ||||
-rw-r--r-- | decoder/include/mem_acc/trc_mem_acc_base.h | 245 | ||||
-rw-r--r-- | decoder/include/mem_acc/trc_mem_acc_bufptr.h | 75 | ||||
-rw-r--r-- | decoder/include/mem_acc/trc_mem_acc_cache.h | 149 | ||||
-rw-r--r-- | decoder/include/mem_acc/trc_mem_acc_cb.h | 96 | ||||
-rw-r--r-- | decoder/include/mem_acc/trc_mem_acc_cb_if.h | 71 | ||||
-rw-r--r-- | decoder/include/mem_acc/trc_mem_acc_file.h | 234 | ||||
-rw-r--r-- | decoder/include/mem_acc/trc_mem_acc_mapper.h | 133 |
8 files changed, 1050 insertions, 0 deletions
diff --git a/decoder/include/mem_acc/trc_mem_acc.h b/decoder/include/mem_acc/trc_mem_acc.h new file mode 100644 index 0000000..66f9122 --- /dev/null +++ b/decoder/include/mem_acc/trc_mem_acc.h @@ -0,0 +1,47 @@ +/* + * \file trc_mem_acc.h + * \brief OpenCSD : + * + * \copyright Copyright (c) 2015, ARM Limited. All Rights Reserved. + */ + +/* + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef ARM_TRC_MEM_ACC_H_INCLUDED +#define ARM_TRC_MEM_ACC_H_INCLUDED + +#include "trc_mem_acc_base.h" +#include "trc_mem_acc_bufptr.h" +#include "trc_mem_acc_file.h" +#include "trc_mem_acc_mapper.h" +#include "trc_mem_acc_cb.h" + + +#endif // ARM_TRC_MEM_ACC_H_INCLUDED + +/* End of File trc_mem_acc.h */ diff --git a/decoder/include/mem_acc/trc_mem_acc_base.h b/decoder/include/mem_acc/trc_mem_acc_base.h new file mode 100644 index 0000000..7f17bde --- /dev/null +++ b/decoder/include/mem_acc/trc_mem_acc_base.h @@ -0,0 +1,245 @@ +/*! + * \file trc_mem_acc_base.h + * \brief OpenCSD : Memory accessor base class. + * + * \copyright Copyright (c) 2015, ARM Limited. All Rights Reserved. + */ + +/* + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef ARM_TRC_MEM_ACC_BASE_H_INCLUDED +#define ARM_TRC_MEM_ACC_BASE_H_INCLUDED + +#include "opencsd/ocsd_if_types.h" +#include <string> + +/*! + * @class TrcMemAccessorBase + * @brief Memory range to access by trace decoder. + * + * Represents a memory access range for the trace decoder. + * Range inclusive from m_startAddress to m_endAddress. + * e.g. a 1k range from 0x1000 has start of 0x1000 and end of 0x13FF + * + * Derived classes provide specific access types such as binary files and memory buffers. + * + */ +class TrcMemAccessorBase +{ +public: + + /** Describes the storage type of the underlying memory accessor */ + enum MemAccTypes { + MEMACC_UNKNOWN, + MEMACC_FILE, //<! Binary data file accessor + MEMACC_BUFPTR, //<! memory buffer accessor + MEMACC_CB_IF, //<! callback interface accessor - use for live memory access + }; + + /** default constructor */ + TrcMemAccessorBase(MemAccTypes type); + + /** costruct with address range values */ + TrcMemAccessorBase(MemAccTypes type, ocsd_vaddr_t startAddr, ocsd_vaddr_t endAddr); + + /** default desctructor */ + virtual ~TrcMemAccessorBase() {}; + + /*! + * Set the inclusive address range of this accessor. + * + * @param startAddr : start address of the range. + * @param endAddr : end address of the range. + */ + void setRange(ocsd_vaddr_t startAddr, ocsd_vaddr_t endAddr); + + /*! + * test if an address is in the inclusive range for this accessor + * + * @param s_address : Address to test. + * + * @return const bool : true if the address is in range. + */ + virtual const bool addrInRange(const ocsd_vaddr_t s_address) const; + + + /*! + * test if an address is the start of range for this accessor + * + * @param s_address : Address to test. + * + * @return const bool : true if the address is start of range. + */ + virtual const bool addrStartOfRange(const ocsd_vaddr_t s_address) const; + + /*! + * Test number of bytes available from the start address, up to the number of requested bytes. + * Tests if all the requested bytes are available from the supplied start address. + * Returns the number available up to full requested amount. + * + * @param s_address : Start address within the range. + * @param reqBytes : Number of bytes needed from the start address. + * + * @return const uint32_t : Bytes available, up to reqBytes. 0 is s_address not in range. + */ + virtual const uint32_t bytesInRange(const ocsd_vaddr_t s_address, const uint32_t reqBytes) const; + + /*! + * test is supplied range accessor overlaps this range. + * + * @param *p_test_acc : Accessor to test for overlap. + * + * @return bool : true if overlap, false if not. + */ + virtual const bool overLapRange(const TrcMemAccessorBase *p_test_acc) const; + + /*! + * Read bytes from via the accessor from the memory range. + * + * @param s_address : Start address of the read. + * @param memSpace : memory space for this access. + * @param trcID : Trace ID of trace source. + * @param reqBytes : Number of bytes required. + * @param *byteBuffer : Buffer to copy the bytes into. + * + * @return uint32_t : Number of bytes read, 0 if s_address out of range, or mem space not accessible. + */ + virtual const uint32_t readBytes(const ocsd_vaddr_t s_address, const ocsd_mem_space_acc_t memSpace, const uint8_t trcID, const uint32_t reqBytes, uint8_t *byteBuffer) = 0; + + /*! + * Validate the address range - ensure addresses aligned, different, st < en etc. + * + * @return bool : true if valid range. + */ + virtual const bool validateRange(); + + + const enum MemAccTypes getType() const { return m_type; }; + + /* handle memory spaces */ + void setMemSpace(ocsd_mem_space_acc_t memSpace) { m_mem_space = memSpace; }; + const ocsd_mem_space_acc_t getMemSpace() const { return m_mem_space; }; + const bool inMemSpace(const ocsd_mem_space_acc_t mem_space) const { return (bool)(((uint8_t)m_mem_space & (uint8_t)mem_space) != 0); }; + + /* memory access info logging */ + virtual void getMemAccString(std::string &accStr) const; + +protected: + ocsd_vaddr_t m_startAddress; /**< accessible range start address */ + ocsd_vaddr_t m_endAddress; /**< accessible range end address */ + const MemAccTypes m_type; /**< memory accessor type */ + ocsd_mem_space_acc_t m_mem_space; +}; + +inline TrcMemAccessorBase::TrcMemAccessorBase(MemAccTypes accType, ocsd_vaddr_t startAddr, ocsd_vaddr_t endAddr) : + m_startAddress(startAddr), + m_endAddress(endAddr), + m_type(accType), + m_mem_space(OCSD_MEM_SPACE_ANY) +{ +} + +inline TrcMemAccessorBase::TrcMemAccessorBase(MemAccTypes accType) : + m_startAddress(0), + m_endAddress(0), + m_type(accType), + m_mem_space(OCSD_MEM_SPACE_ANY) +{ +} + +inline void TrcMemAccessorBase::setRange(ocsd_vaddr_t startAddr, ocsd_vaddr_t endAddr) +{ + m_startAddress = startAddr; + m_endAddress = endAddr; +} + +inline const bool TrcMemAccessorBase::addrInRange(const ocsd_vaddr_t s_address) const +{ + return (s_address >= m_startAddress) && (s_address <= m_endAddress); +} + +inline const bool TrcMemAccessorBase::addrStartOfRange(const ocsd_vaddr_t s_address) const +{ + return (s_address == m_startAddress); +} + + +inline const uint32_t TrcMemAccessorBase::bytesInRange(const ocsd_vaddr_t s_address, const uint32_t reqBytes) const +{ + ocsd_vaddr_t bytesInRange = 0; + if(addrInRange(s_address)) // start not in range, return 0. + { + // bytes available till end address. + bytesInRange = m_endAddress - s_address + 1; + if(bytesInRange > reqBytes) + bytesInRange = reqBytes; + } + return (uint32_t)bytesInRange; +} + +inline const bool TrcMemAccessorBase::overLapRange(const TrcMemAccessorBase *p_test_acc) const +{ + if( addrInRange(p_test_acc->m_startAddress) || + addrInRange(p_test_acc->m_endAddress) + ) + return true; + return false; +} + +inline const bool TrcMemAccessorBase::validateRange() +{ + if(m_startAddress & 0x1) // at least hword aligned for thumb + return false; + if((m_endAddress + 1) & 0x1) + return false; + if(m_startAddress == m_endAddress) // zero length range. + return false; + if(m_startAddress > m_endAddress) // values bakcwards / invalid + return false; + return true; +} + + +class TrcMemAccFactory +{ +public: + /** Accessor Creation */ + static ocsd_err_t CreateBufferAccessor(TrcMemAccessorBase **pAccessor, const ocsd_vaddr_t s_address, const uint8_t *p_buffer, const uint32_t size); + static ocsd_err_t CreateFileAccessor(TrcMemAccessorBase **pAccessor, const std::string &pathToFile, ocsd_vaddr_t startAddr, size_t offset = 0, size_t size = 0); + static ocsd_err_t CreateCBAccessor(TrcMemAccessorBase **pAccessor, const ocsd_vaddr_t s_address, const ocsd_vaddr_t e_address, const ocsd_mem_space_acc_t mem_space); + + /** Accessor Destruction */ + static void DestroyAccessor(TrcMemAccessorBase *pAccessor); +private: + TrcMemAccFactory() {}; + ~TrcMemAccFactory() {}; +}; + +#endif // ARM_TRC_MEM_ACC_BASE_H_INCLUDED + +/* End of File trc_mem_acc_base.h */ diff --git a/decoder/include/mem_acc/trc_mem_acc_bufptr.h b/decoder/include/mem_acc/trc_mem_acc_bufptr.h new file mode 100644 index 0000000..b6208a7 --- /dev/null +++ b/decoder/include/mem_acc/trc_mem_acc_bufptr.h @@ -0,0 +1,75 @@ +/* + * \file trc_mem_acc_bufptr.h + * \brief OpenCSD : + * + * \copyright Copyright (c) 2015, ARM Limited. All Rights Reserved. + */ + +/* + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef ARM_TRC_MEM_ACC_BUFPTR_H_INCLUDED +#define ARM_TRC_MEM_ACC_BUFPTR_H_INCLUDED + +#include "mem_acc/trc_mem_acc_base.h" + +/*! + * @class TrcMemAccBufPtr: + * @brief Trace memory accessor for a memory buffer. + * + * Wraps a memory buffer in an memory range accessor object. + * Takes a copy of the buffer pointer which must remain valid + * for the lifetime of the object. + * + */ +class TrcMemAccBufPtr: public TrcMemAccessorBase +{ +public: + /*! + * Construct the accessor. + * uses the start address as the start of range and calculates the end address + * according to the buffer size + * + * @param s_address : Start address in memory map represented by the data in the buffer. + * @param *p_buffer : pointer to a buffer of binary data. + * @param size : size of the buffer. + * + */ + TrcMemAccBufPtr(const ocsd_vaddr_t s_address, const uint8_t *p_buffer, const uint32_t size); + + virtual ~TrcMemAccBufPtr() {}; /**< default destructor */ + + /** Memory access override - allow decoder to read bytes from the buffer. */ + virtual const uint32_t readBytes(const ocsd_vaddr_t address, const ocsd_mem_space_acc_t memSpace, const uint8_t trcID, const uint32_t reqBytes, uint8_t *byteBuffer); + +private: + const uint8_t *m_p_buffer; /**< pointer to the memory buffer */ +}; + +#endif // ARM_TRC_MEM_ACC_BUFPTR_H_INCLUDED + +/* End of File trc_mem_acc_bufptr.h */ diff --git a/decoder/include/mem_acc/trc_mem_acc_cache.h b/decoder/include/mem_acc/trc_mem_acc_cache.h new file mode 100644 index 0000000..5e81c2a --- /dev/null +++ b/decoder/include/mem_acc/trc_mem_acc_cache.h @@ -0,0 +1,149 @@ +/*! +* \file trc_mem_acc_cache.h +* \brief OpenCSD : Memory accessor cache. +* +* \copyright Copyright (c) 2018, ARM Limited. All Rights Reserved. +*/ + +/* +* Redistribution and use in source and binary forms, with or without modification, +* are permitted provided that the following conditions are met: +* +* 1. Redistributions of source code must retain the above copyright notice, +* this list of conditions and the following disclaimer. +* +* 2. Redistributions in binary form must reproduce the above copyright notice, +* this list of conditions and the following disclaimer in the documentation +* and/or other materials provided with the distribution. +* +* 3. Neither the name of the copyright holder nor the names of its contributors +* may be used to endorse or promote products derived from this software without +* specific prior written permission. +* +* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND +* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +* IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, +* INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + +#ifndef ARM_TRC_MEM_ACC_CACHE_H_INCLUDED +#define ARM_TRC_MEM_ACC_CACHE_H_INCLUDED + +#include <string> +#include "opencsd/ocsd_if_types.h" + +#define MEM_ACC_CACHE_PAGE_SIZE 256 +#define MEM_ACC_CACHE_MRU_SIZE 12 + +class TrcMemAccessorBase; +class ITraceErrorLog; + +typedef struct cache_block { + ocsd_vaddr_t st_addr; + uint32_t valid_len; + uint8_t data[MEM_ACC_CACHE_PAGE_SIZE]; +} cache_block_t; + +// enable define to collect stats for debugging / cache performance tests +//#define LOG_CACHE_STATS + + +/** class TrcMemAccCache - cache small amounts of data from accessors to speed up decode. */ +class TrcMemAccCache +{ +public: + TrcMemAccCache(); + ~TrcMemAccCache() {}; + + void enableCaching(bool bEnable) { m_bCacheEnabled = bEnable; }; + void invalidateAll(); + const bool enabled() const { return m_bCacheEnabled; }; + const bool enabled_for_size(const uint32_t reqSize) const + { + return (m_bCacheEnabled && (reqSize <= MEM_ACC_CACHE_PAGE_SIZE)); + } + + + /** read bytes from cache if possible - load new page if needed, bail out if data not available */ + ocsd_err_t readBytesFromCache(TrcMemAccessorBase *p_accessor, const ocsd_vaddr_t address, const ocsd_mem_space_acc_t mem_space, const uint8_t trcID, uint32_t *numBytes, uint8_t *byteBuffer); + + void setErrorLog(ITraceErrorLog *log); + void logAndClearCounts(); + +private: + bool blockInCache(const ocsd_vaddr_t address, const uint32_t reqBytes); // run through each page to look for data. + bool blockInPage(const ocsd_vaddr_t address, const uint32_t reqBytes); + void logMsg(const std::string &szMsg); + + cache_block_t m_mru[MEM_ACC_CACHE_MRU_SIZE]; + int m_mru_idx = 0; // in use index + int m_mru_next_new = 0; // next new page at this index. + bool m_bCacheEnabled = false; + +#ifdef LOG_CACHE_STATS + uint32_t m_hits = 0; + uint32_t m_misses = 0; + uint32_t m_pages = 0; + uint32_t m_hit_rl[MEM_ACC_CACHE_MRU_SIZE]; + uint32_t m_hit_rl_max[MEM_ACC_CACHE_MRU_SIZE]; +#endif + + ITraceErrorLog *m_err_log = 0; +}; + +inline TrcMemAccCache::TrcMemAccCache() +{ + for (int i = 0; i < MEM_ACC_CACHE_MRU_SIZE; i++) + { + m_mru[i].st_addr = 0; + m_mru[i].valid_len = 0; +#ifdef LOG_CACHE_STATS + m_hit_rl[i] = 0; + m_hit_rl_max[i] = 0; +#endif + } +} + +inline bool TrcMemAccCache::blockInPage(const ocsd_vaddr_t address, const uint32_t reqBytes) +{ + if ((m_mru[m_mru_idx].st_addr <= address) && + m_mru[m_mru_idx].st_addr + m_mru[m_mru_idx].valid_len >= (address + reqBytes)) + return true; + return false; +} + +inline bool TrcMemAccCache::blockInCache(const ocsd_vaddr_t address, const uint32_t reqBytes) +{ + int tests = MEM_ACC_CACHE_MRU_SIZE; + while (tests) + { + if (blockInPage(address, reqBytes)) + return true; // found address in page + tests--; + m_mru_idx++; + if (m_mru_idx == MEM_ACC_CACHE_MRU_SIZE) + m_mru_idx = 0; + } + return false; +} + +inline void TrcMemAccCache::invalidateAll() +{ + for (int i = 0; i < MEM_ACC_CACHE_MRU_SIZE; i++) + { + m_mru[i].valid_len = 0; + m_mru[i].st_addr = 0; + } + m_mru_idx = 0; + m_mru_next_new = 0; +} + +#endif // ARM_TRC_MEM_ACC_CACHE_H_INCLUDED + +/* End of File trc_mem_acc_cache.h */ diff --git a/decoder/include/mem_acc/trc_mem_acc_cb.h b/decoder/include/mem_acc/trc_mem_acc_cb.h new file mode 100644 index 0000000..e58c616 --- /dev/null +++ b/decoder/include/mem_acc/trc_mem_acc_cb.h @@ -0,0 +1,96 @@ +/*! + * \file trc_mem_acc_cb.h + * \brief OpenCSD : Callback trace memory accessor. + * + * \copyright Copyright (c) 2015, ARM Limited. All Rights Reserved. + */ + +/* + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef ARM_TRC_MEM_ACC_CB_H_INCLUDED +#define ARM_TRC_MEM_ACC_CB_H_INCLUDED + +#include "mem_acc/trc_mem_acc_base.h" +#include "mem_acc/trc_mem_acc_cb_if.h" + +class TrcMemAccCB : public TrcMemAccessorBase +{ +public: + TrcMemAccCB(const ocsd_vaddr_t s_address, + const ocsd_vaddr_t e_address, + const ocsd_mem_space_acc_t mem_space); + + + virtual ~TrcMemAccCB() {}; + + /** Memory access override - allow decoder to read bytes from the buffer. */ + virtual const uint32_t readBytes(const ocsd_vaddr_t address, const ocsd_mem_space_acc_t memSpace, const uint8_t trcID, const uint32_t reqBytes, uint8_t *byteBuffer); + + void setCBIfClass(TrcMemAccCBIF *p_if); + void setCBIfFn(Fn_MemAcc_CB p_fn, const void *p_context); + void setCBIDIfFn(Fn_MemAccID_CB p_fn, const void *p_context); + +private: + void clearCBptrs(); + TrcMemAccCBIF *m_p_CBclass; //<! callback class. + Fn_MemAcc_CB m_p_CBfn; //<! callback function. + Fn_MemAccID_CB m_p_CBIDfn; //<! callback with ID function. + const void *m_p_cbfn_context; //<! context pointer for callback function. +}; + +inline void TrcMemAccCB::clearCBptrs() +{ + m_p_CBclass = 0; + m_p_CBfn = 0; + m_p_CBIDfn = 0; + m_p_cbfn_context = 0; +} + +inline void TrcMemAccCB::setCBIfClass(TrcMemAccCBIF *p_if) +{ + clearCBptrs(); // only one callback type per accessor. + m_p_CBclass = p_if; +} + +inline void TrcMemAccCB::setCBIfFn(Fn_MemAcc_CB p_fn, const void *p_context) +{ + clearCBptrs(); // only one callback type per accessor. + m_p_CBfn = p_fn; + m_p_cbfn_context = p_context; +} + +inline void TrcMemAccCB::setCBIDIfFn(Fn_MemAccID_CB p_fn, const void *p_context) +{ + clearCBptrs(); // only one callback type per accessor. + m_p_CBIDfn = p_fn; + m_p_cbfn_context = p_context; +} + +#endif // ARM_TRC_MEM_ACC_CB_H_INCLUDED + +/* End of File trc_mem_acc_cb.h */ diff --git a/decoder/include/mem_acc/trc_mem_acc_cb_if.h b/decoder/include/mem_acc/trc_mem_acc_cb_if.h new file mode 100644 index 0000000..54dc184 --- /dev/null +++ b/decoder/include/mem_acc/trc_mem_acc_cb_if.h @@ -0,0 +1,71 @@ +/*! + * \file trc_mem_acc_cb_if.h + * \brief OpenCSD : Memory Accessor Callback Direct Interface + * + * \copyright Copyright (c) 2015, ARM Limited. All Rights Reserved. + */ + +/* + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef ARM_TRC_MEM_ACC_CB_IF_H_INCLUDED +#define ARM_TRC_MEM_ACC_CB_IF_H_INCLUDED + +#include "opencsd/ocsd_if_types.h" + +/*! + * @class TrcMemAccCBIF + * @brief Interface class to implement memory accessor callbacks + * + * Implement an object with this interface to use in a memory accessor callback type. + * Callback accesses the memory according to address and memory space. + * Use for trace decode memory access on live systems, or where the implemented accessor types + * are not suitable for the memory data being accessed. + * + */ +class TrcMemAccCBIF +{ +public: + TrcMemAccCBIF() {}; + virtual ~TrcMemAccCBIF() {}; + + /*! + * Read bytes from via the accessor from the memory range. + * + * @param s_address : Start address of the read. + * @param memSpace : memory space for this access. + * @param reqBytes : Number of bytes required. + * @param *byteBuffer : Buffer to copy the bytes into. + * + * @return uint32_t : Number of bytes read, 0 if s_address out of range, or mem space not accessible. + */ + virtual const uint32_t readBytes(const ocsd_vaddr_t s_address, const ocsd_mem_space_acc_t memSpace, const uint32_t reqBytes, uint8_t *byteBuffer) = 0; +}; + +#endif // ARM_TRC_MEM_ACC_CB_IF_H_INCLUDED + +/* End of File trc_mem_acc_cb_if.h */ diff --git a/decoder/include/mem_acc/trc_mem_acc_file.h b/decoder/include/mem_acc/trc_mem_acc_file.h new file mode 100644 index 0000000..6c9b537 --- /dev/null +++ b/decoder/include/mem_acc/trc_mem_acc_file.h @@ -0,0 +1,234 @@ +/* + * \file trc_mem_acc_file.h + * \brief OpenCSD : Access binary target memory file + * + * \copyright Copyright (c) 2015, ARM Limited. All Rights Reserved. + */ + +/* + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef ARM_TRC_MEM_ACC_FILE_H_INCLUDED +#define ARM_TRC_MEM_ACC_FILE_H_INCLUDED + +#include <map> +#include <string> +#include <fstream> +#include <list> + +#include "opencsd/ocsd_if_types.h" +#include "mem_acc/trc_mem_acc_base.h" + +// an add-on region to a file - allows setting of a region at a none-zero offset for a file. +class FileRegionMemAccessor : public TrcMemAccessorBase +{ +public: + FileRegionMemAccessor() : TrcMemAccessorBase(MEMACC_FILE) {}; + virtual ~FileRegionMemAccessor() {}; + + void setOffset(const size_t offset) { m_file_offset = offset; }; + const size_t getOffset() const { return m_file_offset; }; + + bool operator<(const FileRegionMemAccessor& rhs) { return this->m_startAddress < rhs.m_startAddress; }; + + // not going to use these objects to read bytes - defer to the file class for that. + virtual const uint32_t readBytes(const ocsd_vaddr_t s_address, const ocsd_mem_space_acc_t memSpace, const uint8_t trcID, const uint32_t reqBytes, uint8_t *byteBuffer) { return 0; }; + + const ocsd_vaddr_t regionStartAddress() const { return m_startAddress; }; + +private: + size_t m_file_offset; +}; + +/*! + * @class TrcMemAccessorFile + * @brief Memory accessor for a binary file. + * + * Memory accessor based on a binary file snapshot of some memory. + * + * Static creation code to allow reference counted accessor usable for + * multiple access maps attached to multiple source trees for the same system. + */ +class TrcMemAccessorFile : public TrcMemAccessorBase +{ +public: + /** read bytes override - reads from file */ + virtual const uint32_t readBytes(const ocsd_vaddr_t address, const ocsd_mem_space_acc_t memSpace, const uint8_t trcID, const uint32_t reqBytes, uint8_t *byteBuffer); + +protected: + TrcMemAccessorFile(); /**< protected default constructor */ + virtual ~ TrcMemAccessorFile(); /**< protected default destructor */ + + /** increment reference counter */ + void IncRefCount() { m_ref_count++; }; + + /** decrement reference counter */ + void DecRefCount() { m_ref_count--; }; + + /** get current reference count */ + const int getRefCount() const { return m_ref_count; }; + + /*! + * Initialise accessor with file name and path, and start address. + * File opened and length calculated to determine end address for the range. + * + * @param &pathToFile : Binary file path and name + * @param startAddr : system memory address associated with start of binary datain file. + * + * @return bool : true if set up successfully, false if file could not be opened. + */ + ocsd_err_t initAccessor(const std::string &pathToFile, ocsd_vaddr_t startAddr, size_t offset, size_t size); + + /** get the file path */ + const std::string &getFilePath() const { return m_file_path; }; + + /** get an offset region if extant for the address */ + FileRegionMemAccessor *getRegionForAddress(const ocsd_vaddr_t startAddr) const; + + /* validate ranges */ + virtual const bool validateRange(); + +public: + + /*! + * File may contain multiple none-overlapping ranges in a single file. + * + * @param startAddr : Address for beginning of byte data. + * @param size : size of range in bytes. + * @param offset : offset into file for that data. + * + * @return bool : true if set successfully. + */ + bool AddOffsetRange(const ocsd_vaddr_t startAddr, const size_t size, const size_t offset); + + /*! + * Override in case we have multiple regions in the file. + * + * @param s_address : Address to test. + * + * @return const bool : true if the address is in range. + */ + virtual const bool addrInRange(const ocsd_vaddr_t s_address) const; + + /*! + * test if an address is the start of range for this accessor + * + * @param s_address : Address to test. + * + * @return const bool : true if the address is start of range. + */ + virtual const bool addrStartOfRange(const ocsd_vaddr_t s_address) const; + + /*! + * Test number of bytes available from the start address, up to the number of requested bytes. + * Tests if all the requested bytes are available from the supplied start address. + * Returns the number available up to full requested amount. + * + * @param s_address : Start address within the range. + * @param reqBytes : Number of bytes needed from the start address. + * + * @return const uint32_t : Bytes available, up to reqBytes. 0 is s_address not in range. + */ + virtual const uint32_t bytesInRange(const ocsd_vaddr_t s_address, const uint32_t reqBytes) const; + + /*! + * test is supplied range accessor overlaps this range. + * + * @param *p_test_acc : Accessor to test for overlap. + * + * @return bool : true if overlap, false if not. + */ + virtual const bool overLapRange(const TrcMemAccessorBase *p_test_acc) const; + + /*! Override to handle ranges and offset accessors plus add in file name. */ + virtual void getMemAccString(std::string &accStr) const; + + + /*! + * Create a file accessor based on the supplied path and address. + * Keeps a list of file accessors created. + * + * File will be checked to ensure valid accessor can be created. + * + * If an accessor using the supplied file is currently in use then a reference to that + * accessor will be returned and the accessor reference counter updated. + * + * @param &pathToFile : Path to binary file + * @param startAddr : Start address of data represented by file. + * + * @return TrcMemAccessorFile * : pointer to accessor if successful, 0 if it could not be created. + */ + static ocsd_err_t createFileAccessor(TrcMemAccessorFile **p_acc, const std::string &pathToFile, ocsd_vaddr_t startAddr, size_t offset = 0, size_t size = 0); + + /*! + * Destroy supplied accessor. + * + * Reference counter decremented and checked and accessor destroyed if no longer in use. + * + * @param *p_accessor : File Accessor to destroy. + */ + static void destroyFileAccessor(TrcMemAccessorFile *p_accessor); + + /*! + * Test if any accessor is currently using the supplied file path + * + * @param &pathToFile : Path to test. + * + * @return bool : true if an accessor exists with this file path. + */ + static const bool isExistingFileAccessor(const std::string &pathToFile); + + /*! + * Get the accessor using the supplied file path + * Use after createFileAccessor if additional memory ranges need + * adding to an exiting file accessor. + * + * @param &pathToFile : Path to test. + * + * @return TrcMemAccessorFile * : none 0 if an accessor exists with this file path. + */ + static TrcMemAccessorFile * getExistingFileAccessor(const std::string &pathToFile); + + + + +private: + static std::map<std::string, TrcMemAccessorFile *> s_FileAccessorMap; /**< map of file accessors in use. */ + +private: + std::ifstream m_mem_file; /**< input binary file stream */ + ocsd_vaddr_t m_file_size; /**< size of the file */ + int m_ref_count; /**< accessor reference count */ + std::string m_file_path; /**< path to input file */ + std::list<FileRegionMemAccessor *> m_access_regions; /**< additional regions in the file at non-zero offsets */ + bool m_base_range_set; /**< true when offset 0 set */ + bool m_has_access_regions; /**< true if single file contains multiple regions */ +}; + +#endif // ARM_TRC_MEM_ACC_FILE_H_INCLUDED + +/* End of File trc_mem_acc_file.h */ diff --git a/decoder/include/mem_acc/trc_mem_acc_mapper.h b/decoder/include/mem_acc/trc_mem_acc_mapper.h new file mode 100644 index 0000000..4a08498 --- /dev/null +++ b/decoder/include/mem_acc/trc_mem_acc_mapper.h @@ -0,0 +1,133 @@ +/* + * \file trc_mem_acc_mapper.h + * \brief OpenCSD : + * + * \copyright Copyright (c) 2015, ARM Limited. All Rights Reserved. + */ + +/* + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef ARM_TRC_MEM_ACC_MAPPER_H_INCLUDED +#define ARM_TRC_MEM_ACC_MAPPER_H_INCLUDED + +#include <vector> + +#include "opencsd/ocsd_if_types.h" +#include "interfaces/trc_tgt_mem_access_i.h" +#include "interfaces/trc_error_log_i.h" +#include "mem_acc/trc_mem_acc_base.h" +#include "mem_acc/trc_mem_acc_cache.h" + +typedef enum _memacc_mapper_t { + MEMACC_MAP_GLOBAL, +} memacc_mapper_t; + +class TrcMemAccMapper : public ITargetMemAccess +{ +public: + TrcMemAccMapper(); + TrcMemAccMapper(bool using_trace_id); + virtual ~TrcMemAccMapper(); + +// decoder memory access interface + virtual ocsd_err_t ReadTargetMemory( const ocsd_vaddr_t address, + const uint8_t cs_trace_id, + const ocsd_mem_space_acc_t mem_space, + uint32_t *num_bytes, + uint8_t *p_buffer); + + virtual void InvalidateMemAccCache(const uint8_t cs_trace_id); + +// mapper memory area configuration interface + + // add an accessor to this map + virtual ocsd_err_t AddAccessor(TrcMemAccessorBase *p_accessor, const uint8_t cs_trace_id) = 0; + + // remove a specific accessor + virtual ocsd_err_t RemoveAccessor(const TrcMemAccessorBase *p_accessor) = 0; + + + // clear all attached accessors from the map + void RemoveAllAccessors(); + + // remove a single accessor based on address. + ocsd_err_t RemoveAccessorByAddress(const ocsd_vaddr_t st_address, const ocsd_mem_space_acc_t mem_space, const uint8_t cs_trace_id = 0); + + // set the error log. + void setErrorLog(ITraceErrorLog *err_log_i); + + // print out the ranges in this mapper. + virtual void logMappedRanges() = 0; + +protected: + virtual bool findAccessor(const ocsd_vaddr_t address, const ocsd_mem_space_acc_t mem_space, const uint8_t cs_trace_id) = 0; // set m_acc_curr if found valid range, leave unchanged if not. + virtual bool readFromCurrent(const ocsd_vaddr_t address, const ocsd_mem_space_acc_t mem_space, const uint8_t cs_trace_id) = 0; + virtual TrcMemAccessorBase *getFirstAccessor() = 0; + virtual TrcMemAccessorBase *getNextAccessor() = 0; + virtual void clearAccessorList() = 0; + + void LogMessage(const std::string &msg); + void LogWarn(const ocsd_err_t err, const std::string &msg); + + TrcMemAccessorBase *m_acc_curr; // most recently used - try this first. + uint8_t m_trace_id_curr; // trace ID for the current accessor + const bool m_using_trace_id; // true if we are using separate memory spaces by TraceID. + ITraceErrorLog *m_err_log; // error log to print out mappings on request. + TrcMemAccCache m_cache; // memory accessor caching. +}; + + +// address spaces common to all sources using this mapper. +// trace id unused. +class TrcMemAccMapGlobalSpace : public TrcMemAccMapper +{ +public: + TrcMemAccMapGlobalSpace(); + virtual ~TrcMemAccMapGlobalSpace(); + + // mapper creation interface - prevent overlaps + virtual ocsd_err_t AddAccessor(TrcMemAccessorBase *p_accessor, const uint8_t cs_trace_id); + + // print out the ranges in this mapper. + virtual void logMappedRanges(); + +protected: + virtual bool findAccessor(const ocsd_vaddr_t address, const ocsd_mem_space_acc_t mem_space, const uint8_t cs_trace_id); + virtual bool readFromCurrent(const ocsd_vaddr_t address,const ocsd_mem_space_acc_t mem_space, const uint8_t cs_trace_id); + virtual TrcMemAccessorBase *getFirstAccessor(); + virtual TrcMemAccessorBase *getNextAccessor(); + virtual void clearAccessorList(); + virtual ocsd_err_t RemoveAccessor(const TrcMemAccessorBase *p_accessor); + + std::vector<TrcMemAccessorBase *> m_acc_global; + std::vector<TrcMemAccessorBase *>::iterator m_acc_it; +}; + +#endif // ARM_TRC_MEM_ACC_MAPPER_H_INCLUDED + +/* End of File trc_mem_acc_mapper.h */ |