13cab2bb3Spatrick /*===- InstrProfiling.h- Support library for PGO instrumentation ----------===*\ 23cab2bb3Spatrick |* 33cab2bb3Spatrick |* Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 43cab2bb3Spatrick |* See https://llvm.org/LICENSE.txt for license information. 53cab2bb3Spatrick |* SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 63cab2bb3Spatrick |* 73cab2bb3Spatrick \*===----------------------------------------------------------------------===*/ 83cab2bb3Spatrick 93cab2bb3Spatrick #ifndef PROFILE_INSTRPROFILING_INTERNALH_ 103cab2bb3Spatrick #define PROFILE_INSTRPROFILING_INTERNALH_ 113cab2bb3Spatrick 123cab2bb3Spatrick #include <stddef.h> 133cab2bb3Spatrick 143cab2bb3Spatrick #include "InstrProfiling.h" 153cab2bb3Spatrick 163cab2bb3Spatrick /*! 173cab2bb3Spatrick * \brief Write instrumentation data to the given buffer, given explicit 183cab2bb3Spatrick * pointers to the live data in memory. This function is probably not what you 193cab2bb3Spatrick * want. Use __llvm_profile_get_size_for_buffer instead. Use this function if 203cab2bb3Spatrick * your program has a custom memory layout. 213cab2bb3Spatrick */ 223cab2bb3Spatrick uint64_t __llvm_profile_get_size_for_buffer_internal( 233cab2bb3Spatrick const __llvm_profile_data *DataBegin, const __llvm_profile_data *DataEnd, 24*810390e3Srobert const char *CountersBegin, const char *CountersEnd, const char *NamesBegin, 25*810390e3Srobert const char *NamesEnd); 263cab2bb3Spatrick 273cab2bb3Spatrick /*! 283cab2bb3Spatrick * \brief Write instrumentation data to the given buffer, given explicit 293cab2bb3Spatrick * pointers to the live data in memory. This function is probably not what you 303cab2bb3Spatrick * want. Use __llvm_profile_write_buffer instead. Use this function if your 313cab2bb3Spatrick * program has a custom memory layout. 323cab2bb3Spatrick * 333cab2bb3Spatrick * \pre \c Buffer is the start of a buffer at least as big as \a 343cab2bb3Spatrick * __llvm_profile_get_size_for_buffer_internal(). 353cab2bb3Spatrick */ 363cab2bb3Spatrick int __llvm_profile_write_buffer_internal( 373cab2bb3Spatrick char *Buffer, const __llvm_profile_data *DataBegin, 38*810390e3Srobert const __llvm_profile_data *DataEnd, const char *CountersBegin, 39*810390e3Srobert const char *CountersEnd, const char *NamesBegin, const char *NamesEnd); 403cab2bb3Spatrick 413cab2bb3Spatrick /*! 423cab2bb3Spatrick * The data structure describing the data to be written by the 433cab2bb3Spatrick * low level writer callback function. 443cab2bb3Spatrick * 453cab2bb3Spatrick * If \ref ProfDataIOVec.Data is null, and \ref ProfDataIOVec.UseZeroPadding is 463cab2bb3Spatrick * 0, the write is skipped (the writer simply advances ElmSize*NumElm bytes). 473cab2bb3Spatrick * 483cab2bb3Spatrick * If \ref ProfDataIOVec.Data is null, and \ref ProfDataIOVec.UseZeroPadding is 493cab2bb3Spatrick * nonzero, ElmSize*NumElm zero bytes are written. 503cab2bb3Spatrick */ 513cab2bb3Spatrick typedef struct ProfDataIOVec { 523cab2bb3Spatrick const void *Data; 533cab2bb3Spatrick size_t ElmSize; 543cab2bb3Spatrick size_t NumElm; 553cab2bb3Spatrick int UseZeroPadding; 563cab2bb3Spatrick } ProfDataIOVec; 573cab2bb3Spatrick 583cab2bb3Spatrick struct ProfDataWriter; 593cab2bb3Spatrick typedef uint32_t (*WriterCallback)(struct ProfDataWriter *This, ProfDataIOVec *, 603cab2bb3Spatrick uint32_t NumIOVecs); 613cab2bb3Spatrick 623cab2bb3Spatrick typedef struct ProfDataWriter { 633cab2bb3Spatrick WriterCallback Write; 643cab2bb3Spatrick void *WriterCtx; 653cab2bb3Spatrick } ProfDataWriter; 663cab2bb3Spatrick 673cab2bb3Spatrick /*! 683cab2bb3Spatrick * The data structure for buffered IO of profile data. 693cab2bb3Spatrick */ 703cab2bb3Spatrick typedef struct ProfBufferIO { 713cab2bb3Spatrick ProfDataWriter *FileWriter; 723cab2bb3Spatrick uint32_t OwnFileWriter; 733cab2bb3Spatrick /* The start of the buffer. */ 743cab2bb3Spatrick uint8_t *BufferStart; 753cab2bb3Spatrick /* Total size of the buffer. */ 763cab2bb3Spatrick uint32_t BufferSz; 773cab2bb3Spatrick /* Current byte offset from the start of the buffer. */ 783cab2bb3Spatrick uint32_t CurOffset; 793cab2bb3Spatrick } ProfBufferIO; 803cab2bb3Spatrick 813cab2bb3Spatrick /* The creator interface used by testing. */ 823cab2bb3Spatrick ProfBufferIO *lprofCreateBufferIOInternal(void *File, uint32_t BufferSz); 833cab2bb3Spatrick 843cab2bb3Spatrick /*! 853cab2bb3Spatrick * This is the interface to create a handle for buffered IO. 863cab2bb3Spatrick */ 873cab2bb3Spatrick ProfBufferIO *lprofCreateBufferIO(ProfDataWriter *FileWriter); 883cab2bb3Spatrick 893cab2bb3Spatrick /*! 903cab2bb3Spatrick * The interface to destroy the bufferIO handle and reclaim 913cab2bb3Spatrick * the memory. 923cab2bb3Spatrick */ 933cab2bb3Spatrick void lprofDeleteBufferIO(ProfBufferIO *BufferIO); 943cab2bb3Spatrick 953cab2bb3Spatrick /*! 963cab2bb3Spatrick * This is the interface to write \c Data of \c Size bytes through 973cab2bb3Spatrick * \c BufferIO. Returns 0 if successful, otherwise return -1. 983cab2bb3Spatrick */ 993cab2bb3Spatrick int lprofBufferIOWrite(ProfBufferIO *BufferIO, const uint8_t *Data, 1003cab2bb3Spatrick uint32_t Size); 1013cab2bb3Spatrick /*! 1023cab2bb3Spatrick * The interface to flush the remaining data in the buffer. 1033cab2bb3Spatrick * through the low level writer callback. 1043cab2bb3Spatrick */ 1053cab2bb3Spatrick int lprofBufferIOFlush(ProfBufferIO *BufferIO); 1063cab2bb3Spatrick 1073cab2bb3Spatrick /* The low level interface to write data into a buffer. It is used as the 1083cab2bb3Spatrick * callback by other high level writer methods such as buffered IO writer 1093cab2bb3Spatrick * and profile data writer. */ 1103cab2bb3Spatrick uint32_t lprofBufferWriter(ProfDataWriter *This, ProfDataIOVec *IOVecs, 1113cab2bb3Spatrick uint32_t NumIOVecs); 1123cab2bb3Spatrick void initBufferWriter(ProfDataWriter *BufferWriter, char *Buffer); 1133cab2bb3Spatrick 1143cab2bb3Spatrick struct ValueProfData; 1153cab2bb3Spatrick struct ValueProfRecord; 1163cab2bb3Spatrick struct InstrProfValueData; 1173cab2bb3Spatrick struct ValueProfNode; 1183cab2bb3Spatrick 1193cab2bb3Spatrick /*! 1203cab2bb3Spatrick * The class that defines a set of methods to read value profile 1213cab2bb3Spatrick * data for streaming/serialization from the instrumentation runtime. 1223cab2bb3Spatrick */ 1233cab2bb3Spatrick typedef struct VPDataReaderType { 1243cab2bb3Spatrick uint32_t (*InitRTRecord)(const __llvm_profile_data *Data, 1253cab2bb3Spatrick uint8_t *SiteCountArray[]); 1263cab2bb3Spatrick /* Function pointer to getValueProfRecordHeader method. */ 1273cab2bb3Spatrick uint32_t (*GetValueProfRecordHeaderSize)(uint32_t NumSites); 1283cab2bb3Spatrick /* Function pointer to getFristValueProfRecord method. */ 1293cab2bb3Spatrick struct ValueProfRecord *(*GetFirstValueProfRecord)(struct ValueProfData *); 1303cab2bb3Spatrick /* Return the number of value data for site \p Site. */ 1313cab2bb3Spatrick uint32_t (*GetNumValueDataForSite)(uint32_t VK, uint32_t Site); 1323cab2bb3Spatrick /* Return the total size of the value profile data of the 1333cab2bb3Spatrick * current function. */ 1343cab2bb3Spatrick uint32_t (*GetValueProfDataSize)(void); 1353cab2bb3Spatrick /*! 1363cab2bb3Spatrick * Read the next \p N value data for site \p Site and store the data 1373cab2bb3Spatrick * in \p Dst. \p StartNode is the first value node to start with if 1383cab2bb3Spatrick * it is not null. The function returns the pointer to the value 1393cab2bb3Spatrick * node pointer to be used as the \p StartNode of the next batch reading. 1403cab2bb3Spatrick * If there is nothing left, it returns NULL. 1413cab2bb3Spatrick */ 1423cab2bb3Spatrick struct ValueProfNode *(*GetValueData)(uint32_t ValueKind, uint32_t Site, 1433cab2bb3Spatrick struct InstrProfValueData *Dst, 1443cab2bb3Spatrick struct ValueProfNode *StartNode, 1453cab2bb3Spatrick uint32_t N); 1463cab2bb3Spatrick } VPDataReaderType; 1473cab2bb3Spatrick 148*810390e3Srobert /* Write profile data to destination. If SkipNameDataWrite is set to 1, 149*810390e3Srobert the name data is already in destination, we just skip over it. */ 1503cab2bb3Spatrick int lprofWriteData(ProfDataWriter *Writer, VPDataReaderType *VPDataReader, 1513cab2bb3Spatrick int SkipNameDataWrite); 1523cab2bb3Spatrick int lprofWriteDataImpl(ProfDataWriter *Writer, 1533cab2bb3Spatrick const __llvm_profile_data *DataBegin, 1543cab2bb3Spatrick const __llvm_profile_data *DataEnd, 155*810390e3Srobert const char *CountersBegin, const char *CountersEnd, 1563cab2bb3Spatrick VPDataReaderType *VPDataReader, const char *NamesBegin, 1573cab2bb3Spatrick const char *NamesEnd, int SkipNameDataWrite); 1583cab2bb3Spatrick 1593cab2bb3Spatrick /* Merge value profile data pointed to by SrcValueProfData into 1603cab2bb3Spatrick * in-memory profile counters pointed by to DstData. */ 1613cab2bb3Spatrick void lprofMergeValueProfData(struct ValueProfData *SrcValueProfData, 1623cab2bb3Spatrick __llvm_profile_data *DstData); 1633cab2bb3Spatrick 1643cab2bb3Spatrick VPDataReaderType *lprofGetVPDataReader(); 1653cab2bb3Spatrick 1663cab2bb3Spatrick /* Internal interface used by test to reset the max number of 1673cab2bb3Spatrick * tracked values per value site to be \p MaxVals. 1683cab2bb3Spatrick */ 1693cab2bb3Spatrick void lprofSetMaxValsPerSite(uint32_t MaxVals); 1703cab2bb3Spatrick void lprofSetupValueProfiler(); 1713cab2bb3Spatrick 1723cab2bb3Spatrick /* Return the profile header 'signature' value associated with the current 1733cab2bb3Spatrick * executable or shared library. The signature value can be used to for 1743cab2bb3Spatrick * a profile name that is unique to this load module so that it does not 1753cab2bb3Spatrick * collide with profiles from other binaries. It also allows shared libraries 1763cab2bb3Spatrick * to dump merged profile data into its own profile file. */ 1773cab2bb3Spatrick uint64_t lprofGetLoadModuleSignature(); 1783cab2bb3Spatrick 1793cab2bb3Spatrick /* 1803cab2bb3Spatrick * Return non zero value if the profile data has already been 1813cab2bb3Spatrick * dumped to the file. 1823cab2bb3Spatrick */ 1831f9cb04fSpatrick unsigned lprofProfileDumped(void); 1841f9cb04fSpatrick void lprofSetProfileDumped(unsigned); 1851f9cb04fSpatrick 1863cab2bb3Spatrick COMPILER_RT_VISIBILITY extern void (*FreeHook)(void *); 1873cab2bb3Spatrick COMPILER_RT_VISIBILITY extern uint8_t *DynamicBufferIOBuffer; 1883cab2bb3Spatrick COMPILER_RT_VISIBILITY extern uint32_t VPBufferSize; 1893cab2bb3Spatrick COMPILER_RT_VISIBILITY extern uint32_t VPMaxNumValsPerSite; 1903cab2bb3Spatrick /* Pointer to the start of static value counters to be allocted. */ 1913cab2bb3Spatrick COMPILER_RT_VISIBILITY extern ValueProfNode *CurrentVNode; 1923cab2bb3Spatrick COMPILER_RT_VISIBILITY extern ValueProfNode *EndVNode; 1933cab2bb3Spatrick extern void (*VPMergeHook)(struct ValueProfData *, __llvm_profile_data *); 1943cab2bb3Spatrick 195d89ec533Spatrick /* 196d89ec533Spatrick * Write binary ids into profiles if writer is given. 197d89ec533Spatrick * Return -1 if an error occurs, otherwise, return total size of binary ids. 198d89ec533Spatrick */ 199d89ec533Spatrick int __llvm_write_binary_ids(ProfDataWriter *Writer); 200d89ec533Spatrick 2013cab2bb3Spatrick #endif 202