Skip to content

Commit 249579f

Browse files
committed
Added section about explicitly resolved (fka canonical) syntax
1 parent 9431e74 commit 249579f

File tree

1 file changed

+215
-25
lines changed

1 file changed

+215
-25
lines changed

specification/dartLangSpec.tex

+215-25
Original file line numberDiff line numberDiff line change
@@ -2650,7 +2650,7 @@ \subsection{Type of a Function}
26502650
different type parameters, F-bounds, and the types of formal parameters.
26512651
However, we do not wish to distinguish between two function types if they have
26522652
the same structure and only differ in the choice of names.
2653-
This treatment of names is also known as alpha-equivalence.%
2653+
This treatment of names is also known as alpha equivalence.%
26542654
}
26552655

26562656
\LMHash{}%
@@ -21884,24 +21884,18 @@ \subsubsection{Subtype Rules}
2188421884
However, we must eliminate the difficulties associated with
2188521885
different syntax denoting the same type,
2188621886
and different types denoted by the same syntax.
21887-
We do this by assuming that every type in the program has been expressed
21888-
in a manner where those situations never occur,
21889-
because each type is denoted by the same globally unique syntax everywhere.%
21887+
We do this by defining in detail what it means to be the same type
21888+
(\ref{sameStaticType}).%
2189021889
}
2189121890

2189221891
\LMHash{}%
2189321892
In section~\ref{subtypes} and its subsections,
2189421893
all designations of types are considered to be the same
21895-
if{}f they have the same canonical syntax
21896-
(\ref{theCanonicalSyntaxOfTypes}).
21894+
type if{}f they satisfy the criteria in
21895+
Section~\ref{sameStaticType}.
2189721896

21898-
\commentary{%
21899-
Note that the canonical syntax also implies
21900-
transitive expansion of all type aliases
21901-
(\ref{typedef}).
21902-
In other words, subtyping rules do not need to consider type aliases,
21903-
because all type aliases have been expanded.%
21904-
}
21897+
\LMHash{}%
21898+
The subtype rules assume that all type aliases have been transitively expanded.
2190521899

2190621900
\LMHash{}%
2190721901
Every \synt{typeName} used in a type mentioned
@@ -22282,19 +22276,13 @@ \subsection{Function Types}
2228222276
coincide in this case.%
2228322277
}
2228422278

22285-
\LMHash{}%
22286-
Two function types are considered equal if consistent renaming of type
22287-
parameters can make them identical.
22288-
2228922279
\commentary{%
22290-
A common way to say this is that we do not distinguish
22291-
function types which are alpha-equivalent.
22292-
For the subtyping rule below this means we can assume that
22293-
a suitable renaming has already taken place.
22294-
In cases where this is not possible
22295-
because the number of type parameters in the two types differ
22296-
or the bounds are different,
22297-
no subtype relationship exists.%
22280+
Two function types are the same type
22281+
if, roughly, consistent renaming of type
22282+
parameters can make them identical.
22283+
This is also known as alpha equivalence.
22284+
The detailed rules are described in
22285+
Section~\ref{sameStaticType}.%
2229822286
}
2229922287

2230022288
\LMHash{}%
@@ -23153,6 +23141,208 @@ \subsubsection{Least Upper Bounds}
2315323141
}
2315423142

2315523143

