Improvements to mask management code; removes a number of unnecessary blends.
We now maintain a the distinction between the value of the mask passed into a function and the "internal" mask within the function that only accounts for varying control flow within the function. The full mask (the AND of the function mask and the internal mask) must be used for assignments to static and global variables, and reference function parameters. Further, it is the appropriate mask to use for making decisions about varying control flow. However, we can use the internal mask for assignments to variables declared in the current function (including the return value and non-reference parameters to the function). Doing so allows us to catch a few more cases where the internal mask is all on, even if the mask coming into the function wasn't all on, and thence use moves rather than blends for those assignments. (Which in turn can allow additional optimizations to happen.) Fixes issue #23.
This commit is contained in:
11
func.cpp
11
func.cpp
@@ -104,7 +104,10 @@ Function::Function(DeclSpecs *ds, Declarator *decl, Stmt *c) {
|
||||
for (unsigned int i = 0; i < decl->functionArgs->size(); ++i) {
|
||||
Declaration *pdecl = (*decl->functionArgs)[i];
|
||||
assert(pdecl->declarators.size() == 1);
|
||||
args.push_back(pdecl->declarators[0]->sym);
|
||||
Symbol *sym = pdecl->declarators[0]->sym;
|
||||
if (dynamic_cast<const ReferenceType *>(sym->type) == NULL)
|
||||
sym->parentFunction = this;
|
||||
args.push_back(sym);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -462,7 +465,7 @@ Function::emitCode(FunctionEmitContext *ctx, llvm::Function *function,
|
||||
llvm::Value *ptr = ctx->GetElementPtrInst(structParamPtr, 0, nArgs,
|
||||
"task_struct_mask");
|
||||
llvm::Value *ptrval = ctx->LoadInst(ptr, NULL, "mask");
|
||||
ctx->SetEntryMask(ptrval);
|
||||
ctx->SetFunctionMask(ptrval);
|
||||
|
||||
// Copy threadIndex and threadCount into stack-allocated storage so
|
||||
// that their symbols point to something reasonable.
|
||||
@@ -500,12 +503,12 @@ Function::emitCode(FunctionEmitContext *ctx, llvm::Function *function,
|
||||
// happens for exmaple with 'export'ed functions that the app
|
||||
// calls.
|
||||
if (argIter == function->arg_end())
|
||||
ctx->SetEntryMask(LLVMMaskAllOn);
|
||||
ctx->SetFunctionMask(LLVMMaskAllOn);
|
||||
else {
|
||||
// Otherwise use the mask to set the entry mask value
|
||||
argIter->setName("__mask");
|
||||
assert(argIter->getType() == LLVMTypes::MaskType);
|
||||
ctx->SetEntryMask(argIter);
|
||||
ctx->SetFunctionMask(argIter);
|
||||
assert(++argIter == function->arg_end());
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user