Intel SPMD Program Compiler  1.12.0
func.cpp
Go to the documentation of this file.
1 /*
2  Copyright (c) 2011-2019, Intel Corporation
3  All rights reserved.
4 
5  Redistribution and use in source and binary forms, with or without
6  modification, are permitted provided that the following conditions are
7  met:
8 
9  * Redistributions of source code must retain the above copyright
10  notice, this list of conditions and the following disclaimer.
11 
12  * Redistributions in binary form must reproduce the above copyright
13  notice, this list of conditions and the following disclaimer in the
14  documentation and/or other materials provided with the distribution.
15 
16  * Neither the name of Intel Corporation nor the names of its
17  contributors may be used to endorse or promote products derived from
18  this software without specific prior written permission.
19 
20 
21  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
22  IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
23  TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
24  PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
25  OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
26  EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
27  PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
28  PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
29  LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
30  NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
31  SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 */
33 
34 /** @file func.cpp
35  @brief
36 */
37 
38 #include "func.h"
39 #include "ctx.h"
40 #include "expr.h"
41 #include "llvmutil.h"
42 #include "module.h"
43 #include "stmt.h"
44 #include "sym.h"
45 #include "type.h"
46 #include "util.h"
47 #include <stdio.h>
48 
49 #if ISPC_LLVM_VERSION == ISPC_LLVM_3_2 // 3.2
50 #ifdef ISPC_NVPTX_ENABLED
51 #include <llvm/Metadata.h>
52 #endif /* ISPC_NVPTX_ENABLED */
53 #include <llvm/DerivedTypes.h>
54 #include <llvm/Instructions.h>
55 #include <llvm/Intrinsics.h>
56 #include <llvm/LLVMContext.h>
57 #include <llvm/Module.h>
58 #include <llvm/Type.h>
59 #else
60 #ifdef ISPC_NVPTX_ENABLED
61 #include <llvm/IR/Metadata.h>
62 #endif /* ISPC_NVPTX_ENABLED */
63 #include <llvm/IR/DerivedTypes.h>
64 #include <llvm/IR/Instructions.h>
65 #include <llvm/IR/Intrinsics.h>
66 #include <llvm/IR/LLVMContext.h>
67 #include <llvm/IR/Module.h>
68 #include <llvm/IR/Type.h>
69 #endif
70 #if ISPC_LLVM_VERSION <= ISPC_LLVM_3_6
71 #include "llvm/PassManager.h"
72 #else // LLVM 3.7+
73 #include "llvm/IR/LegacyPassManager.h"
74 #endif
75 #include <llvm/PassRegistry.h>
76 #include <llvm/Support/FileUtilities.h>
77 #include <llvm/Support/FormattedStream.h>
78 #include <llvm/Target/TargetMachine.h>
79 #include <llvm/Target/TargetOptions.h>
80 #include <llvm/Transforms/IPO.h>
81 #if ISPC_LLVM_VERSION >= ISPC_LLVM_3_5 // LLVM 3.5+
82 #include <llvm/IR/CFG.h>
83 #include <llvm/IR/IRPrintingPasses.h>
84 #include <llvm/IR/Verifier.h>
85 #else
86 #include <llvm/Analysis/Verifier.h>
87 #include <llvm/Assembly/PrintModulePass.h>
88 #include <llvm/Support/CFG.h>
89 #endif
90 #include <llvm/Support/ToolOutputFile.h>
91 
93  sym = s;
94  code = c;
95 
96  maskSymbol = m->symbolTable->LookupVariable("__mask");
97  Assert(maskSymbol != NULL);
98 
99  if (code != NULL) {
100  code = TypeCheck(code);
101 
102  if (code != NULL && g->debugPrint) {
103  printf("After typechecking function \"%s\":\n", sym->name.c_str());
104  code->Print(0);
105  printf("---------------------\n");
106  }
107 
108  if (code != NULL) {
109  code = Optimize(code);
110  if (g->debugPrint) {
111  printf("After optimizing function \"%s\":\n", sym->name.c_str());
112  code->Print(0);
113  printf("---------------------\n");
114  }
115  }
116  }
117 
118  if (g->debugPrint) {
119  printf("Add Function %s\n", sym->name.c_str());
120  code->Print(0);
121  printf("\n\n\n");
122  }
123 
124  const FunctionType *type = CastType<FunctionType>(sym->type);
125  Assert(type != NULL);
126 
127  for (int i = 0; i < type->GetNumParameters(); ++i) {
128  const char *paramName = type->GetParameterName(i).c_str();
129  Symbol *sym = m->symbolTable->LookupVariable(paramName);
130  if (sym == NULL)
131  Assert(strncmp(paramName, "__anon_parameter_", 17) == 0);
132  args.push_back(sym);
133 
134  const Type *t = type->GetParameterType(i);
135  if (sym != NULL && CastType<ReferenceType>(t) == NULL)
136  sym->parentFunction = this;
137  }
138 
139  if (type->isTask
140 #ifdef ISPC_NVPTX_ENABLED
141  && (g->target->getISA() != Target::NVPTX)
142 #endif
143  ) {
144  threadIndexSym = m->symbolTable->LookupVariable("threadIndex");
146  threadCountSym = m->symbolTable->LookupVariable("threadCount");
148  taskIndexSym = m->symbolTable->LookupVariable("taskIndex");
150  taskCountSym = m->symbolTable->LookupVariable("taskCount");
152 
153  taskIndexSym0 = m->symbolTable->LookupVariable("taskIndex0");
155  taskIndexSym1 = m->symbolTable->LookupVariable("taskIndex1");
157  taskIndexSym2 = m->symbolTable->LookupVariable("taskIndex2");
159 
160  taskCountSym0 = m->symbolTable->LookupVariable("taskCount0");
162  taskCountSym1 = m->symbolTable->LookupVariable("taskCount1");
164  taskCountSym2 = m->symbolTable->LookupVariable("taskCount2");
166  } else {
170  }
171 }
172 
174  const FunctionType *type = CastType<FunctionType>(sym->type);
175  Assert(type != NULL);
176  return type->GetReturnType();
177 }
178 
180  const FunctionType *type = CastType<FunctionType>(sym->type);
181  Assert(type != NULL);
182  return type;
183 }
184 
185 /** Parameters for tasks are stored in a big structure; this utility
186  function emits code to copy those values out of the task structure into
187  local stack-allocated variables. (Which we expect that LLVM's
188  'mem2reg' pass will in turn promote to SSA registers..
189  */
190 static void lCopyInTaskParameter(int i, llvm::Value *structArgPtr, const std::vector<Symbol *> &args,
191  FunctionEmitContext *ctx) {
192  // We expect the argument structure to come in as a poitner to a
193  // structure. Confirm and figure out its type here.
194  const llvm::Type *structArgType = structArgPtr->getType();
195  Assert(llvm::isa<llvm::PointerType>(structArgType));
196  const llvm::PointerType *pt = llvm::dyn_cast<const llvm::PointerType>(structArgType);
197  Assert(llvm::isa<llvm::StructType>(pt->getElementType()));
198  const llvm::StructType *argStructType = llvm::dyn_cast<const llvm::StructType>(pt->getElementType());
199 
200  // Get the type of the argument we're copying in and its Symbol pointer
201  llvm::Type *argType = argStructType->getElementType(i);
202  Symbol *sym = args[i];
203 
204  if (sym == NULL)
205  // anonymous parameter, so don't worry about it
206  return;
207 
208  // allocate space to copy the parameter in to
209  sym->storagePtr = ctx->AllocaInst(argType, sym->name.c_str());
210 
211  // get a pointer to the value in the struct
212  llvm::Value *ptr = ctx->AddElementOffset(structArgPtr, i, NULL, sym->name.c_str());
213 
214  // and copy the value from the struct and into the local alloca'ed
215  // memory
216  llvm::Value *ptrval = ctx->LoadInst(ptr, sym->name.c_str());
217  ctx->StoreInst(ptrval, sym->storagePtr);
218  ctx->EmitFunctionParameterDebugInfo(sym, i);
219 }
220 
221 /** Given the statements implementing a function, emit the code that
222  implements the function. Most of the work do be done here just
223  involves wiring up the function parameter values to be available in the
224  function body code.
225  */
226 void Function::emitCode(FunctionEmitContext *ctx, llvm::Function *function, SourcePos firstStmtPos) {
227  // Connect the __mask builtin to the location in memory that stores its
228  // value
230 
231  // add debugging info for __mask
232  maskSymbol->pos = firstStmtPos;
234 
235 #if ISPC_LLVM_VERSION >= ISPC_LLVM_3_7 // LLVM 3.7+
236  if (g->NoOmitFramePointer)
237  function->addFnAttr("no-frame-pointer-elim", "true");
238 #endif
239  g->target->markFuncWithTargetAttr(function);
240 #if 0
241  llvm::BasicBlock *entryBBlock = ctx->GetCurrentBasicBlock();
242 #endif
243  const FunctionType *type = CastType<FunctionType>(sym->type);
244  Assert(type != NULL);
245  if (type->isTask == true
246 #ifdef ISPC_NVPTX_ENABLED
247  && (g->target->getISA() != Target::NVPTX)
248 #endif
249  ) {
250  // For tasks, there should always be three parameters: the
251  // pointer to the structure that holds all of the arguments, the
252  // thread index, and the thread count variables.
253  llvm::Function::arg_iterator argIter = function->arg_begin();
254 #if ISPC_LLVM_VERSION <= ISPC_LLVM_3_7 /* 3.2, 3.3, 3.4, 3.5, 3.6, 3.7 */
255  llvm::Value *structParamPtr = argIter++;
256  llvm::Value *threadIndex = argIter++;
257  llvm::Value *threadCount = argIter++;
258  llvm::Value *taskIndex = argIter++;
259  llvm::Value *taskCount = argIter++;
260  llvm::Value *taskIndex0 = argIter++;
261  llvm::Value *taskIndex1 = argIter++;
262  llvm::Value *taskIndex2 = argIter++;
263  llvm::Value *taskCount0 = argIter++;
264  llvm::Value *taskCount1 = argIter++;
265  llvm::Value *taskCount2 = argIter++;
266 #else /* LLVM 3.8+ */
267  llvm::Value *structParamPtr = &*(argIter++);
268  llvm::Value *threadIndex = &*(argIter++);
269  llvm::Value *threadCount = &*(argIter++);
270  llvm::Value *taskIndex = &*(argIter++);
271  llvm::Value *taskCount = &*(argIter++);
272  llvm::Value *taskIndex0 = &*(argIter++);
273  llvm::Value *taskIndex1 = &*(argIter++);
274  llvm::Value *taskIndex2 = &*(argIter++);
275  llvm::Value *taskCount0 = &*(argIter++);
276  llvm::Value *taskCount1 = &*(argIter++);
277  llvm::Value *taskCount2 = &*(argIter++);
278 #endif
279  // Copy the function parameter values from the structure into local
280  // storage
281  for (unsigned int i = 0; i < args.size(); ++i)
282  lCopyInTaskParameter(i, structParamPtr, args, ctx);
283 
284  if (type->isUnmasked == false) {
285  // Copy in the mask as well.
286  int nArgs = (int)args.size();
287  // The mask is the last parameter in the argument structure
288  llvm::Value *ptr = ctx->AddElementOffset(structParamPtr, nArgs, NULL, "task_struct_mask");
289  llvm::Value *ptrval = ctx->LoadInst(ptr, "mask");
290  ctx->SetFunctionMask(ptrval);
291  }
292 
293  // Copy threadIndex and threadCount into stack-allocated storage so
294  // that their symbols point to something reasonable.
296  ctx->StoreInst(threadIndex, threadIndexSym->storagePtr);
297 
299  ctx->StoreInst(threadCount, threadCountSym->storagePtr);
300 
301  // Copy taskIndex and taskCount into stack-allocated storage so
302  // that their symbols point to something reasonable.
304  ctx->StoreInst(taskIndex, taskIndexSym->storagePtr);
305 
307  ctx->StoreInst(taskCount, taskCountSym->storagePtr);
308 
310  ctx->StoreInst(taskIndex0, taskIndexSym0->storagePtr);
312  ctx->StoreInst(taskIndex1, taskIndexSym1->storagePtr);
314  ctx->StoreInst(taskIndex2, taskIndexSym2->storagePtr);
315 
317  ctx->StoreInst(taskCount0, taskCountSym0->storagePtr);
319  ctx->StoreInst(taskCount1, taskCountSym1->storagePtr);
321  ctx->StoreInst(taskCount2, taskCountSym2->storagePtr);
322  } else {
323  // Regular, non-task function
324  llvm::Function::arg_iterator argIter = function->arg_begin();
325  for (unsigned int i = 0; i < args.size(); ++i, ++argIter) {
326  Symbol *sym = args[i];
327  if (sym == NULL)
328  // anonymous function parameter
329  continue;
330 
331  argIter->setName(sym->name.c_str());
332 
333  // Allocate stack storage for the parameter and emit code
334  // to store the its value there.
335  sym->storagePtr = ctx->AllocaInst(argIter->getType(), sym->name.c_str());
336 #if ISPC_LLVM_VERSION <= ISPC_LLVM_3_7 /* 3.2, 3.3, 3.4, 3.5, 3.6, 3.7 */
337  ctx->StoreInst(argIter, sym->storagePtr);
338 #else /* LLVM 3.8+ */
339  ctx->StoreInst(&*argIter, sym->storagePtr);
340 #endif
341  ctx->EmitFunctionParameterDebugInfo(sym, i);
342  }
343 
344  // If the number of actual function arguments is equal to the
345  // number of declared arguments in decl->functionParams, then we
346  // don't have a mask parameter, so set it to be all on. This
347  // happens for exmaple with 'export'ed functions that the app
348  // calls.
349  if (argIter == function->arg_end()) {
350  Assert(type->isUnmasked || type->isExported);
352  } else {
353  Assert(type->isUnmasked == false);
354 
355  // Otherwise use the mask to set the entry mask value
356  argIter->setName("__mask");
357  Assert(argIter->getType() == LLVMTypes::MaskType);
358 #if ISPC_LLVM_VERSION <= ISPC_LLVM_3_7 /* 3.2, 3.3, 3.4, 3.5, 3.6, 3.7 */
359  ctx->SetFunctionMask(argIter);
360 #else /* LLVM 3.8+ */
361  ctx->SetFunctionMask(&*argIter);
362 #endif
363  Assert(++argIter == function->arg_end());
364  }
365 #ifdef ISPC_NVPTX_ENABLED
366  if (type->isTask == true && g->target->getISA() == Target::NVPTX) {
367  llvm::NamedMDNode *annotations = m->module->getOrInsertNamedMetadata("nvvm.annotations");
368 #if ISPC_LLVM_VERSION >= ISPC_LLVM_3_6 // LLVM 3.6+
369  llvm::SmallVector<llvm::Metadata *, 3> av;
370  av.push_back(llvm::ValueAsMetadata::get(function));
371  av.push_back(llvm::MDString::get(*g->ctx, "kernel"));
372  av.push_back(llvm::ConstantAsMetadata::get(LLVMInt32(1)));
373  annotations->addOperand(llvm::MDNode::get(*g->ctx, llvm::ArrayRef<llvm::Metadata *>(av)));
374 #else
375  llvm::SmallVector<llvm::Value *, 3> av;
376  av.push_back(function);
377  av.push_back(llvm::MDString::get(*g->ctx, "kernel"));
378  av.push_back(LLVMInt32(1));
379  annotations->addOperand(llvm::MDNode::get(*g->ctx, av));
380 #endif
381  }
382 #endif /* ISPC_NVPTX_ENABLED */
383  }
384 
385  // Finally, we can generate code for the function
386  if (code != NULL) {
387  ctx->SetDebugPos(code->pos);
388  ctx->AddInstrumentationPoint("function entry");
389 
390  int costEstimate = EstimateCost(code);
391  Debug(code->pos, "Estimated cost for function \"%s\" = %d\n", sym->name.c_str(), costEstimate);
392 
393  // If the body of the function is non-trivial, then we wrap the
394  // entire thing inside code that tests to see if the mask is all
395  // on, all off, or mixed. If this is a simple function, then this
396  // isn't worth the code bloat / overhead.
397  bool checkMask = (type->isTask == true) ||
398  (
399 #if ISPC_LLVM_VERSION == ISPC_LLVM_3_2 // 3.2
400  (function->getFnAttributes().hasAttribute(llvm::Attributes::AlwaysInline) == false)
401 #elif ISPC_LLVM_VERSION <= ISPC_LLVM_4_0
402  (function->getAttributes().getFnAttributes().hasAttribute(
403  llvm::AttributeSet::FunctionIndex, llvm::Attribute::AlwaysInline) == false)
404 #else // LLVM 5.0+
405  (function->getAttributes().getFnAttributes().hasAttribute(llvm::Attribute::AlwaysInline) ==
406  false)
407 #endif
408  && costEstimate > CHECK_MASK_AT_FUNCTION_START_COST);
409  checkMask &= (type->isUnmasked == false);
410  checkMask &= (g->target->getMaskingIsFree() == false);
411  checkMask &= (g->opt.disableCoherentControlFlow == false);
412 
413  if (checkMask) {
414  llvm::Value *mask = ctx->GetFunctionMask();
415  llvm::Value *allOn = ctx->All(mask);
416  llvm::BasicBlock *bbAllOn = ctx->CreateBasicBlock("all_on");
417  llvm::BasicBlock *bbSomeOn = ctx->CreateBasicBlock("some_on");
418 
419  // Set up basic blocks for goto targets
420  ctx->InitializeLabelMap(code);
421 
422  ctx->BranchInst(bbAllOn, bbSomeOn, allOn);
423  // all on: we've determined dynamically that the mask is all
424  // on. Set the current mask to "all on" explicitly so that
425  // codegen for this path can be improved with this knowledge in
426  // hand...
427  ctx->SetCurrentBasicBlock(bbAllOn);
430  code->EmitCode(ctx);
431  if (ctx->GetCurrentBasicBlock())
432  ctx->ReturnInst();
433 
434  // not all on: however, at least one lane must be running,
435  // since we should never run with all off... some on: reset
436  // the mask to the value it had at function entry and emit the
437  // code. Resetting the mask here is important, due to the "all
438  // on" setting of it for the path above.
439  ctx->SetCurrentBasicBlock(bbSomeOn);
440  ctx->SetFunctionMask(mask);
441 
442  // Set up basic blocks for goto targets again; we want to have
443  // one set of them for gotos in the 'all on' case, and a
444  // distinct set for the 'mixed mask' case.
445  ctx->InitializeLabelMap(code);
446 
447  code->EmitCode(ctx);
448  if (ctx->GetCurrentBasicBlock())
449  ctx->ReturnInst();
450  } else {
451  // Set up basic blocks for goto targets
452  ctx->InitializeLabelMap(code);
453  // No check, just emit the code
454  code->EmitCode(ctx);
455  }
456  }
457 
458  if (ctx->GetCurrentBasicBlock()) {
459  // FIXME: We'd like to issue a warning if we've reached the end of
460  // the function without a return statement (for non-void
461  // functions). But the test below isn't right, since we can have
462  // (with 'x' a varying test) "if (x) return a; else return b;", in
463  // which case we have a valid basic block but its unreachable so ok
464  // to not have return statement.
465 #if 0
466  // If the bblock has no predecessors, then it doesn't matter if it
467  // doesn't have a return; it'll never be reached. If it does,
468  // issue a warning. Also need to warn if it's the entry block for
469  // the function (in which case it will not have predeccesors but is
470  // still reachable.)
471  if (type->GetReturnType()->IsVoidType() == false &&
472  (pred_begin(ec.bblock) != pred_end(ec.bblock) || (ec.bblock == entryBBlock)))
473  Warning(sym->pos, "Missing return statement in function returning \"%s\".",
474  type->rType->GetString().c_str());
475 #endif
476 
477  // FIXME: would like to set the context's current position to
478  // e.g. the end of the function code
479 
480  // if bblock is non-NULL, it hasn't been terminated by e.g. a
481  // return instruction. Need to add a return instruction.
482  ctx->ReturnInst();
483  }
484 }
485 
487  if (sym == NULL)
488  // May be NULL due to error earlier in compilation
489  return;
490 
491  llvm::Function *function = sym->function;
492  Assert(function != NULL);
493 
494  // But if that function has a definition, we don't want to redefine it.
495  if (function->empty() == false) {
496  Error(sym->pos, "Ignoring redefinition of function \"%s\".", sym->name.c_str());
497  return;
498  }
499 
500  // If function is an 'extern C', it cannot be defined in ISPC.
501  const FunctionType *type = CastType<FunctionType>(sym->type);
502  Assert(type != NULL);
503  if (type->isExternC) {
504  Error(sym->pos, "\n\'extern \"C\"\' function \"%s\" cannot be defined in ISPC.", sym->name.c_str());
505  return;
506  }
507 
508  // Figure out a reasonable source file position for the start of the
509  // function body. If possible, get the position of the first actual
510  // non-StmtList statment...
511  SourcePos firstStmtPos = sym->pos;
512  if (code) {
513  StmtList *sl = llvm::dyn_cast<StmtList>(code);
514  if (sl && sl->stmts.size() > 0 && sl->stmts[0] != NULL)
515  firstStmtPos = sl->stmts[0]->pos;
516  else
517  firstStmtPos = code->pos;
518  }
519 
520  // And we can now go ahead and emit the code
521  {
522  FunctionEmitContext ec(this, sym, function, firstStmtPos);
523  emitCode(&ec, function, firstStmtPos);
524  }
525 
526  if (m->errorCount == 0) {
527  // If the function is 'export'-qualified, emit a second version of
528  // it without a mask parameter and without name mangling so that
529  // the application can call it
530  if (type->isExported) {
531  if (!type->isTask) {
532  llvm::FunctionType *ftype = type->LLVMFunctionType(g->ctx, true);
533  llvm::GlobalValue::LinkageTypes linkage = llvm::GlobalValue::ExternalLinkage;
534  std::string functionName = sym->name;
536  // If we treat generic as smth, we should have appropriate mangling
537  if (g->target->getISA() == Target::GENERIC && !g->target->getTreatGenericAsSmth().empty())
538  functionName += std::string("_") + g->target->getTreatGenericAsSmth();
539  else
540  functionName += std::string("_") + g->target->GetISAString();
541  }
542 #ifdef ISPC_NVPTX_ENABLED
543  if (g->target->getISA() == Target::NVPTX) {
544  functionName +=
545  std::string("___export"); /* add ___export to the end, for ptxcc to recognize it is exported */
546 #if 0
547  llvm::NamedMDNode* annotations =
548  m->module->getOrInsertNamedMetadata("nvvm.annotations");
549  llvm::SmallVector<llvm::Value*, 3> av;
550  av.push_back(function);
551  av.push_back(llvm::MDString::get(*g->ctx, "kernel"));
552  av.push_back(llvm::ConstantInt::get(llvm::IntegerType::get(*g->ctx,32), 1));
553  annotations->addOperand(llvm::MDNode::get(*g->ctx, av));
554 #endif
555  }
556 #endif /* ISPC_NVPTX_ENABLED */
557  llvm::Function *appFunction = llvm::Function::Create(ftype, linkage, functionName.c_str(), m->module);
558  appFunction->setDoesNotThrow();
559 
560 #if ISPC_LLVM_VERSION < ISPC_LLVM_5_0
561  // We should iterate from 1 because zero parameter is return.
562  // We should iterate till getNumParams instead of getNumParams+1 because new
563  // function is export function and doesn't contain the last parameter "mask".
564  for (int i = 1; i < function->getFunctionType()->getNumParams(); i++) {
565  if (function->doesNotAlias(i)) {
566  appFunction->setDoesNotAlias(i);
567  }
568  }
569 #else // LLVM 5.0+
570  for (int i = 0; i < function->getFunctionType()->getNumParams() - 1; i++) {
571  if (function->hasParamAttribute(i, llvm::Attribute::NoAlias)) {
572  appFunction->addParamAttr(i, llvm::Attribute::NoAlias);
573  }
574  }
575 #endif
576  g->target->markFuncWithTargetAttr(appFunction);
577 
578  if (appFunction->getName() != functionName) {
579  // this was a redefinition for which we already emitted an
580  // error, so don't worry about this one...
581  appFunction->eraseFromParent();
582  } else {
583  // And emit the code again
584  FunctionEmitContext ec(this, sym, appFunction, firstStmtPos);
585  emitCode(&ec, appFunction, firstStmtPos);
586  if (m->errorCount == 0) {
587  sym->exportedFunction = appFunction;
588  }
589 #ifdef ISPC_NVPTX_ENABLED
590  if (g->target->getISA() == Target::NVPTX) {
591  llvm::NamedMDNode *annotations = m->module->getOrInsertNamedMetadata("nvvm.annotations");
592 #if ISPC_LLVM_VERSION >= ISPC_LLVM_3_6 // LLVM 3.6+
593 
594  llvm::SmallVector<llvm::Metadata *, 3> av;
595  av.push_back(llvm::ValueAsMetadata::get(appFunction));
596  av.push_back(llvm::MDString::get(*g->ctx, "kernel"));
597  av.push_back(llvm::ConstantAsMetadata::get(
598  llvm::ConstantInt::get(llvm::IntegerType::get(*g->ctx, 32), 1)));
599  annotations->addOperand(llvm::MDNode::get(*g->ctx, llvm::ArrayRef<llvm::Metadata *>(av)));
600 #else
601  llvm::SmallVector<llvm::Value *, 3> av;
602  av.push_back(appFunction);
603  av.push_back(llvm::MDString::get(*g->ctx, "kernel"));
604  av.push_back(llvm::ConstantInt::get(llvm::IntegerType::get(*g->ctx, 32), 1));
605  annotations->addOperand(llvm::MDNode::get(*g->ctx, av));
606 #endif
607  }
608 #endif /* ISPC_NVPTX_ENABLED */
609  }
610  }
611  }
612  }
613 }
llvm::Value * storagePtr
Definition: sym.h:71
llvm::Constant * LLVMMaskAllOn
Definition: llvmutil.cpp:92
llvm::Function * function
Definition: sym.h:75
void InitializeLabelMap(Stmt *code)
Definition: ctx.cpp:1095
llvm::Value * AddElementOffset(llvm::Value *basePtr, int elementNum, const Type *ptrType, const char *name=NULL, const PointerType **resultPtrType=NULL)
Definition: ctx.cpp:2179
Opt opt
Definition: ispc.h:542
const Type * GetReturnType() const
Definition: type.h:896
Declaration of the FunctionEmitContext class
void EmitVariableDebugInfo(Symbol *sym)
Definition: ctx.cpp:1506
Symbol * taskIndexSym
Definition: func.h:62
Symbol * threadIndexSym
Definition: func.h:61
void BranchInst(llvm::BasicBlock *block)
Definition: ctx.cpp:2961
std::string getTreatGenericAsSmth() const
Definition: ispc.h:265
Module * m
Definition: ispc.cpp:102
Interface class for statements in the ispc language.
Definition: stmt.h:49
Target * target
Definition: ispc.h:544
llvm::Value * LoadInst(llvm::Value *ptr, llvm::Value *mask, const Type *ptrType, const char *name=NULL, bool one_elem=false)
Definition: ctx.cpp:2367
const std::string & GetParameterName(int i) const
Definition: type.cpp:2817
void emitCode(FunctionEmitContext *ctx, llvm::Function *function, SourcePos firstStmtPos)
Definition: func.cpp:226
Symbol * maskSymbol
Definition: func.h:60
llvm::Value * AllocaInst(llvm::Type *llvmType, const char *name=NULL, int align=0, bool atEntryBlock=true)
Definition: ctx.cpp:2579
bool getMaskingIsFree() const
Definition: ispc.h:283
bool NoOmitFramePointer
Definition: ispc.h:574
std::vector< Symbol * > args
Definition: func.h:58
Symbol * taskIndexSym2
Definition: func.h:65
void AddInstrumentationPoint(const char *note)
Definition: ctx.cpp:1413
int GetNumParameters() const
Definition: type.h:906
std::string name
Definition: sym.h:70
Symbol * LookupVariable(const char *name)
Definition: sym.cpp:112
llvm::BasicBlock * GetCurrentBasicBlock()
Definition: ctx.cpp:423
#define Assert(expr)
Definition: ispc.h:163
virtual void EmitCode(FunctionEmitContext *ctx) const =0
llvm::BasicBlock * CreateBasicBlock(const char *name)
Definition: ctx.cpp:1368
header file with declarations for symbol and symbol table classes.
bool disableMaskAllOnOptimizations
Definition: ispc.h:471
ASTNode * Optimize(ASTNode *root)
Definition: ast.cpp:234
llvm::ConstantInt * LLVMInt32(int32_t i)
Definition: llvmutil.cpp:228
void StoreInst(llvm::Value *value, llvm::Value *ptr)
Definition: ctx.cpp:2827
llvm::Module * module
Definition: module.h:156
ASTNode * TypeCheck(ASTNode *root)
Definition: ast.cpp:242
File with declarations for classes related to statements in the language.
Symbol * taskCountSym0
Definition: func.h:63
Globals * g
Definition: ispc.cpp:101
bool debugPrint
Definition: ispc.h:568
llvm::Value * GetFunctionMask()
Definition: ctx.cpp:427
bool disableCoherentControlFlow
Definition: ispc.h:493
Symbol * taskIndexSym1
Definition: func.h:64
const bool isExternC
Definition: type.h:922
Symbol * taskCountSym2
Definition: func.h:65
void Error(SourcePos p, const char *format,...) PRINTF_FUNC
Definition: util.cpp:351
const FunctionType * GetType() const
Definition: func.cpp:179
bool mangleFunctionsWithTarget
Definition: ispc.h:634
Header file with declarations for various LLVM utility stuff.
Stmt * code
Definition: func.h:59
SourcePos pos
Definition: sym.h:69
Symbol * taskCountSym
Definition: func.h:62
Function(Symbol *sym, Stmt *code)
Definition: func.cpp:92
Representation of a range of positions in a source file.
Definition: ispc.h:131
Symbol * taskCountSym1
Definition: func.h:64
void markFuncWithTargetAttr(llvm::Function *func)
Definition: ispc.cpp:1534
SourcePos pos
Definition: ast.h:77
Symbol * taskIndexSym0
Definition: func.h:63
void Warning(SourcePos p, const char *format,...) PRINTF_FUNC
Definition: util.cpp:375
bool IsVoidType() const
Definition: type.cpp:207
static llvm::Type * Int32Type
Definition: llvmutil.h:77
void SetDebugPos(SourcePos pos)
Definition: ctx.cpp:1432
Representation of a function in a source file.
Symbol * sym
Definition: func.h:57
const bool isTask
Definition: type.h:914
void GenerateIR()
Definition: func.cpp:486
llvm::Value * GetFullMaskPointer()
Definition: ctx.cpp:435
ISA getISA() const
Definition: ispc.h:263
const Type * GetParameterType(int i) const
Definition: type.cpp:2802
const char * GetISAString() const
Definition: ispc.cpp:1402
Type representing a function (return type + argument types)
Definition: type.h:858
Representation of a program symbol.
Definition: sym.h:63
Interface class that defines the type abstraction.
Definition: type.h:95
std::vector< Stmt * > stmts
Definition: stmt.h:459
Expr abstract base class and expression implementations.
void SetCurrentBasicBlock(llvm::BasicBlock *bblock)
Definition: ctx.cpp:425
static llvm::VectorType * MaskType
Definition: llvmutil.h:89
const bool isUnmasked
Definition: type.h:927
int EstimateCost(ASTNode *root)
Definition: ast.cpp:271
static void lCopyInTaskParameter(int i, llvm::Value *structArgPtr, const std::vector< Symbol *> &args, FunctionEmitContext *ctx)
Definition: func.cpp:190
void EmitFunctionParameterDebugInfo(Symbol *sym, int parameterNum)
Definition: ctx.cpp:1545
const Function * parentFunction
Definition: sym.h:103
Representation of a list of statements in the program.
Definition: stmt.h:441
llvm::Value * All(llvm::Value *mask)
Definition: ctx.cpp:1202
virtual void Print(int indent) const =0
const Type * GetReturnType() const
Definition: func.cpp:173
const bool isExported
Definition: type.h:918
Declaration of the Module class, which is the ispc-side representation of the results of compiling a ...
int errorCount
Definition: module.h:149
llvm::LLVMContext * ctx
Definition: ispc.h:645
const Type * type
Definition: sym.h:83
std::string GetString() const
Definition: type.cpp:2568
Symbol * threadCountSym
Definition: func.h:61
void Debug(SourcePos p, const char *format,...) PRINTF_FUNC
Definition: util.cpp:363
llvm::Instruction * ReturnInst()
Definition: ctx.cpp:3283
void SetFunctionMask(llvm::Value *val)
Definition: ctx.cpp:437
SymbolTable * symbolTable
Definition: module.h:153
llvm::Function * exportedFunction
Definition: sym.h:78
File with declarations for classes related to type representation.
llvm::FunctionType * LLVMFunctionType(llvm::LLVMContext *ctx, bool disableMask=false) const
Definition: type.cpp:2738