170 likes | 328 Views
Topic #6: Type Checking. EE 456 – Compiling Techniques Prof. Carl Sable Fall 2003. Error Checking. Dynamic checking takes place while program is running Static checking takes place during compilation Type checks Flow-of-control checks Uniqueness checks Name-related checks. Types.
E N D
Topic #6: Type Checking EE 456 – Compiling Techniques Prof. Carl Sable Fall 2003
Error Checking • Dynamic checking takes place while program is running • Static checking takes place during compilation • Type checks • Flow-of-control checks • Uniqueness checks • Name-related checks
Types • Every expression has an associated type • Rules exist to assign a type to an expression, e.g.: • If you add, subtract, or multiply two integer operands, the result is an integer • If you take the address of an operand of type T, the type of the result is pointer to T • In Pascal and C, types are either basic or constructed
Type Expressions (1) • A "type expression" is the type of a programming language construct • Type expressions include basic types, e.g. integer or real • A special basic type, type_error, signals an error during type checking • Some languages include a void type
Type Expressions (2) • Applying "type constructors" to type expressions forms new type expressions • Arrays • Records • Pointers • Cartesian Products • A function maps elements from one set (domain) to another set (range) • mod has type "int x int int" • function f(a, b: char) : ↑integer; (f has type "char x char pointer(integer)")
Type Systems • A type system is a collection of rules for assigning type expressions • A type checker implements a type system • Different type systems may be used by different compilers of the same language • A type checker should adequately handle error recovery
Static vs. Dynamic Checks • In principle, any check can be done dynamically if the target code carries type information • A sound type system eliminates the need for dynamic checking • A language is strongly typed of its compiler only accepts programs that have no type errors • In practice, some checks can only be done dynamically (e.g. checking array indices).
Simple Type Checker (1) P D ; E D D ; D | id : T T char | integer | array [num] of T | ↑T E literal | num | id | E mod E | E[E] | E↑ • The simple language above allows a sequence of declarations followed by a single expression • A simple syntax-directed definition can specify a type checker for this language
Symbol Tables • Much of type checking assumes that we can look up the type of an identifier • Need to store identifiers in a symbol table • Symbol table is created and used during compilation process • Table is updated whenever a new name or new information about a name is discovered • Compiler must be able to add new entries or find existing entries efficiently • Can implement table as a linked list or a hash table
Symbol Table Entries • Each entry in a symbol table is for the declaration of a name • Format for entries does not have to be uniform • Each entry can be in the form of a record • Some information about a name can pointed to by pointer in the record • Keywords should be entered initially, if at all; not necessary if intercepted by lexical analyzer
Lexemes • If there is a maximum length for a lexeme, all lexemes can be stored in table entries • If there is no maximum (or if maximum is rarely reached), can use a string table • Entry points to location in string table • Would be some limit for all lexemes together • Another option is to separately allocate space for every lexeme
Representing Scope Information • Difficult if language allows nested procedures • In this case, best to maintain a separate symbol table for every scope • When name is encountered, enclosing procedures are scanned until name is found • Simpler if there are no nested procedures • Ever variable is local to current procedure of global • After compiler is finished processing a procedure body, the entries for the procedure can be deleted