1 /*===-- module.c - tool for testing libLLVM and llvm-c API ----------------===*\ 2 |* *| 3 |* The LLVM Compiler Infrastructure *| 4 |* *| 5 |* This file is distributed under the University of Illinois Open Source *| 6 |* License. See LICENSE.TXT for details. *| 7 |* *| 8 |*===----------------------------------------------------------------------===*| 9 |* *| 10 |* This file implements the --module-dump, --module-list-functions and *| 11 |* --module-list-globals commands in llvm-c-test. *| 12 |* *| 13 \*===----------------------------------------------------------------------===*/ 14 15 #include "llvm-c-test.h" 16 #include "llvm-c/BitReader.h" 17 #include "llvm-c/Core.h" 18 #include <stdio.h> 19 #include <stdlib.h> 20 #include <string.h> 21 22 static void diagnosticHandler(LLVMDiagnosticInfoRef DI, void *C) { 23 char *CErr = LLVMGetDiagInfoDescription(DI); 24 fprintf(stderr, "Error with new bitcode parser: %s\n", CErr); 25 LLVMDisposeMessage(CErr); 26 exit(1); 27 } 28 29 static LLVMModuleRef load_module(bool Lazy, bool New) { 30 LLVMMemoryBufferRef MB; 31 LLVMModuleRef M; 32 char *msg = NULL; 33 34 if (LLVMCreateMemoryBufferWithSTDIN(&MB, &msg)) { 35 fprintf(stderr, "Error reading file: %s\n", msg); 36 exit(1); 37 } 38 39 LLVMBool Ret; 40 if (New) { 41 LLVMContextRef C = LLVMGetGlobalContext(); 42 LLVMContextSetDiagnosticHandler(C, diagnosticHandler, NULL); 43 if (Lazy) 44 Ret = LLVMGetBitcodeModule2(MB, &M); 45 else 46 Ret = LLVMParseBitcode2(MB, &M); 47 } else { 48 if (Lazy) 49 Ret = LLVMGetBitcodeModule(MB, &M, &msg); 50 else 51 Ret = LLVMParseBitcode(MB, &M, &msg); 52 } 53 54 if (Ret) { 55 fprintf(stderr, "Error parsing bitcode: %s\n", msg); 56 LLVMDisposeMemoryBuffer(MB); 57 exit(1); 58 } 59 60 if (!Lazy) 61 LLVMDisposeMemoryBuffer(MB); 62 63 return M; 64 } 65 66 int module_dump(bool Lazy, bool New) { 67 LLVMModuleRef M = load_module(Lazy, New); 68 69 char *irstr = LLVMPrintModuleToString(M); 70 puts(irstr); 71 LLVMDisposeMessage(irstr); 72 73 LLVMDisposeModule(M); 74 75 return 0; 76 } 77 78 int module_list_functions(void) { 79 LLVMModuleRef M = load_module(false, false); 80 LLVMValueRef f; 81 82 f = LLVMGetFirstFunction(M); 83 while (f) { 84 if (LLVMIsDeclaration(f)) { 85 printf("FunctionDeclaration: %s\n", LLVMGetValueName(f)); 86 } else { 87 LLVMBasicBlockRef bb; 88 LLVMValueRef isn; 89 unsigned nisn = 0; 90 unsigned nbb = 0; 91 92 printf("FunctionDefinition: %s [#bb=%u]\n", LLVMGetValueName(f), 93 LLVMCountBasicBlocks(f)); 94 95 for (bb = LLVMGetFirstBasicBlock(f); bb; 96 bb = LLVMGetNextBasicBlock(bb)) { 97 nbb++; 98 for (isn = LLVMGetFirstInstruction(bb); isn; 99 isn = LLVMGetNextInstruction(isn)) { 100 nisn++; 101 if (LLVMIsACallInst(isn)) { 102 LLVMValueRef callee = 103 LLVMGetOperand(isn, LLVMGetNumOperands(isn) - 1); 104 printf(" calls: %s\n", LLVMGetValueName(callee)); 105 } 106 } 107 } 108 printf(" #isn: %u\n", nisn); 109 printf(" #bb: %u\n\n", nbb); 110 } 111 f = LLVMGetNextFunction(f); 112 } 113 114 LLVMDisposeModule(M); 115 116 return 0; 117 } 118 119 int module_list_globals(void) { 120 LLVMModuleRef M = load_module(false, false); 121 LLVMValueRef g; 122 123 g = LLVMGetFirstGlobal(M); 124 while (g) { 125 LLVMTypeRef T = LLVMTypeOf(g); 126 char *s = LLVMPrintTypeToString(T); 127 128 printf("Global%s: %s %s\n", 129 LLVMIsDeclaration(g) ? "Declaration" : "Definition", 130 LLVMGetValueName(g), s); 131 132 LLVMDisposeMessage(s); 133 134 g = LLVMGetNextGlobal(g); 135 } 136 137 LLVMDisposeModule(M); 138 139 return 0; 140 } 141