| 592 | } |
| 593 | |
| 594 | bool Module::addFunction ( const FunctionPtr & fn, bool canFail ) { |
| 595 | fn->module = this; |
| 596 | auto mangledName = fn->getMangledName(); |
| 597 | fn->module = nullptr; |
| 598 | if ( fn->builtIn && fn->arguments.size()>DAS_MAX_FUNCTION_ARGUMENTS ) { |
| 599 | DAS_FATAL_ERROR("can't add function %s to module %s, too many arguments, DAS_MAX_FUNCTION_ARGUMENTS=%i\n", mangledName.c_str(), name.c_str(), DAS_MAX_FUNCTION_ARGUMENTS ); |
| 600 | } |
| 601 | if ( fn->builtIn && fn->sideEffectFlags==uint32_t(SideEffects::none) && fn->result->isVoid() ) { |
| 602 | DAS_FATAL_ERROR("can't add function %s to module %s; it has no side effects and no return type\n", mangledName.c_str(), name.c_str() ); |
| 603 | } |
| 604 | if ( fn->result && !fn->result->ref && fn->result->isWorkhorseType() && !fn->result->isPointer() ) { |
| 605 | fn->result->constant = true; |
| 606 | } |
| 607 | if ( fn->builtIn ) { |
| 608 | cumulativeHash = wyhash(mangledName.c_str(), mangledName.size(), cumulativeHash); |
| 609 | } |
| 610 | if ( fn->builtIn && fn->sideEffectFlags==uint32_t(SideEffects::modifyArgument) ) { |
| 611 | bool anyRW = false; |
| 612 | for ( const auto & arg : fn->arguments ) { |
| 613 | if ( arg->type->isRef() && !arg->type->isConst() ) { |
| 614 | anyRW = true; |
| 615 | } else if ( arg->type->isPointer() && arg->type->firstType && !arg->type->firstType->isConst() ) { |
| 616 | anyRW = true; |
| 617 | } |
| 618 | } |
| 619 | if ( !anyRW ) { |
| 620 | DAS_FATAL_ERROR("can't add function %s to module %s; modify argument requires non-const ref argument\n", mangledName.c_str(), name.c_str() ); |
| 621 | } |
| 622 | } |
| 623 | if ( functions.insert(mangledName, fn) ) { |
| 624 | functionsByName[hash64z(fn->name.c_str())].push_back(fn); |
| 625 | fn->module = this; |
| 626 | return true; |
| 627 | } else { |
| 628 | if ( !canFail ) { |
| 629 | DAS_FATAL_ERROR("can't add duplicate function %s to module %s\n", mangledName.c_str(), name.c_str() ); |
| 630 | } |
| 631 | return false; |
| 632 | } |
| 633 | } |
| 634 | |
| 635 | bool Module::replaceFunction ( const FunctionPtr & fn ) { |
| 636 | fn->module = this; |
no test coverage detected