Skip to content

Latest commit

 

History

History
173 lines (87 loc) · 11.3 KB

ii.22.37-typedef-0x02.md

File metadata and controls

173 lines (87 loc) · 11.3 KB

II.22.37 TypeDef: 0x02

The TypeDef table has the following columns:

  • Flags (a 4-byte bitmask of type TypeAttributes, §II.23.1.15)

  • TypeName (an index into the String heap)

  • TypeNamespace (an index into the String heap)

  • Extends (an index into the TypeDef, TypeRef, or TypeSpec table; more precisely, a TypeDefOrRefII.24.2.6) coded index)

  • FieldList (an index into the Field table; it marks the first of a contiguous run of Fields owned by this Type). The run continues to the smaller of:

    • the last row of the Field table

    • the next run of Fields, found by inspecting the FieldList of the next row in this TypeDef table

  • MethodList (an index into the MethodDef table; it marks the first of a continguous run of Methods owned by this Type). The run continues to the smaller of:

    • the last row of the MethodDef table

    • the next run of Methods, found by inspecting the MethodList of the next row in this TypeDef table

    The first row of the TypeDef table represents the pseudo class that acts as parent for functions and variables defined at module scope.

Note that any type shall be one, and only one, of

  • Class (Flags.Interface = 0, and derives ultimately from System.Object)

  • Interface (Flags.Interface = 1)

  • Value type, derived ultimately from System.ValueType

For any given type, there are two separate and distinct chains of pointers to other types (the pointers are actually implemented as indexes into metadata tables). The two chains are:

  • Extension chain – defined via the Extends column of the TypeDef table. Typically, a derived Class extends a base Class (always one, and only one, base Class)

  • Interface chains – defined via the InterfaceImpl table. Typically, a Class implements zero, one or more Interfaces

These two chains (extension and interface) are always kept separate in metadata. The Extends chain represents one-to-one relations—that is, one Class extends (or 'derives from') exactly one other Class (called its immediate base class). The Interface chains can represent one-to-many relations—that is, one Class might well implement two or more Interfaces.

An interface can also implement one or more other interfaces—metadata stores those links via the InterfaceImpl table (the nomenclature is a little inappropriate here—there is no "implementation" involved; perhaps a clearer name might have been Interface table, or InterfaceInherit table)

Another slightly specialized type is a nested type which is declared in ILAsm as lexically nested within an enclosing type declaration. Whether a type is nested can be determined by the value of its Flags.Visibility sub-field – it shall be one of the set {NestedPublic, NestedPrivate, NestedFamily, NestedAssembly, NestedFamANDAssem, NestedFamORAssem}.

If a type is generic, its parameters are defined in the GenericParam table (§II.22.20). Entries in the GenericParam table reference entries in the TypeDef table; there is no reference from the TypeDef table to the GenericParam table.

This contains informative text only.

The roots of the inheritance hierarchies look like this:

Roots of the inheritance hierarchies

There is one system-defined root, System.Object. All Classes and ValueTypes shall derive, ultimately, from System.Object; Classes can derive from other Classes (through a single, non-looping chain) to any depth required. This Extends inheritance chain is shown with heavy arrows.

(See below for details of the System.Delegate Class)

Interfaces do not inherit from one another; however, they can have zero or more required interfaces, which shall be implemented. The Interface requirement chain is shown as light, dashed arrows. This includes links between Interfaces and Classes/ValueTypes – where the latter are said to implement that interface or interfaces. Regular ValueTypes (i.e., excluding Enums — see later) are defined as deriving directly from System.ValueType. Regular ValueTypes cannot be derived to a depth of more than one. (Another way to state this is that user-defined ValueTypes shall be sealed.) User-defined Enums shall derive directly from System.Enum. Enums cannot be derived to a depth of more than one below System.Enum. (Another way to state this is that user-defined Enums shall be sealed.) System.Enum derives directly from System.ValueType.

User-defined delegates derive from System.Delegate. Delegates cannot be derived to a depth of more than one.

