@@ -158,6 +158,7 @@ import {
158
158
TernaryExpression ,
159
159
ArrayLiteralExpression ,
160
160
StringLiteralExpression ,
161
+ UnaryExpression ,
161
162
UnaryPostfixExpression ,
162
163
UnaryPrefixExpression ,
163
164
@@ -3534,7 +3535,7 @@ export class Compiler extends DiagnosticEmitter {
3534
3535
if ( classReference ) {
3535
3536
let overload = classReference . lookupOverload ( OperatorKind . LT ) ;
3536
3537
if ( overload ) {
3537
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
3538
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
3538
3539
break ;
3539
3540
}
3540
3541
}
@@ -3634,7 +3635,7 @@ export class Compiler extends DiagnosticEmitter {
3634
3635
if ( classReference ) {
3635
3636
let overload = classReference . lookupOverload ( OperatorKind . GT ) ;
3636
3637
if ( overload ) {
3637
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
3638
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
3638
3639
break ;
3639
3640
}
3640
3641
}
@@ -3734,7 +3735,7 @@ export class Compiler extends DiagnosticEmitter {
3734
3735
if ( classReference ) {
3735
3736
let overload = classReference . lookupOverload ( OperatorKind . LE ) ;
3736
3737
if ( overload ) {
3737
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
3738
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
3738
3739
break ;
3739
3740
}
3740
3741
}
@@ -3834,7 +3835,7 @@ export class Compiler extends DiagnosticEmitter {
3834
3835
if ( classReference ) {
3835
3836
let overload = classReference . lookupOverload ( OperatorKind . GE ) ;
3836
3837
if ( overload ) {
3837
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
3838
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
3838
3839
break ;
3839
3840
}
3840
3841
}
@@ -3941,7 +3942,7 @@ export class Compiler extends DiagnosticEmitter {
3941
3942
if ( classReference ) {
3942
3943
let overload = classReference . lookupOverload ( OperatorKind . EQ ) ;
3943
3944
if ( overload ) {
3944
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
3945
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
3945
3946
break ;
3946
3947
}
3947
3948
}
@@ -4038,7 +4039,7 @@ export class Compiler extends DiagnosticEmitter {
4038
4039
if ( classReference ) {
4039
4040
let overload = classReference . lookupOverload ( OperatorKind . NE ) ;
4040
4041
if ( overload ) {
4041
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
4042
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
4042
4043
break ;
4043
4044
}
4044
4045
}
@@ -4138,7 +4139,7 @@ export class Compiler extends DiagnosticEmitter {
4138
4139
if ( classReference ) {
4139
4140
let overload = classReference . lookupOverload ( OperatorKind . ADD ) ;
4140
4141
if ( overload ) {
4141
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
4142
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
4142
4143
break ;
4143
4144
}
4144
4145
}
@@ -4227,7 +4228,7 @@ export class Compiler extends DiagnosticEmitter {
4227
4228
if ( classReference ) {
4228
4229
let overload = classReference . lookupOverload ( OperatorKind . SUB ) ;
4229
4230
if ( overload ) {
4230
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
4231
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
4231
4232
break ;
4232
4233
}
4233
4234
}
@@ -4317,7 +4318,7 @@ export class Compiler extends DiagnosticEmitter {
4317
4318
if ( classReference ) {
4318
4319
let overload = classReference . lookupOverload ( OperatorKind . MUL ) ;
4319
4320
if ( overload ) {
4320
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
4321
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
4321
4322
break ;
4322
4323
}
4323
4324
}
@@ -4407,7 +4408,7 @@ export class Compiler extends DiagnosticEmitter {
4407
4408
if ( classReference ) {
4408
4409
let overload = classReference . lookupOverload ( OperatorKind . POW ) ;
4409
4410
if ( overload ) {
4410
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
4411
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
4411
4412
break ;
4412
4413
}
4413
4414
}
@@ -4504,7 +4505,7 @@ export class Compiler extends DiagnosticEmitter {
4504
4505
if ( classReference ) {
4505
4506
let overload = classReference . lookupOverload ( OperatorKind . DIV ) ;
4506
4507
if ( overload ) {
4507
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
4508
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
4508
4509
break ;
4509
4510
}
4510
4511
}
@@ -4613,7 +4614,7 @@ export class Compiler extends DiagnosticEmitter {
4613
4614
if ( classReference ) {
4614
4615
let overload = classReference . lookupOverload ( OperatorKind . REM ) ;
4615
4616
if ( overload ) {
4616
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
4617
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
4617
4618
break ;
4618
4619
}
4619
4620
}
@@ -4779,7 +4780,7 @@ export class Compiler extends DiagnosticEmitter {
4779
4780
if ( classReference ) {
4780
4781
let overload = classReference . lookupOverload ( OperatorKind . BITWISE_SHL ) ;
4781
4782
if ( overload ) {
4782
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
4783
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
4783
4784
break ;
4784
4785
}
4785
4786
}
@@ -4845,7 +4846,7 @@ export class Compiler extends DiagnosticEmitter {
4845
4846
if ( classReference ) {
4846
4847
let overload = classReference . lookupOverload ( OperatorKind . BITWISE_SHR ) ;
4847
4848
if ( overload ) {
4848
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
4849
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
4849
4850
break ;
4850
4851
}
4851
4852
}
@@ -4933,7 +4934,7 @@ export class Compiler extends DiagnosticEmitter {
4933
4934
if ( classReference ) {
4934
4935
let overload = classReference . lookupOverload ( OperatorKind . BITWISE_SHR_U ) ;
4935
4936
if ( overload ) {
4936
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
4937
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
4937
4938
break ;
4938
4939
}
4939
4940
}
@@ -5002,7 +5003,7 @@ export class Compiler extends DiagnosticEmitter {
5002
5003
if ( classReference ) {
5003
5004
let overload = classReference . lookupOverload ( OperatorKind . BITWISE_AND ) ;
5004
5005
if ( overload ) {
5005
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
5006
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
5006
5007
break ;
5007
5008
}
5008
5009
}
@@ -5092,7 +5093,7 @@ export class Compiler extends DiagnosticEmitter {
5092
5093
if ( classReference ) {
5093
5094
let overload = classReference . lookupOverload ( OperatorKind . BITWISE_OR ) ;
5094
5095
if ( overload ) {
5095
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
5096
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
5096
5097
break ;
5097
5098
}
5098
5099
}
@@ -5185,7 +5186,7 @@ export class Compiler extends DiagnosticEmitter {
5185
5186
if ( classReference ) {
5186
5187
let overload = classReference . lookupOverload ( OperatorKind . BITWISE_XOR ) ;
5187
5188
if ( overload ) {
5188
- expr = this . compileBinaryOverload ( overload , left , leftExpr , right , expression ) ;
5189
+ expr = this . compileBinaryOverload ( overload , leftExpr , leftType , right , expression ) ;
5189
5190
break ;
5190
5191
}
5191
5192
}
@@ -5505,40 +5506,34 @@ export class Compiler extends DiagnosticEmitter {
5505
5506
}
5506
5507
5507
5508
private compileUnaryOverload (
5508
- operatorInstance : Function ,
5509
- value : Expression ,
5509
+ /** Overload function instance. */
5510
+ overload : Function ,
5511
+ /** Compiled value expression. */
5510
5512
valueExpr : ExpressionRef ,
5511
- reportNode : Node
5513
+ /** Value type. */
5514
+ valueType : Type ,
5515
+ /** Report node. */
5516
+ reportNode : UnaryExpression
5512
5517
) : ExpressionRef {
5513
- // FIXME: see comment in compileBinaryOverload below why recompiling on type mismatch
5514
- // is a bad idea currently. so this assumes that the type matches.
5515
- return this . makeCallDirect ( operatorInstance , [ valueExpr ] , reportNode , false ) ;
5518
+ valueExpr = this . convertExpression ( valueExpr , valueType , overload . unaryOverloadValueType , false , false , reportNode ) ;
5519
+ return this . makeCallDirect ( overload , [ valueExpr ] , reportNode , false ) ;
5516
5520
}
5517
5521
5518
5522
private compileBinaryOverload (
5519
- operatorInstance : Function ,
5520
- left : Expression ,
5523
+ /** Overload function instance. */
5524
+ overload : Function ,
5525
+ /** Compiled left expression. */
5521
5526
leftExpr : ExpressionRef ,
5527
+ /** Left expression type. */
5528
+ leftType : Type ,
5529
+ /** Right expression to compile. */
5522
5530
right : Expression ,
5523
- reportNode : Node
5531
+ /** Report node. */
5532
+ reportNode : BinaryExpression
5524
5533
) : ExpressionRef {
5525
- var rightType : Type ;
5526
- if ( operatorInstance . is ( CommonFlags . INSTANCE ) ) {
5527
- let classInstance = assert ( operatorInstance . parent ) ; assert ( classInstance . kind == ElementKind . CLASS ) ;
5528
- rightType = operatorInstance . signature . parameterTypes [ 0 ] ;
5529
- } else {
5530
- // FIXME: if LHS type differs we can't recompile left because that'd completely confuse
5531
- // local states, like having retained locals that actually do not even exist, possibly
5532
- // releasing something random in that local before and evil things like that. Hence this
5533
- // assumes that LHS type matches, which in turn means that static overloads must be
5534
- // guaranteed to never mismatch LHS type, which in turn means that we can't have shiny
5535
- // things like multiple static overloads for different combinations of LHS/RHS types.
5536
- // We might want that at some point of course, but requires to complete the resolver so
5537
- // it can actually resolve every kind of expression without ever having to recompile.
5538
- rightType = operatorInstance . signature . parameterTypes [ 1 ] ;
5539
- }
5540
- var rightExpr = this . compileExpression ( right , rightType , Constraints . CONV_IMPLICIT ) ;
5541
- return this . makeCallDirect ( operatorInstance , [ leftExpr , rightExpr ] , reportNode ) ;
5534
+ leftExpr = this . convertExpression ( leftExpr , leftType , overload . binaryOverloadLeftType , false , false , reportNode ) ;
5535
+ var rightExpr = this . compileExpression ( right , overload . binaryOverloadRightType , Constraints . CONV_IMPLICIT ) ;
5536
+ return this . makeCallDirect ( overload , [ leftExpr , rightExpr ] , reportNode ) ;
5542
5537
}
5543
5538
5544
5539
private compileAssignment ( expression : Expression , valueExpression : Expression , contextualType : Type ) : ExpressionRef {
@@ -8640,7 +8635,7 @@ export class Compiler extends DiagnosticEmitter {
8640
8635
flow . freeTempLocal ( tempLocal ) ;
8641
8636
tempLocal = null ;
8642
8637
}
8643
- expr = this . compileUnaryOverload ( overload , expression . operand , getValue , expression ) ;
8638
+ expr = this . compileUnaryOverload ( overload , getValue , this . currentType , expression ) ;
8644
8639
if ( isInstance ) break ;
8645
8640
return expr ; // here
8646
8641
}
@@ -8729,7 +8724,7 @@ export class Compiler extends DiagnosticEmitter {
8729
8724
flow . freeTempLocal ( tempLocal ) ;
8730
8725
tempLocal = null ;
8731
8726
}
8732
- expr = this . compileUnaryOverload ( overload , expression . operand , getValue , expression ) ;
8727
+ expr = this . compileUnaryOverload ( overload , getValue , this . currentType , expression ) ;
8733
8728
if ( overload . is ( CommonFlags . INSTANCE ) ) break ;
8734
8729
return expr ; // here
8735
8730
}
@@ -8873,7 +8868,7 @@ export class Compiler extends DiagnosticEmitter {
8873
8868
let classReference = this . currentType . classReference ;
8874
8869
if ( classReference ) {
8875
8870
let overload = classReference . lookupOverload ( OperatorKind . PLUS ) ;
8876
- if ( overload ) return this . compileUnaryOverload ( overload , expression . operand , expr , expression ) ;
8871
+ if ( overload ) return this . compileUnaryOverload ( overload , expr , this . currentType , expression ) ;
8877
8872
}
8878
8873
this . error (
8879
8874
DiagnosticCode . The_0_operator_cannot_be_applied_to_type_1 ,
@@ -8908,7 +8903,7 @@ export class Compiler extends DiagnosticEmitter {
8908
8903
let classReference = this . currentType . classReference ;
8909
8904
if ( classReference ) {
8910
8905
let overload = classReference . lookupOverload ( OperatorKind . MINUS ) ;
8911
- if ( overload ) return this . compileUnaryOverload ( overload , expression . operand , expr , expression ) ;
8906
+ if ( overload ) return this . compileUnaryOverload ( overload , expr , this . currentType , expression ) ;
8912
8907
}
8913
8908
this . error (
8914
8909
DiagnosticCode . The_0_operator_cannot_be_applied_to_type_1 ,
@@ -8976,7 +8971,7 @@ export class Compiler extends DiagnosticEmitter {
8976
8971
if ( classReference ) {
8977
8972
let overload = classReference . lookupOverload ( OperatorKind . PREFIX_INC ) ;
8978
8973
if ( overload ) {
8979
- expr = this . compileUnaryOverload ( overload , expression . operand , expr , expression ) ;
8974
+ expr = this . compileUnaryOverload ( overload , expr , this . currentType , expression ) ;
8980
8975
if ( overload . is ( CommonFlags . INSTANCE ) ) break ; // re-assign
8981
8976
return expr ; // skip re-assign
8982
8977
}
@@ -9047,7 +9042,7 @@ export class Compiler extends DiagnosticEmitter {
9047
9042
if ( classReference ) {
9048
9043
let overload = classReference . lookupOverload ( OperatorKind . PREFIX_DEC ) ;
9049
9044
if ( overload ) {
9050
- expr = this . compileUnaryOverload ( overload , expression . operand , expr , expression ) ;
9045
+ expr = this . compileUnaryOverload ( overload , expr , this . currentType , expression ) ;
9051
9046
if ( overload . is ( CommonFlags . INSTANCE ) ) break ; // re-assign
9052
9047
return expr ; // skip re-assign
9053
9048
}
@@ -9116,7 +9111,7 @@ export class Compiler extends DiagnosticEmitter {
9116
9111
let classReference = this . currentType . classReference ;
9117
9112
if ( classReference ) {
9118
9113
let overload = classReference . lookupOverload ( OperatorKind . NOT ) ;
9119
- if ( overload ) return this . compileUnaryOverload ( overload , expression . operand , expr , expression ) ;
9114
+ if ( overload ) return this . compileUnaryOverload ( overload , expr , this . currentType , expression ) ;
9120
9115
}
9121
9116
// allow '!' for references even without an overload
9122
9117
}
@@ -9141,7 +9136,7 @@ export class Compiler extends DiagnosticEmitter {
9141
9136
let classReference = this . currentType . classReference ;
9142
9137
if ( classReference ) {
9143
9138
let overload = classReference . lookupOverload ( OperatorKind . BITWISE_NOT ) ;
9144
- if ( overload ) return this . compileUnaryOverload ( overload , expression . operand , expr , expression ) ;
9139
+ if ( overload ) return this . compileUnaryOverload ( overload , expr , this . currentType , expression ) ;
9145
9140
}
9146
9141
this . error (
9147
9142
DiagnosticCode . The_0_operator_cannot_be_applied_to_type_1 ,
0 commit comments