@@ -116,6 +116,10 @@ struct SharedEmitContext
116
116
117
117
// Map used to tell AST lowering what decls are represented by IR.
118
118
HashSet<Decl*>* irDeclSetForAST = nullptr ;
119
+
120
+ // Are we doing IR-only emit, so that everything should get
121
+ // its mangled name?
122
+ bool isFullIRMode = false ;
119
123
};
120
124
121
125
struct EmitContext
@@ -2996,10 +3000,21 @@ struct EmitVisitor
2996
3000
}
2997
3001
}
2998
3002
3003
+ bool isBuiltinDecl (Decl* decl)
3004
+ {
3005
+ for (auto dd = decl; dd; dd = dd->ParentDecl )
3006
+ {
3007
+ if (dd->FindModifier <FromStdLibModifier>())
3008
+ return true ;
3009
+ }
3010
+ return false ;
3011
+ }
3012
+
2999
3013
void EmitDeclRef (DeclRef<Decl> declRef)
3000
3014
{
3001
3015
// Are we emitting an AST in a context where some declarations
3002
3016
// are actually stored as IR code?
3017
+
3003
3018
if (auto irDeclSet = context->shared ->irDeclSetForAST )
3004
3019
{
3005
3020
Decl* decl = declRef.getDecl ();
@@ -3010,6 +3025,17 @@ struct EmitVisitor
3010
3025
}
3011
3026
}
3012
3027
3028
+ if (context->shared ->isFullIRMode )
3029
+ {
3030
+ // Don't apply this to builting declarations
3031
+ if (!isBuiltinDecl (declRef.getDecl ()))
3032
+ {
3033
+ emit (getIRName (declRef));
3034
+ return ;
3035
+ }
3036
+ }
3037
+
3038
+
3013
3039
3014
3040
// TODO: need to qualify a declaration name based on parent scopes/declarations
3015
3041
@@ -4453,26 +4479,34 @@ emitDeclImpl(decl, nullptr);
4453
4479
4454
4480
String getIRName (DeclRefBase const & declRef)
4455
4481
{
4456
- // It is a bit ugly, but we need a deterministic way
4457
- // to get a name for things when emitting from the IR
4458
- // that won't conflict with any keywords, builtins, etc.
4459
- // in the target language.
4482
+ // In general, when referring to a declaration that has been lowered
4483
+ // via the IR, we want to use its mangled name.
4484
+ //
4485
+ // There are two main exceptions to this:
4486
+ //
4487
+ // 1. For debugging, we accept the `-no-mangle` flag which basically
4488
+ // instructs us to try to use the original name of all declarations,
4489
+ // to make the output more like what is expected to come out of
4490
+ // fxc pass-through. This case should get deprecated some day.
4460
4491
//
4461
- // Eventually we should accomplish this by using
4462
- // mangled names everywhere, but that complicates things
4463
- // when we are also using direct comparison to fxc/glslang
4464
- // output for some of our tests .
4492
+ // 2. It is really annoying to have the fields of a `struct` type
4493
+ // get ridiculously lengthy mangled names, and this also messes
4494
+ // up stuff like specialization (since the mangled name of a field
4495
+ // would then include the mangled name of the outer type) .
4465
4496
//
4466
4497
4467
4498
String name;
4468
4499
if (context->shared ->entryPoint ->compileRequest ->compileFlags & SLANG_COMPILE_FLAG_NO_MANGLING)
4469
4500
{
4501
+ // Special case (1):
4470
4502
name.append (getText (declRef.GetName ()));
4503
+ return name;
4471
4504
}
4472
- else
4473
- {
4474
- name.append (getMangledName (declRef));
4475
- }
4505
+
4506
+ // Special case (2): not implemented yet.
4507
+
4508
+ // General case:
4509
+ name.append (getMangledName (declRef));
4476
4510
return name;
4477
4511
}
4478
4512
@@ -7040,6 +7074,24 @@ emitDeclImpl(decl, nullptr);
7040
7074
{}
7041
7075
}
7042
7076
7077
+ void emitIRUsedTypesForGlobalValueWithCode (
7078
+ EmitContext* ctx,
7079
+ IRGlobalValueWithCode* value)
7080
+ {
7081
+ for ( auto bb = value->getFirstBlock (); bb; bb = bb->getNextBlock () )
7082
+ {
7083
+ for ( auto pp = bb->getFirstParam (); pp; pp = pp->getNextParam () )
7084
+ {
7085
+ emitIRUsedTypesForValue (ctx, pp);
7086
+ }
7087
+
7088
+ for ( auto ii = bb->getFirstInst (); ii; ii = ii->getNextInst () )
7089
+ {
7090
+ emitIRUsedTypesForValue (ctx, ii);
7091
+ }
7092
+ }
7093
+ }
7094
+
7043
7095
void emitIRUsedTypesForValue (
7044
7096
EmitContext* ctx,
7045
7097
IRValue* value)
@@ -7050,19 +7102,23 @@ emitDeclImpl(decl, nullptr);
7050
7102
case kIROp_Func :
7051
7103
{
7052
7104
auto irFunc = (IRFunc*) value;
7105
+
7106
+ // Don't emit anything for a generic function,
7107
+ // since we only care about the types used by
7108
+ // the actual specializations.
7109
+ if (irFunc->genericDecl )
7110
+ return ;
7111
+
7053
7112
emitIRUsedType (ctx, irFunc->getResultType ());
7054
- for ( auto bb = irFunc->getFirstBlock (); bb; bb = bb->getNextBlock () )
7055
- {
7056
- for ( auto pp = bb->getFirstParam (); pp; pp = pp->getNextParam () )
7057
- {
7058
- emitIRUsedTypesForValue (ctx, pp);
7059
- }
7060
7113
7061
- for ( auto ii = bb->getFirstInst (); ii; ii = ii->getNextInst () )
7062
- {
7063
- emitIRUsedTypesForValue (ctx, ii);
7064
- }
7065
- }
7114
+ emitIRUsedTypesForGlobalValueWithCode (ctx, irFunc);
7115
+ }
7116
+ break ;
7117
+
7118
+ case kIROp_global_var :
7119
+ {
7120
+ auto irGlobal = (IRGlobalVar*) value;
7121
+ emitIRUsedTypesForGlobalValueWithCode (ctx, irGlobal);
7066
7122
}
7067
7123
break ;
7068
7124
@@ -7372,6 +7428,8 @@ String emitEntryPoint(
7372
7428
// compilation work. We thus start by cloning any code needed
7373
7429
// by the entry point over to our fresh IR module.
7374
7430
7431
+ sharedContext.isFullIRMode = true ;
7432
+
7375
7433
specializeIRForEntryPoint (
7376
7434
irSpecializationState,
7377
7435
entryPoint);
0 commit comments