summaryrefslogtreecommitdiffstats
path: root/source/slang/slang-emit-cpp.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'source/slang/slang-emit-cpp.cpp')
-rw-r--r--source/slang/slang-emit-cpp.cpp93
1 files changed, 49 insertions, 44 deletions
diff --git a/source/slang/slang-emit-cpp.cpp b/source/slang/slang-emit-cpp.cpp
index 7f743d9e0..6b7fc46bf 100644
--- a/source/slang/slang-emit-cpp.cpp
+++ b/source/slang/slang-emit-cpp.cpp
@@ -398,10 +398,7 @@ SlangResult CPPSourceEmitter::calcTypeName(IRType* type, CodeGenTarget target, S
{
auto ptrType = static_cast<IRPtrType*>(type);
SLANG_RETURN_ON_FAIL(calcTypeName(ptrType->getValueType(), target, out));
- // TODO(JS): It seems although it says it is a pointer, it can actually be output as a reference
- // not clear where the ptr aspect is there, as in the definition it is just 'out', implying out
- // is somewhere converted to a ptr?
- out << "&";
+ out << "*";
return SLANG_OK;
}
case kIROp_RefType:
@@ -577,14 +574,6 @@ SlangResult CPPSourceEmitter::calcTypeName(IRType* type, CodeGenTarget target, S
void CPPSourceEmitter::useType(IRType* type)
{
- if (type->op == kIROp_PtrType)
- {
- // TODO(JS):
- // If it's a pointer type we ignore. We may want to strip but in practice it's
- // probably not necessary.
- return;
- }
-
_getTypeName(type);
}
@@ -934,22 +923,26 @@ void CPPSourceEmitter::_emitGetAtDefinition(const UnownedStringSlice& funcName,
IRType* srcType = funcType->getParamType(0);
- for (Index i = 0; i < 2; ++i)
+ for (Index i = 0; i < 3; ++i)
{
UnownedStringSlice typePrefix = (i == 0) ? UnownedStringSlice::fromLiteral("const ") : UnownedStringSlice();
+ bool lValue = (i != 2);
emitFunctionPreambleImpl(nullptr);
writer->emit(typePrefix);
emitType(specOp->returnType);
- m_writer->emit("& ");
-
+ if (lValue)
+ m_writer->emit("*");
+ writer->emit(" ");
writer->emit(funcName);
writer->emit("(");
writer->emit(typePrefix);
emitType(funcType->getParamType(0));
- writer->emit("& a, ");
+ if (lValue)
+ writer->emit("*");
+ writer->emit(" a, ");
emitType(funcType->getParamType(1));
writer->emit(" b)\n{\n");
@@ -962,8 +955,10 @@ void CPPSourceEmitter::_emitGetAtDefinition(const UnownedStringSlice& funcName,
writer->emit("assert(b >= 0 && b < ");
writer->emit(vecSize);
writer->emit(");\n");
-
- writer->emit("return (&a.x)[b];\n");
+ if (lValue)
+ writer->emit("return (&a->x) + b;\n");
+ else
+ writer->emit("return (&a.x)[b];\n");
}
else if (auto matrixType = as<IRMatrixType>(srcType))
{
@@ -974,7 +969,10 @@ void CPPSourceEmitter::_emitGetAtDefinition(const UnownedStringSlice& funcName,
writer->emit(rowCount);
writer->emit(");\n");
- writer->emit("return a.rows[b];\n");
+ if (lValue)
+ writer->emit("return &(a->rows[b]);\n");
+ else
+ writer->emit("return a.rows[b];\n");
}
writer->dedent();
@@ -1566,7 +1564,7 @@ void CPPSourceEmitter::_emitInOutParamType(IRType* type, String const& name, IRT
UnownedStringSlice slice = _getTypeName(valueType);
m_writer->emit(slice);
- m_writer->emit("& ");
+ m_writer->emit("* ");
m_writer->emitName(nameAndLoc);
}
@@ -2095,21 +2093,39 @@ void CPPSourceEmitter::emitIntrinsicCallExprImpl(
else
{
// The user is invoking a built-in subscript operator
- auto prec = getInfo(EmitOp::Postfix);
- needClose = maybeEmitParens(outerPrec, prec);
- emitOperand(args[0].get(), leftSide(outerPrec, prec));
- m_writer->emit("[");
- emitOperand(args[1].get(), getInfo(EmitOp::General));
- m_writer->emit("]");
+ // Determine if we are calling the `ref` accessor:
+ // `ref` accessor returns a pointer of element type.
+ auto ptrType = as<IRPtrType>(inst->getFullType());
+ auto resourceType = inst->getOperand(1)->getFullType();
+ auto elementType = resourceType ? resourceType->getOperand(0) : nullptr;
+ bool isRef = ptrType && ptrType->getValueType() == elementType;
+ auto emitSubscript = [this, &args](EmitOpInfo _outerPrec)
+ {
+ auto prec = getInfo(EmitOp::Postfix);
+ bool needCloseSubscript = maybeEmitParens(_outerPrec, prec);
+ emitOperand(args[0].get(), leftSide(_outerPrec, prec));
+ m_writer->emit("[");
+ emitOperand(args[1].get(), getInfo(EmitOp::General));
+ m_writer->emit("]");
+ maybeCloseParens(needCloseSubscript);
+ };
+
+ if (isRef)
+ {
+ auto prefixPrec = getInfo(EmitOp::Prefix);
+ needClose = maybeEmitParens(outerPrec, prefixPrec);
+ m_writer->emit("&");
+ outerPrec = rightSide(outerPrec, prefixPrec);
+ }
+ emitSubscript(outerPrec);
+ maybeCloseParens(needClose);
if (argCount == 3)
{
m_writer->emit(" = ");
emitOperand(args[2].get(), getInfo(EmitOp::General));
}
-
- maybeCloseParens(needClose);
}
return;
@@ -2358,19 +2374,6 @@ void CPPSourceEmitter::emitOperandImpl(IRInst* inst, EmitOpInfo const& outerPre
{
// It's in UniformState
m_writer->emit("(");
-
- switch (inst->getDataType()->op)
- {
- case kIROp_ParameterBlockType:
- case kIROp_ConstantBufferType:
- case kIROp_StructType:
- {
- m_writer->emit("*");
- break;
- }
- default: break;
- }
-
m_writer->emit("uniformState->");
m_writer->emit(name);
m_writer->emit(")");
@@ -2408,12 +2411,14 @@ void CPPSourceEmitter::emitOperandImpl(IRInst* inst, EmitOpInfo const& outerPre
}
}
}
-
- ; // Fall-thru
+ m_writer->emit(getName(inst));
+ break;
}
+ case kIROp_Var:
case kIROp_GlobalVar:
+ emitVarExpr(inst, outerPrec);
+ break;
default:
- // GlobalVar should be fine as should just be a member of Context
m_writer->emit(getName(inst));
break;
}