1 /*===-- llvm-c/Remarks.h - Remarks Public C Interface -------------*- C -*-===*\ 2 |* *| 3 |* Part of the LLVM Project, under the Apache License v2.0 with LLVM *| 4 |* Exceptions. *| 5 |* See https://llvm.org/LICENSE.txt for license information. *| 6 |* SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception *| 7 |* *| 8 |*===----------------------------------------------------------------------===*| 9 |* *| 10 |* This header provides a public interface to a remark diagnostics library. *| 11 |* LLVM provides an implementation of this interface. *| 12 |* *| 13 \*===----------------------------------------------------------------------===*/ 14 15 #ifndef LLVM_C_REMARKS_H 16 #define LLVM_C_REMARKS_H 17 18 #include "llvm-c/ExternC.h" 19 #include "llvm-c/Types.h" 20 #ifdef __cplusplus 21 #include <cstddef> 22 #else 23 #include <stddef.h> 24 #endif /* !defined(__cplusplus) */ 25 26 LLVM_C_EXTERN_C_BEGIN 27 28 /** 29 * @defgroup LLVMCREMARKS Remarks 30 * @ingroup LLVMC 31 * 32 * @{ 33 */ 34 35 // 0 -> 1: Bitstream remarks support. 36 #define REMARKS_API_VERSION 1 37 38 /** 39 * The type of the emitted remark. 40 */ 41 enum LLVMRemarkType { 42 LLVMRemarkTypeUnknown, 43 LLVMRemarkTypePassed, 44 LLVMRemarkTypeMissed, 45 LLVMRemarkTypeAnalysis, 46 LLVMRemarkTypeAnalysisFPCommute, 47 LLVMRemarkTypeAnalysisAliasing, 48 LLVMRemarkTypeFailure 49 }; 50 51 /** 52 * String containing a buffer and a length. The buffer is not guaranteed to be 53 * zero-terminated. 54 * 55 * \since REMARKS_API_VERSION=0 56 */ 57 typedef struct LLVMRemarkOpaqueString *LLVMRemarkStringRef; 58 59 /** 60 * Returns the buffer holding the string. 61 * 62 * \since REMARKS_API_VERSION=0 63 */ 64 extern const char *LLVMRemarkStringGetData(LLVMRemarkStringRef String); 65 66 /** 67 * Returns the size of the string. 68 * 69 * \since REMARKS_API_VERSION=0 70 */ 71 extern uint32_t LLVMRemarkStringGetLen(LLVMRemarkStringRef String); 72 73 /** 74 * DebugLoc containing File, Line and Column. 75 * 76 * \since REMARKS_API_VERSION=0 77 */ 78 typedef struct LLVMRemarkOpaqueDebugLoc *LLVMRemarkDebugLocRef; 79 80 /** 81 * Return the path to the source file for a debug location. 82 * 83 * \since REMARKS_API_VERSION=0 84 */ 85 extern LLVMRemarkStringRef 86 LLVMRemarkDebugLocGetSourceFilePath(LLVMRemarkDebugLocRef DL); 87 88 /** 89 * Return the line in the source file for a debug location. 90 * 91 * \since REMARKS_API_VERSION=0 92 */ 93 extern uint32_t LLVMRemarkDebugLocGetSourceLine(LLVMRemarkDebugLocRef DL); 94 95 /** 96 * Return the column in the source file for a debug location. 97 * 98 * \since REMARKS_API_VERSION=0 99 */ 100 extern uint32_t LLVMRemarkDebugLocGetSourceColumn(LLVMRemarkDebugLocRef DL); 101 102 /** 103 * Element of the "Args" list. The key might give more information about what 104 * the semantics of the value are, e.g. "Callee" will tell you that the value 105 * is a symbol that names a function. 106 * 107 * \since REMARKS_API_VERSION=0 108 */ 109 typedef struct LLVMRemarkOpaqueArg *LLVMRemarkArgRef; 110 111 /** 112 * Returns the key of an argument. The key defines what the value is, and the 113 * same key can appear multiple times in the list of arguments. 114 * 115 * \since REMARKS_API_VERSION=0 116 */ 117 extern LLVMRemarkStringRef LLVMRemarkArgGetKey(LLVMRemarkArgRef Arg); 118 119 /** 120 * Returns the value of an argument. This is a string that can contain newlines. 121 * 122 * \since REMARKS_API_VERSION=0 123 */ 124 extern LLVMRemarkStringRef LLVMRemarkArgGetValue(LLVMRemarkArgRef Arg); 125 126 /** 127 * Returns the debug location that is attached to the value of this argument. 128 * 129 * If there is no debug location, the return value will be `NULL`. 130 * 131 * \since REMARKS_API_VERSION=0 132 */ 133 extern LLVMRemarkDebugLocRef LLVMRemarkArgGetDebugLoc(LLVMRemarkArgRef Arg); 134 135 /** 136 * A remark emitted by the compiler. 137 * 138 * \since REMARKS_API_VERSION=0 139 */ 140 typedef struct LLVMRemarkOpaqueEntry *LLVMRemarkEntryRef; 141 142 /** 143 * Free the resources used by the remark entry. 144 * 145 * \since REMARKS_API_VERSION=0 146 */ 147 extern void LLVMRemarkEntryDispose(LLVMRemarkEntryRef Remark); 148 149 /** 150 * The type of the remark. For example, it can allow users to only keep the 151 * missed optimizations from the compiler. 152 * 153 * \since REMARKS_API_VERSION=0 154 */ 155 extern enum LLVMRemarkType LLVMRemarkEntryGetType(LLVMRemarkEntryRef Remark); 156 157 /** 158 * Get the name of the pass that emitted this remark. 159 * 160 * \since REMARKS_API_VERSION=0 161 */ 162 extern LLVMRemarkStringRef 163 LLVMRemarkEntryGetPassName(LLVMRemarkEntryRef Remark); 164 165 /** 166 * Get an identifier of the remark. 167 * 168 * \since REMARKS_API_VERSION=0 169 */ 170 extern LLVMRemarkStringRef 171 LLVMRemarkEntryGetRemarkName(LLVMRemarkEntryRef Remark); 172 173 /** 174 * Get the name of the function being processed when the remark was emitted. 175 * 176 * \since REMARKS_API_VERSION=0 177 */ 178 extern LLVMRemarkStringRef 179 LLVMRemarkEntryGetFunctionName(LLVMRemarkEntryRef Remark); 180 181 /** 182 * Returns the debug location that is attached to this remark. 183 * 184 * If there is no debug location, the return value will be `NULL`. 185 * 186 * \since REMARKS_API_VERSION=0 187 */ 188 extern LLVMRemarkDebugLocRef 189 LLVMRemarkEntryGetDebugLoc(LLVMRemarkEntryRef Remark); 190 191 /** 192 * Return the hotness of the remark. 193 * 194 * A hotness of `0` means this value is not set. 195 * 196 * \since REMARKS_API_VERSION=0 197 */ 198 extern uint64_t LLVMRemarkEntryGetHotness(LLVMRemarkEntryRef Remark); 199 200 /** 201 * The number of arguments the remark holds. 202 * 203 * \since REMARKS_API_VERSION=0 204 */ 205 extern uint32_t LLVMRemarkEntryGetNumArgs(LLVMRemarkEntryRef Remark); 206 207 /** 208 * Get a new iterator to iterate over a remark's argument. 209 * 210 * If there are no arguments in \p Remark, the return value will be `NULL`. 211 * 212 * The lifetime of the returned value is bound to the lifetime of \p Remark. 213 * 214 * \since REMARKS_API_VERSION=0 215 */ 216 extern LLVMRemarkArgRef LLVMRemarkEntryGetFirstArg(LLVMRemarkEntryRef Remark); 217 218 /** 219 * Get the next argument in \p Remark from the position of \p It. 220 * 221 * Returns `NULL` if there are no more arguments available. 222 * 223 * The lifetime of the returned value is bound to the lifetime of \p Remark. 224 * 225 * \since REMARKS_API_VERSION=0 226 */ 227 extern LLVMRemarkArgRef LLVMRemarkEntryGetNextArg(LLVMRemarkArgRef It, 228 LLVMRemarkEntryRef Remark); 229 230 typedef struct LLVMRemarkOpaqueParser *LLVMRemarkParserRef; 231 232 /** 233 * Creates a remark parser that can be used to parse the buffer located in \p 234 * Buf of size \p Size bytes. 235 * 236 * \p Buf cannot be `NULL`. 237 * 238 * This function should be paired with LLVMRemarkParserDispose() to avoid 239 * leaking resources. 240 * 241 * \since REMARKS_API_VERSION=0 242 */ 243 extern LLVMRemarkParserRef LLVMRemarkParserCreateYAML(const void *Buf, 244 uint64_t Size); 245 246 /** 247 * Creates a remark parser that can be used to parse the buffer located in \p 248 * Buf of size \p Size bytes. 249 * 250 * \p Buf cannot be `NULL`. 251 * 252 * This function should be paired with LLVMRemarkParserDispose() to avoid 253 * leaking resources. 254 * 255 * \since REMARKS_API_VERSION=1 256 */ 257 extern LLVMRemarkParserRef LLVMRemarkParserCreateBitstream(const void *Buf, 258 uint64_t Size); 259 260 /** 261 * Returns the next remark in the file. 262 * 263 * The value pointed to by the return value needs to be disposed using a call to 264 * LLVMRemarkEntryDispose(). 265 * 266 * All the entries in the returned value that are of LLVMRemarkStringRef type 267 * will become invalidated once a call to LLVMRemarkParserDispose is made. 268 * 269 * If the parser reaches the end of the buffer, the return value will be `NULL`. 270 * 271 * In the case of an error, the return value will be `NULL`, and: 272 * 273 * 1) LLVMRemarkParserHasError() will return `1`. 274 * 275 * 2) LLVMRemarkParserGetErrorMessage() will return a descriptive error 276 * message. 277 * 278 * An error may occur if: 279 * 280 * 1) An argument is invalid. 281 * 282 * 2) There is a parsing error. This can occur on things like malformed YAML. 283 * 284 * 3) There is a Remark semantic error. This can occur on well-formed files with 285 * missing or extra fields. 286 * 287 * Here is a quick example of the usage: 288 * 289 * ``` 290 * LLVMRemarkParserRef Parser = LLVMRemarkParserCreateYAML(Buf, Size); 291 * LLVMRemarkEntryRef Remark = NULL; 292 * while ((Remark = LLVMRemarkParserGetNext(Parser))) { 293 * // use Remark 294 * LLVMRemarkEntryDispose(Remark); // Release memory. 295 * } 296 * bool HasError = LLVMRemarkParserHasError(Parser); 297 * LLVMRemarkParserDispose(Parser); 298 * ``` 299 * 300 * \since REMARKS_API_VERSION=0 301 */ 302 extern LLVMRemarkEntryRef LLVMRemarkParserGetNext(LLVMRemarkParserRef Parser); 303 304 /** 305 * Returns `1` if the parser encountered an error while parsing the buffer. 306 * 307 * \since REMARKS_API_VERSION=0 308 */ 309 extern LLVMBool LLVMRemarkParserHasError(LLVMRemarkParserRef Parser); 310 311 /** 312 * Returns a null-terminated string containing an error message. 313 * 314 * In case of no error, the result is `NULL`. 315 * 316 * The memory of the string is bound to the lifetime of \p Parser. If 317 * LLVMRemarkParserDispose() is called, the memory of the string will be 318 * released. 319 * 320 * \since REMARKS_API_VERSION=0 321 */ 322 extern const char *LLVMRemarkParserGetErrorMessage(LLVMRemarkParserRef Parser); 323 324 /** 325 * Releases all the resources used by \p Parser. 326 * 327 * \since REMARKS_API_VERSION=0 328 */ 329 extern void LLVMRemarkParserDispose(LLVMRemarkParserRef Parser); 330 331 /** 332 * Returns the version of the remarks library. 333 * 334 * \since REMARKS_API_VERSION=0 335 */ 336 extern uint32_t LLVMRemarkVersion(void); 337 338 /** 339 * @} // endgoup LLVMCREMARKS 340 */ 341 342 LLVM_C_EXTERN_C_END 343 344 #endif /* LLVM_C_REMARKS_H */ 345