For the directives to declare types see §II.9.

  1. A TypeDef table can contain one or more rows.

  2. Flags:

    1. Flags shall have only those values set that are specified [ERROR]

    2. can set 0 or 1 of SequentialLayout and ExplicitLayout (if none set, then defaults to AutoLayout) [ERROR]

    3. can set 0 or 1 of UnicodeClass and AutoClass (if none set, then defaults to AnsiClass) [ERROR]

    4. If Flags.HasSecurity = 1, then at least one of the following conditions shall be true: [ERROR]

      • this Type owns at least one row in the DeclSecurity table

      • this Type has a custom attribute called SuppressUnmanagedCodeSecurityAttribute

    5. If this Type owns one (or more) rows in the DeclSecurity table then Flags.HasSecurity shall be 1 [ERROR]

    6. If this Type has a custom attribute called SuppressUnmanagedCodeSecurityAttribute then Flags.HasSecurity shall be 1 [ERROR]

    7. Note that it is valid for an Interface to have HasSecurity set. However, the security system ignores any permission requests attached to that Interface

  3. Name shall index a non-empty string in the String heap [ERROR]

  4. The TypeName string shall be a valid CLS identifier [CLS]

  5. TypeNamespace can be null or non-null

  6. If non-null, then TypeNamespace shall index a non-empty string in the String heap [ERROR]

  7. If non-null, TypeNamespace's string shall be a valid CLS Identifier [CLS]

  8. Every Class (with the exception of System.Object and the special class <Module>) shall extend one, and only one, other Class – so Extends for a Class shall be non-null [ERROR]

  9. System.Object shall have an Extends value of null [ERROR]

  10. System.ValueType shall have an Extends value of System.Object [ERROR]

  11. With the exception of System.Object and the special class <Module>, for any Class, Extends shall index a valid row in the TypeDef, TypeRef, or TypeSpec table, where valid means 1 ≤ row ≤ rowcount. In addition, that row itself shall be a Class (not an Interface or ValueType) In addition, that base Class shall not be sealed (its Flags.Sealed shall be 0) [ERROR]

  12. A Class cannot extend itself, or any of its children (i.e., its derived Classes), since this would introduce loops in the hierarchy tree [ERROR] (For generic types, see §II.9.1 and §II.9.2.)

  13. An Interface never extends another Type – so Extends shall be null (Interfaces do implement other Interfaces, but recall that this relationship is captured via the InterfaceImpl table, rather than the Extends column) [ERROR]

  14. FieldList can be null or non-null

  15. A Class or Interface can 'own' zero or more fields

  16. A ValueType shall have a non-zero size – either by defining at least one field, or by providing a non-zero ClassSize [ERROR]

  17. If FieldList is non-null, it shall index a valid row in the Field table, where valid means 1 ≤ row ≤ rowcount+1 [ERROR]

  18. MethodList can be null or non-null

  19. A Type can 'own' zero or more methods

  20. The runtime size of a ValueType shall not exceed 1 MByte (0x100000 bytes) [ERROR]

  21. If MethodList is non-null, it shall index a valid row in the MethodDef table, where valid means 1 ≤ row ≤ rowcount+1 [ERROR]

  22. A Class which has one or more abstract methods cannot be instantiated, and shall have Flags.Abstract = 1. Note that the methods owned by the class include all of those inherited from its base class and interfaces it implements, plus those defined via its MethodList. (The CLI shall analyze class definitions at runtime; if it finds a class to have one or more abstract methods, but has Flags.Abstract = 0, it will throw an exception) [ERROR]

  23. An Interface shall have Flags.Abstract = 1 [ERROR]

  24. It is valid for an abstract Type to have a constructor method (ie, a method named .ctor)

  25. Any non-abstract Type (ie Flags.Abstract = 0) shall provide an implementation (body) for every method its contract requires. Its methods can be inherited from its base class, from the interfaces it implements, or defined by itself. The implementations can be inherited from its base class, or defined by itself [ERROR]

  26. An Interface (Flags.Interface = 1) can own static fields (Field.Static = 1) but cannot own instance fields (Field.Static = 0) [ERROR]

  27. An Interface cannot be sealed (if Flags.Interface = 1, then Flags.Sealed shall be 0) [ERROR]

  28. All of the methods owned by an Interface (Flags.Interface = 1) shall be abstract (Flags.Abstract = 1) [ERROR]

  29. There shall be no duplicate rows in the TypeDef table, based on TypeNamespace+TypeName (unless this is a nested type – see below) [ERROR]

  30. If this is a nested type, there shall be no duplicate row in the TypeDef table, based upon TypeNamespace+TypeName+OwnerRowInNestedClassTable [ERROR]

  31. There shall be no duplicate rows, where TypeNamespace+TypeName fields are compared using CLS conflicting-identifier-rules (unless this is a nested type – see below) [CLS]

  32. If this is a nested type, there shall be no duplicate rows, based upon TypeNamespace+TypeName+OwnerRowInNestedClassTable and where TypeNamespace+TypeName fields are compared using CLS conflicting-identifier-rules [CLS]

  33. If Extends = System.Enum (i.e., type is a user-defined Enum) then:

    1. shall be sealed (Sealed = 1) [ERROR]

    2. shall not have any methods of its own (MethodList chain shall be zero length) [ERROR]

    3. shall not implement any interfaces (no entries in InterfaceImpl table for this type) [ERROR]

    4. shall not have any properties [ERROR]

    5. shall not have any events [ERROR]

    6. any static fields shall be literal (have Flags.Literal = 1) [ERROR]

    7. shall have one or more static, literal fields, each of which has the type of the Enum [CLS]

    8. shall be exactly one instance field, of built-in integer type [ERROR]

    9. the Name string of the instance field shall be "value__", the field shall be marked RTSpecialName, and that field shall have one of the CLS integer types [CLS]

    10. shall not have any static fields unless they are literal [ERROR]

  34. A Nested type (defined above) shall own exactly one row in the NestedClass table, where 'owns' means a row in that NestedClass table whose NestedClass column holds the TypeDef token for this type definition [ERROR]

  35. A ValueType shall be sealed [ERROR]

End informative text.