23144+
\subsection{Same Static Type}
23145+
\LMLabel{sameStaticType}
23146+
23147+
\LMHash{}%
23148+
This section specifies how to soundly determine whether or not two types
23149+
that are encountered during static analysis are the same type.
23150+
23151+
\LMHash{}%
23152+
Concrete syntax denoting types gives rise to several difficulties
23153+
when used to determine static semantic properties,
23154+
like subtyping relationships
23155+
(\ref{subtypes})
23156+
or upper and lower bounds
23157+
(\ref{standardUpperBoundsAndStandardLowerBounds}).
23158+
23159+
\commentary{%
23160+
Note that the notion of being the same type at run time is different from
23161+
the notion of being the same type during static analysis.
23162+
For example, two distinct type variables \code{X} and \code{Y}
23163+
might at run time be bound to the same type, e.g.,
23164+
\code{List<int>}.
23165+
However, during static analysis we must maintain that
23166+
\code{X} and \code{Y} are different types
23167+
because there is no guarantee that they are always bound to
23168+
the same type at run time.%
23169+
}
23170+
23171+
\commentary{%
23172+
The phrases `same type' and `identical syntax' deserves some extra scrutiny.
23173+
If a library $L$ imports the libraries $L_1$ and $L_2$
23174+
(where $L_1$ and $L_2$ are not the same library),
23175+
and both $L_1$ and $L_2$ declare a class \code{C},
23176+
then the syntax \code{C} may occur as a type during static analysis of $L$
23177+
in situations where it refers to two distinct types.
23178+
23179+
For instance, $L_1$ could declare a variable \code{v}
23180+
of type \code{C}-in-$L_1$,
23181+
and $L_2$ could declare a function
23182+
\code{\VOID\,foo(C\,\,c)\,\,\{\}}
23183+
which uses the type \code{C}-in-$L_2$,
23184+
and $L$ could contain the expression \code{foo(v)}.
23185+
23186+
Note that even though it would be a compile-time error to use \code{C} in $L$
23187+
(because it is ambiguous),
23188+
it is not an error to have an expression like \code{foo(v)},
23189+
and the static analysis of this expression \emph{must}
23190+
be able to determine that the two types whose name is \code{C} are
23191+
not the same type. The invocation may or may not be an error,
23192+
depending on the subtyping relations.%
23193+
}
23194+
23195+
\rationale{%
23196+
This shows that concrete syntax behaves in such a manner that it is
23197+
unsafe to consider two types to be the same type,
23198+
based on the fact that they are denoted by the same syntax,
23199+
even during the static analysis of a single expression.
23200+
23201+
Similarly, it is incorrect to consider two terms derived from \synt{type}
23202+
as different types based on the fact that they are syntactically different.
23203+
For example, they could be the same type imported with different import
23204+
prefixes.
23205+
23206+
We could say that two identifiers
23207+
(possibly qualified, e.g., \code{myPrefix.C} and \code{C})
23208+
denote the same type
23209+
if they have been resolved to the same declaration.
23210+
23211+
However, we introduce \emph{the explicitly resolved syntax for a type},
23212+
which is basically an explicit representation of this idea,
23213+
in order to make the underlying issues more explicit.
23214+
The explicitly resolved syntax has the property that
23215+
each type has a unique syntactic form
23216+
(except for alpha equivalence, which is defined below).
23217+
We may then consider this unique syntactic form as a static semantic value,
23218+
rather than just a syntactic form which is dependent on
23219+
its location in the program.%
23220+
}
23221+
23222+
\LMHash{}%
23223+
The
23224+
\IndexCustom{explicitly resolved syntax}{type!explicitly resolved syntax of}
23225+
of the types in a given library $L_1$
23226+
and all libraries \List{L}{2}{n} reachable from $L_1$ via
23227+
one or more import links
23228+
is determined as follows.
23229+
First, choose a set of distinct, globally fresh identifiers
23230+
\List{\metavar{prefix}}{1}{n}.
23231+
Then transform each library $L_i$, $i \in 1 .. n$ as follows:
23232+
23233+
\begin{enumerate}
23234+
\item
23235+
For each type variable declared in $L_i$, consistently rename
23236+
it to a globally fresh name.
23237+
\item
23238+
If $D_T$ is a declaration of a class, mixin, or type alias in $L_i$
23239+
whose name $n$ is private,
23240+
and an occurrence of $n$ that resolves to $D$
23241+
exists in a type alias declaration $D_A$ whose name is non-private,
23242+
then perform a consistent renaming of
23243+
all occurrences of $n$ in $L_i$ that resolve to $D_T$
23244+
to a fresh, non-private identifier.
23245+
\commentary{%
23246+
We make $D_T$ public, because it is being leaked anyway.%
23247+
}
23248+
\item
23249+
Add a set of import directives to $L_i$ that imports
23250+
each of the libraries \List{L}{1}{n} with
23251+
the corresponding prefix $\metavar{prefix}_j$, $j \in 1 .. n$.
23252+
23253+
\commentary{%
23254+
This means that every library in the set
23255+
$\{\,\List{L}{1}{n}\,\}$
23256+
imports every other library in that set,
23257+
even itself and system libraries like \code{dart:core}.%
23258+
}
23259+
\item
23260+
Let \id{} be an occurrence of
23261+
a non-private type identifier derived from \synt{typeName}
23262+
that resolves to a library declaration in the library $L_j$
23263+
in the original program;
23264+
\id{} is then transformed to \code{$\metavar{prefix}_j$.\id}.
23265+
Let \code{$p$.\id} be derived from \synt{typeName} such that $p$ is
23266+
an import prefix in the original program
23267+
and \id{} is a non-private identifier,
23268+
and consider the case where \code{$p$.\id} resolves to
23269+
a library declaration in the library $L_j$ in the original program,
23270+
for some $j$;
23271+
\code{$p$.\id} is then transformed to \code{$\metavar{prefix}_j$.\id}.
23272+
\item
23273+
Replace every type in $L_i$ that denotes a type alias
23274+
along with its actual type arguments, if any,
23275+
by its transitive alias expansion
23276+
(\ref{typedef}).
23277+
\commentary{%
23278+
Note that the bodies of type alias declarations
23279+
already use the new prefixes,
23280+
so the results of the alias expansion will also use
23281+
the new prefixes consistently.%
23282+
}
23283+
\end{enumerate}
23284+
23285+
\commentary{%
23286+
In short, this transformation adds a unique prefix to every type name
23287+
which is resolved to a top-level declaration
23288+
(in the same library or in an imported library).
23289+
23290+
This transformation does not change any occurrence of \VOID,
23291+
and does not need to;
23292+
\VOID{} is a reserved word, not a type identifier.
23293+
Also, \code{$\metavar{prefix}_j$.\VOID} would be a syntax error.
23294+
23295+
Note that the transformation changes terms derived from \synt{type},
23296+
but it does not change expressions, or any other program element
23297+
(except that a \synt{type} can occur in an expression, e.g., \code{<int>[]}).
23298+
In particular, it does not change type literals
23299+
(that is, expressions denoting types).%
23300+
}
23301+
23302+
\LMHash{}%
23303+
Every \synt{type} in the resulting set of libraries
23304+
is now expressed in a globally unique syntactic form,
23305+
which is the form that we call the
23306+
\IndexCustom{explicitly resolved syntax of}{type!explicitly resolved syntax of}
23307+
said types.
23308+
23309+
\LMHash{}%
23310+
When we say that two types $T_1$ and $T_2$ have the
23311+
\IndexCustom{same explicitly resolved syntax}{type!same explicitly resolved syntax},
23312+
it refers to the situation where the current library
23313+
and all libraries which are reachable via one or more imports
23314+
have been transformed as described above,
23315+
and the resulting explicitly resolved syntaxes are textually identical.
23316+
23317+
\LMHash{}%
23318+
We need to introduce one more concept:
23319+
An \Index{alpha conversion} of a type is a consistent renaming
23320+
of the type variables declared in that type.
23321+
23322+
\commentary{%
23323+
In Dart, only function types can be subject to an alpha conversion:
23324+
A function type is the only kind of type that declares type variables.
23325+
For example,
23326+
\code{List<X>\,\,\FUNCTION<X>({X\,\,arg})}
23327+
can be turned into
23328+
\code{List<Y>\,\,\FUNCTION<Y>({Y\,\,arg})}
23329+
by alpha conversion.%
23330+
}
23331+
23332+
\LMHash{}%
23333+
Two function types are \Index{alpha equivalent} if{}f
23334+
there exists an alpha conversion that makes them textually identical.
23335+
23336+
\LMHash{}%
23337+
Finally, we define that two type denotations $T_1$ and $T_2$ are the
23338+
\IndexCustom{same static type}{type!same static}
23339+
if there exist alpha conversions
23340+
that can be applied to the function types
23341+
that occur as subterms of $T_1$ and $T_2$, if any,
23342+
such that the resulting terms $T'_1$ and $T'_2$ have
23343+
the same explicitly resolved syntax.
23344+
23345+
2315623346
\section{Reference}
2315723347
\LMLabel{reference}
2315823348

0 commit comments

Comments
 (0)