Skip to content

Commit b376d0b

Browse files
committed
Error like other keywords, though undefined is not a keyword
1 parent 6206462 commit b376d0b

10 files changed

+32
-64
lines changed

src/compiler/checker.ts

Lines changed: 2 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -1473,6 +1473,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
14731473
var globals = createSymbolTable();
14741474
var undefinedSymbol = createSymbol(SymbolFlags.Property, "undefined" as __String);
14751475
undefinedSymbol.declarations = [];
1476+
globals.set(undefinedSymbol.escapedName, undefinedSymbol);
14761477

14771478
var globalThisSymbol = createSymbol(SymbolFlags.Module, "globalThis" as __String, CheckFlags.Readonly);
14781479
globalThisSymbol.exports = globals;
@@ -2255,9 +2256,6 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
22552256
var identityRelation = new Map<string, RelationComparisonResult>();
22562257
var enumRelation = new Map<string, RelationComparisonResult>();
22572258

2258-
var builtinGlobals = createSymbolTable();
2259-
builtinGlobals.set(undefinedSymbol.escapedName, undefinedSymbol);
2260-
22612259
// Extensions suggested for path imports when module resolution is node16 or higher.
22622260
// The first element of each tuple is the extension a file has.
22632261
// The second element of each tuple is the extension that should be used in a path import.
@@ -2720,23 +2718,6 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
27202718
}
27212719
}
27222720

2723-
function addToSymbolTable(target: SymbolTable, source: SymbolTable, message: DiagnosticMessage) {
2724-
source.forEach((sourceSymbol, id) => {
2725-
const targetSymbol = target.get(id);
2726-
if (targetSymbol) {
2727-
// Error on redeclarations
2728-
forEach(targetSymbol.declarations, addDeclarationDiagnostic(unescapeLeadingUnderscores(id), message));
2729-
}
2730-
else {
2731-
target.set(id, sourceSymbol);
2732-
}
2733-
});
2734-
2735-
function addDeclarationDiagnostic(id: string, message: DiagnosticMessage) {
2736-
return (declaration: Declaration) => diagnostics.add(createDiagnosticForNode(declaration, message, id));
2737-
}
2738-
}
2739-
27402721
function getSymbolLinks(symbol: Symbol): SymbolLinks {
27412722
if (symbol.flags & SymbolFlags.Transient) return (symbol as TransientSymbol).links;
27422723
const id = getSymbolId(symbol);
@@ -44320,6 +44301,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
4432044301
case "symbol":
4432144302
case "void":
4432244303
case "object":
44304+
case "undefined":
4432344305
error(name, message, name.escapedText as string);
4432444306
}
4432544307
}
@@ -48795,9 +48777,6 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
4879548777
}
4879648778
}
4879748779

48798-
// Setup global builtins
48799-
addToSymbolTable(globals, builtinGlobals, Diagnostics.Declaration_name_conflicts_with_built_in_global_identifier_0);
48800-
4880148780
getSymbolLinks(undefinedSymbol).type = undefinedWideningType;
4880248781
getSymbolLinks(argumentsSymbol).type = getGlobalType("IArguments" as __String, /*arity*/ 0, /*reportErrors*/ true);
4880348782
getSymbolLinks(unknownSymbol).type = errorType;

src/compiler/parser.ts

Lines changed: 0 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -2419,13 +2419,6 @@ namespace Parser {
24192419
}
24202420
}
24212421

2422-
function parseErrorForDeclarationNamedUndefined(name: Identifier) {
2423-
if (name.escapedText === "undefined") {
2424-
const pos = skipTrivia(sourceText, name.pos);
2425-
parseErrorAt(pos, name.end, Diagnostics.Declaration_name_conflicts_with_built_in_global_identifier_0, "undefined");
2426-
}
2427-
}
2428-
24292422
function getSpaceSuggestion(expressionText: string) {
24302423
for (const keyword of viableKeywordSuggestions) {
24312424
if (expressionText.length > keyword.length + 2 && startsWith(expressionText, keyword)) {
@@ -3930,7 +3923,6 @@ namespace Parser {
39303923
const pos = getNodePos();
39313924
const modifiers = parseModifiers(/*allowDecorators*/ false, /*permitConstAsModifier*/ true);
39323925
const name = parseIdentifier();
3933-
parseErrorForDeclarationNamedUndefined(name);
39343926
let constraint: TypeNode | undefined;
39353927
let expression: Expression | undefined;
39363928
if (parseOptional(SyntaxKind.ExtendsKeyword)) {
@@ -4377,7 +4369,6 @@ namespace Parser {
43774369
function parseMappedTypeParameter() {
43784370
const pos = getNodePos();
43794371
const name = parseIdentifierName();
4380-
parseErrorForDeclarationNamedUndefined(name);
43814372
parseExpected(SyntaxKind.InKeyword);
43824373
const type = parseType();
43834374
return finishNode(factory.createTypeParameterDeclaration(/*modifiers*/ undefined, name, type, /*defaultType*/ undefined), pos);
@@ -4742,7 +4733,6 @@ namespace Parser {
47424733
function parseTypeParameterOfInferType(): TypeParameterDeclaration {
47434734
const pos = getNodePos();
47444735
const name = parseIdentifier();
4745-
parseErrorForDeclarationNamedUndefined(name);
47464736
const constraint = tryParse(tryParseConstraintOfInferType);
47474737
const node = factory.createTypeParameterDeclaration(/*modifiers*/ undefined, name, constraint);
47484738
return finishNode(node, pos);
@@ -8107,9 +8097,6 @@ namespace Parser {
81078097

81088098
// We don't parse the name here in await context, instead we will report a grammar error in the checker.
81098099
const name = parseNameOfClassDeclarationOrExpression();
8110-
if (name) {
8111-
parseErrorForDeclarationNamedUndefined(name);
8112-
}
81138100
const typeParameters = parseTypeParameters();
81148101
if (some(modifiers, isExportModifier)) setAwaitContext(/*value*/ true);
81158102
const heritageClauses = parseHeritageClauses();
@@ -8192,7 +8179,6 @@ namespace Parser {
81928179
function parseInterfaceDeclaration(pos: number, hasJSDoc: boolean, modifiers: NodeArray<ModifierLike> | undefined): InterfaceDeclaration {
81938180
parseExpected(SyntaxKind.InterfaceKeyword);
81948181
const name = parseIdentifier();
8195-
parseErrorForDeclarationNamedUndefined(name);
81968182
const typeParameters = parseTypeParameters();
81978183
const heritageClauses = parseHeritageClauses();
81988184
const members = parseObjectTypeMembers();
@@ -8206,7 +8192,6 @@ namespace Parser {
82068192
parseErrorAtCurrentToken(Diagnostics.Line_break_not_permitted_here);
82078193
}
82088194
const name = parseIdentifier();
8209-
parseErrorForDeclarationNamedUndefined(name);
82108195
const typeParameters = parseTypeParameters();
82118196
parseExpected(SyntaxKind.EqualsToken);
82128197
const type = token() === SyntaxKind.IntrinsicKeyword && tryParse(parseKeywordAndNoDot) || parseType();
@@ -8230,7 +8215,6 @@ namespace Parser {
82308215
function parseEnumDeclaration(pos: number, hasJSDoc: boolean, modifiers: NodeArray<ModifierLike> | undefined): EnumDeclaration {
82318216
parseExpected(SyntaxKind.EnumKeyword);
82328217
const name = parseIdentifier();
8233-
parseErrorForDeclarationNamedUndefined(name);
82348218
let members;
82358219
if (parseExpected(SyntaxKind.OpenBraceToken)) {
82368220
members = doOutsideOfYieldAndAwaitContext(() => parseDelimitedList(ParsingContext.EnumMembers, parseEnumMember));
@@ -8261,7 +8245,6 @@ namespace Parser {
82618245
// propagate the 'Namespace' flag across the names if set.
82628246
const namespaceFlag = flags & NodeFlags.Namespace;
82638247
const name = flags & NodeFlags.NestedNamespace ? parseIdentifierName() : parseIdentifier();
8264-
parseErrorForDeclarationNamedUndefined(name);
82658248
const body = parseOptional(SyntaxKind.DotToken)
82668249
? parseModuleOrNamespaceDeclaration(getNodePos(), /*hasJSDoc*/ false, /*modifiers*/ undefined, NodeFlags.NestedNamespace | namespaceFlag) as NamespaceDeclaration
82678250
: parseModuleBlock();

tests/baselines/reference/mappedTypeRecursiveInference.types

Lines changed: 4 additions & 4 deletions
Large diffs are not rendered by default.
Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,13 @@
1-
typeNamedUndefined.ts(3,17): error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
2-
typeNamedUndefined.ts(13,13): error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
1+
typeNamedUndefined.ts(3,17): error TS2457: Type alias name cannot be 'undefined'.
2+
typeNamedUndefined.ts(13,13): error TS2457: Type alias name cannot be 'undefined'.
33

44

55
==== typeNamedUndefined.ts (2 errors) ====
66
export namespace ns {
77
const s = Symbol();
88
export type undefined = typeof s;
99
~~~~~~~~~
10-
!!! error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
10+
!!! error TS2457: Type alias name cannot be 'undefined'.
1111
export function x(p: undefined): undefined { // global undefined
1212
return p;
1313
}
@@ -19,5 +19,5 @@ typeNamedUndefined.ts(13,13): error TS2397: Declaration name conflicts with buil
1919

2020
export type undefined = "";
2121
~~~~~~~~~
22-
!!! error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
22+
!!! error TS2457: Type alias name cannot be 'undefined'.
2323

tests/baselines/reference/undefinedTypeAssignment1.errors.txt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
1-
undefinedTypeAssignment1.ts(1,6): error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
1+
undefinedTypeAssignment1.ts(1,6): error TS2457: Type alias name cannot be 'undefined'.
22

33

44
==== undefinedTypeAssignment1.ts (1 errors) ====
55
type undefined = string;
66
~~~~~~~~~
7-
!!! error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
7+
!!! error TS2457: Type alias name cannot be 'undefined'.
88
function p(undefined = "wat") {
99
return undefined;
1010
}
Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
1-
undefinedTypeAssignment2.ts(1,5): error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
1+
undefinedTypeAssignment2.ts(1,5): error TS2300: Duplicate identifier 'undefined'.
22

33

44
==== undefinedTypeAssignment2.ts (1 errors) ====
55
var undefined = void 0;
66
~~~~~~~~~
7-
!!! error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
7+
!!! error TS2300: Duplicate identifier 'undefined'.
88

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
1-
undefinedTypeAssignment3.ts(1,5): error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
1+
undefinedTypeAssignment3.ts(1,5): error TS2300: Duplicate identifier 'undefined'.
22

33

44
==== undefinedTypeAssignment3.ts (1 errors) ====
55
var undefined = null;
66
~~~~~~~~~
7-
!!! error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
7+
!!! error TS2300: Duplicate identifier 'undefined'.
88

tests/baselines/reference/undefinedTypeAssignment4.errors.txt

Lines changed: 13 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,22 +1,28 @@
1-
undefinedTypeAssignment4.ts(1,7): error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
2-
undefinedTypeAssignment4.ts(4,11): error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
3-
undefinedTypeAssignment4.ts(7,11): error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
1+
undefinedTypeAssignment4.ts(1,7): error TS2300: Duplicate identifier 'undefined'.
2+
undefinedTypeAssignment4.ts(1,7): error TS2414: Class name cannot be 'undefined'.
3+
undefinedTypeAssignment4.ts(4,11): error TS2300: Duplicate identifier 'undefined'.
4+
undefinedTypeAssignment4.ts(4,11): error TS2427: Interface name cannot be 'undefined'.
5+
undefinedTypeAssignment4.ts(7,11): error TS2300: Duplicate identifier 'undefined'.
46

57

6-
==== undefinedTypeAssignment4.ts (3 errors) ====
8+
==== undefinedTypeAssignment4.ts (5 errors) ====
79
class undefined {
810
~~~~~~~~~
9-
!!! error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
11+
!!! error TS2300: Duplicate identifier 'undefined'.
12+
~~~~~~~~~
13+
!!! error TS2414: Class name cannot be 'undefined'.
1014
foo: string;
1115
}
1216
interface undefined {
1317
~~~~~~~~~
14-
!!! error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
18+
!!! error TS2300: Duplicate identifier 'undefined'.
19+
~~~~~~~~~
20+
!!! error TS2427: Interface name cannot be 'undefined'.
1521
member: number;
1622
}
1723
namespace undefined {
1824
~~~~~~~~~
19-
!!! error TS2397: Declaration name conflicts with built-in global identifier 'undefined'.
25+
!!! error TS2300: Duplicate identifier 'undefined'.
2026
export var x = 42;
2127
}
2228
var x: undefined;

tests/baselines/reference/undefinedTypeAssignment4.symbols

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,5 +24,5 @@ var x: undefined;
2424

2525
var y: typeof undefined;
2626
>y : Symbol(y, Decl(undefinedTypeAssignment4.ts, 10, 3))
27-
>undefined : Symbol(undefined, Decl(undefinedTypeAssignment4.ts, 0, 0), Decl(undefinedTypeAssignment4.ts, 2, 1), Decl(undefinedTypeAssignment4.ts, 5, 1))
27+
>undefined : Symbol(undefined)
2828

tests/baselines/reference/undefinedTypeAssignment4.types

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,6 @@ var x: undefined;
2222
>x : undefined
2323

2424
var y: typeof undefined;
25-
>y : typeof undefined
26-
>undefined : typeof undefined
25+
>y : any
26+
>undefined : undefined
2727

0 commit comments

Comments
 (0)