X-Git-Url: http://plrg.eecs.uci.edu/git/?a=blobdiff_plain;f=docs%2FSourceLevelDebugging.html;h=e7eac08ee81cea3079558be84fca750138d2c856;hb=5bfd9692089830da0d17f618a40f026a7600c67c;hp=544b9142e263513d8060406bc6525909fc29a5b1;hpb=e9db5e29e3af91eec572bfeb8dcec908213298b0;p=oota-llvm.git diff --git a/docs/SourceLevelDebugging.html b/docs/SourceLevelDebugging.html index 544b9142e26..e7eac08ee81 100644 --- a/docs/SourceLevelDebugging.html +++ b/docs/SourceLevelDebugging.html @@ -8,7 +8,7 @@ -
Source Level Debugging with LLVM
+

Source Level Debugging with LLVM

@@ -53,6 +53,19 @@
  • C/C++ struct/union types
  • C/C++ enumeration types
  • +
  • LLVM Dwarf Extensions +
      +
    1. Debugging Information Extension + for Objective C Properties
    2. + + +
    +
  • @@ -68,10 +81,10 @@ height="369"> - +

    Introduction

    -
    +

    This document is the central repository for all information pertaining to debug information in LLVM. It describes the actual format @@ -80,14 +93,12 @@ height="369"> Further, this document provides specific examples of what debug information for C/C++ looks like.

    -
    - - + -
    +

    The idea of the LLVM debugging information is to capture how the important pieces of the source-language's Abstract Syntax Tree map onto LLVM code. @@ -133,11 +144,11 @@ height="369">

    - + -
    +

    The role of debug information is to provide meta information normally stripped away during the compilation process. This meta information provides @@ -157,11 +168,11 @@ height="369">

    - + -
    +

    An extremely high priority of LLVM debugging information is to make it interact well with optimizations and analysis. In particular, the LLVM debug @@ -176,22 +187,15 @@ height="369"> as setting program variables, or calling functions that have been deleted. -

  • LLVM optimizations gracefully interact with debugging information. If - they are not aware of debug information, they are automatically disabled - as necessary in the cases that would invalidate the debug info. This - retains the LLVM features, making it easy to write new - transformations.
  • -
  • As desired, LLVM optimizations can be upgraded to be aware of the LLVM debugging information, allowing them to update the debugging information as they perform aggressive optimizations. This means that, with effort, the LLVM optimizers could optimize debug code just as well as non-debug code.
  • -
  • LLVM debug information does not prevent many important optimizations from +
  • LLVM debug information does not prevent optimizations from happening (for example inlining, basic block reordering/merging/cleanup, - tail duplication, etc), further reducing the amount of the compiler that - eventually is "aware" of debugging information.
  • + tail duplication, etc).
  • LLVM debug information is automatically optimized along with the rest of the program, using existing facilities. For example, duplicate @@ -226,13 +230,15 @@ height="369">
  • +
    + - + -
    +

    LLVM debugging information has been carefully designed to make it possible for the optimizer to optimize the program and debugging information without @@ -265,14 +271,12 @@ height="369"> common to any source-language. The next section describes the data layout conventions used by the C and C++ front-ends.

    -
    - - + -
    +

    In consideration of the complexity and volume of debug information, LLVM provides a specification for well formed debug descriptors.

    @@ -307,19 +311,17 @@ height="369"> of tags are loosely bound to the tag values of DWARF information entries. However, that does not restrict the use of the information supplied to DWARF targets. To facilitate versioning of debug information, the tag is augmented - with the current debug version (LLVMDebugVersion = 8 << 16 or 0x80000 or - 524288.)

    + with the current debug version (LLVMDebugVersion = 8 << 16 or + 0x80000 or 524288.)

    The details of the various descriptors follow.

    -
    - - + -
    +
    @@ -335,6 +337,10 @@ height="369">
       i1,        ;; True if this is optimized.
       metadata,  ;; Flags
       i32        ;; Runtime version
    +  metadata   ;; List of enums types
    +  metadata   ;; List of retained types
    +  metadata   ;; List of subprograms
    +  metadata   ;; List of global variables
     }
     
    @@ -346,16 +352,19 @@ height="369"> that produced it.

    Compile unit descriptors provide the root context for objects declared in a - specific compilation unit. File descriptors are defined using this context.

    + specific compilation unit. File descriptors are defined using this context. + These descriptors are collected by a named metadata + !llvm.dbg.cu. Compile unit descriptor keeps track of subprograms, + global variables and type information.
    - + -
    +
    @@ -364,7 +373,7 @@ height="369">
                  ;; (DW_TAG_file_type)
       metadata,  ;; Source file name
       metadata,  ;; Source file directory (includes trailing slash)
    -  metadata   ;; Reference to compile unit where defined
    +  metadata   ;; Unused
     }
     
    @@ -374,17 +383,16 @@ height="369"> provide context for source line correspondence.

    Each input file is encoded as a separate file descriptor in LLVM debugging - information output. Each file descriptor would be defined using a - compile unit.

    + information output.

    - + -
    +
    @@ -413,11 +421,11 @@ global variables are collected by named metadata !llvm.dbg.gv.

    - + -
    +
    @@ -433,15 +441,17 @@ global variables are collected by named metadata !llvm.dbg.gv.

    i32, ;; Line number where defined metadata, ;; Reference to type descriptor i1, ;; True if the global is local to compile unit (static) - i1 ;; True if the global is defined in the compile unit (not extern) - i32 ;; Virtuality, e.g. dwarf::DW_VIRTUALITY__virtual - i32 ;; Index into a virtual function + i1, ;; True if the global is defined in the compile unit (not extern) + i32, ;; Virtuality, e.g. dwarf::DW_VIRTUALITY__virtual + i32, ;; Index into a virtual function metadata, ;; indicates which base type contains the vtable pointer for the ;; derived class - i1 ;; isArtificial - i1 ;; isOptimized - Function *;; Pointer to LLVM function - metadata ;; Lists function template parameters + i32, ;; Flags - Artifical, Private, Protected, Explicit, Prototyped. + i1, ;; isOptimized + Function *,;; Pointer to LLVM function + metadata, ;; Lists function template parameters + metadata ;; Function declaration descriptor + metadata ;; List of function variables }
    @@ -449,18 +459,16 @@ global variables are collected by named metadata !llvm.dbg.gv.

    These descriptors provide debug information about functions, methods and subprograms. They provide details such as name, return types and the source location where the subprogram is defined. - All subprogram descriptors are collected by a named metadata - !llvm.dbg.sp.

    - + -
    +
    @@ -475,25 +483,38 @@ global variables are collected by named metadata !llvm.dbg.gv.

    -

    These descriptors provide debug information about nested blocks within a +

    This descriptor provides debug information about nested blocks within a subprogram. The line number and column numbers are used to dinstinguish two lexical blocks at same depth.

    +
    +
    +!3 = metadata !{
    +  i32,     ;; Tag = 11 + LLVMDebugVersion (DW_TAG_lexical_block)
    +  metadata ;; Reference to the scope we're annotating with a file change
    +  metadata,;; Reference to the file the scope is enclosed in.
    +}
    +
    +
    + +

    This descriptor provides a wrapper around a lexical scope to handle file + changes in the middle of a lexical block.

    +
    - + -
    +
     !4 = metadata !{
       i32,      ;; Tag = 36 + LLVMDebugVersion 
                 ;; (DW_TAG_base_type)
    -  metadata, ;; Reference to context (typically a compile unit)
    +  metadata, ;; Reference to context 
       metadata, ;; Name (may be "" for anonymous types)
       metadata, ;; Reference to file where defined (may be NULL)
       i32,      ;; Line number where defined (may be 0)
    @@ -508,7 +529,7 @@ global variables are collected by named metadata !llvm.dbg.gv.

    These descriptors define primitive types used in the code. Example int, bool and float. The context provides the scope of the type, which is usually the - top level. Since basic types are not usually user defined the compile unit + top level. Since basic types are not usually user defined the context and line number can be left as NULL and 0. The size, alignment and offset are expressed in bits and can be 64 bit values. The alignment is used to round the offset when embedded in a @@ -534,11 +555,11 @@ DW_ATE_unsigned_char = 8

    - + -
    +
    @@ -551,8 +572,9 @@ DW_ATE_unsigned_char = 8
       i64,      ;; Size in bits
       i64,      ;; Alignment in bits
       i64,      ;; Offset in bits
    +  i32,      ;; Flags to encode attributes, e.g. private
       metadata, ;; Reference to type derived from
    -  metadata, ;; (optional) Name of the Objective C property assoicated with 
    +  metadata, ;; (optional) Name of the Objective C property associated with 
                 ;; Objective-C an ivar 
       metadata, ;; (optional) Name of the Objective C property getter selector.
       metadata, ;; (optional) Name of the Objective C property setter selector.
    @@ -587,13 +609,13 @@ DW_TAG_restrict_type    = 55
     
     

    DW_TAG_typedef is used to provide a name for the derived type.

    -

    DW_TAG_pointer_type,DW_TAG_reference_type, - DW_TAG_const_type, DW_TAG_volatile_type - and DW_TAG_restrict_type are used to qualify +

    DW_TAG_pointer_type, DW_TAG_reference_type, + DW_TAG_const_type, DW_TAG_volatile_type and + DW_TAG_restrict_type are used to qualify the derived type.

    Derived type location can be determined - from the compile unit and line number. The size, alignment and offset are + from the context and line number. The size, alignment and offset are expressed in bits and can be 64 bit values. The alignment is used to round the offset when embedded in a composite type (example to keep float doubles on 64 bit boundaries.) The offset is @@ -606,11 +628,11 @@ DW_TAG_restrict_type = 55

    - + -
    +
    @@ -683,7 +705,7 @@ DW_TAG_inheritance      = 28
        the formal arguments to the subroutine.

    Composite type location can be - determined from the compile unit and line number. The size, alignment and + determined from the context and line number. The size, alignment and offset are expressed in bits and can be 64 bit values. The alignment is used to round the offset when embedded in a composite type (as an example, to keep @@ -693,11 +715,11 @@ DW_TAG_inheritance = 28

    - + -
    +
    @@ -719,11 +741,11 @@ DW_TAG_inheritance      = 28
     
    - + -
    +
    @@ -743,11 +765,11 @@ DW_TAG_inheritance      = 28
     
    - + -
    +
    @@ -758,7 +780,9 @@ DW_TAG_inheritance      = 28
       metadata, ;; Reference to file where defined
       i32,      ;; 24 bit - Line number where defined
                 ;; 8 bit - Argument number. 1 indicates 1st argument.
    -  metadata  ;; Type descriptor
    +  metadata, ;; Type descriptor
    +  i32,      ;; flags
    +  metadata  ;; (optional) Reference to inline location
     }
     
    @@ -780,45 +804,45 @@ DW_TAG_return_variable = 258 has no source correspondent.

    The context is either the subprogram or block where the variable is defined. - Name the source variable name. Compile unit and line indicate where the + Name the source variable name. Context and line indicate where the variable was defined. Type descriptor defines the declared type of the variable.

    +
    + - + -
    +

    LLVM uses several intrinsic functions (name prefixed with "llvm.dbg") to provide debug information at various points in generated code.

    -
    - - + -
    +
       void %llvm.dbg.declare(metadata, metadata)
     
    -

    This intrinsic provides information about a local element (ex. variable.) The - first argument is metadata holding alloca for the variable. The - second argument is metadata containing description of the variable.

    +

    This intrinsic provides information about a local element (e.g., variable). The + first argument is metadata holding the alloca for the variable. The + second argument is metadata containing a description of the variable.

    - + -
    +
       void %llvm.dbg.value(metadata, i64, metadata)
     
    @@ -826,16 +850,18 @@ DW_TAG_return_variable = 258

    This intrinsic provides information when a user source variable is set to a new value. The first argument is the new value (wrapped as metadata). The second argument is the offset in the user source variable where the new value - is written. The third argument is metadata containing description of the - user source variable.

    + is written. The third argument is metadata containing a description of the + user source variable.

    +
    +
    - + -
    +

    In many languages, the local variables in functions can have their lifetimes or scopes limited to a subset of a function. In the C family of languages, for example, variables are only live (readable and writable) within the @@ -993,13 +1019,15 @@ call void @llvm.dbg.declare(metadata, metadata !12), !dbg !14

    +
    + - + -
    +

    The C and C++ front-ends represent information about the program in a format that is effectively identical @@ -1020,14 +1048,12 @@ call void @llvm.dbg.declare(metadata, metadata !12), !dbg !14

    The following sections provide examples of various C/C++ constructs and the debug information that would best describe those constructs.

    -
    - - + -
    +

    Given the source files MySource.cpp and MyHeader.h located in the directory /Users/mine/sources, the following code:

    @@ -1101,11 +1127,11 @@ using Instruction::getMetadata() and
    - + -
    +

    Given an integer global variable declared as follows:

    @@ -1171,11 +1197,11 @@ int MyGlobal = 100;
    - + -
    +

    Given a function declared as follows:

    @@ -1228,22 +1254,20 @@ define i32 @main(i32 %argc, i8** %argv) {
    - + -
    +

    The following are the basic type descriptors for C/C++ core types:

    -
    - -
    +

    bool -

    + -
    +
    @@ -1265,11 +1289,11 @@ define i32 @main(i32 %argc, i8** %argv) {
     
    -
    +

    char -

    + -
    +
    @@ -1291,11 +1315,11 @@ define i32 @main(i32 %argc, i8** %argv) {
     
    - + -
    +
    @@ -1317,11 +1341,11 @@ define i32 @main(i32 %argc, i8** %argv) {
     
    -
    +

    short -

    + -
    +
    @@ -1343,11 +1367,11 @@ define i32 @main(i32 %argc, i8** %argv) {
     
    - + -
    +
    @@ -1369,11 +1393,11 @@ define i32 @main(i32 %argc, i8** %argv) {
     
    -
    +

    int -

    + -
    +
    @@ -1394,11 +1418,11 @@ define i32 @main(i32 %argc, i8** %argv) {
     
    - + -
    +
    @@ -1420,11 +1444,11 @@ define i32 @main(i32 %argc, i8** %argv) {
     
    - + -
    +
    @@ -1446,11 +1470,11 @@ define i32 @main(i32 %argc, i8** %argv) {
     
    - + -
    +
    @@ -1472,11 +1496,11 @@ define i32 @main(i32 %argc, i8** %argv) {
     
    -
    +

    float -

    + -
    +
    @@ -1498,11 +1522,11 @@ define i32 @main(i32 %argc, i8** %argv) {
     
    -
    +

    double -

    + -
    +
    @@ -1523,12 +1547,14 @@ define i32 @main(i32 %argc, i8** %argv) {
     
     
    +
    + - + -
    +

    Given the following as an example of C/C++ derived type:

    @@ -1609,11 +1635,11 @@ typedef const int *IntPtr;
    - + -
    +

    Given the following as an example of C/C++ struct type:

    @@ -1722,11 +1748,11 @@ struct Color {
    - + -
    +

    Given the following as an example of C/C++ enumeration type:

    @@ -1787,6 +1813,309 @@ enum Trees {
    +
    + + + +

    + Debugging information format +

    + +
    + +

    + Debugging Information Extension for Objective C +Properties +

    +
    + +

    + Introduction +

    + + +
    +

    Objective C provides a simpler way to declare and define accessor methods +using declared properties. The language provides features to declare a +property and to let compiler synthesize accessor methods. +

    + +

    The debugger lets developer inspect Objective C interfaces and their +instance variables and class variables. However, the debugger does not know +anything about the properties defined in Objective C interfaces. The debugger +consumes information generated by compiler in DWARF format. The format does +not support encoding of Objective C properties. This proposal describes DWARF +extensions to encode Objective C properties, which the debugger can use to let +developers inspect Objective C properties. +

    + +
    + + + +

    + Proposal +

    + + +
    +

    Objective C properties exist separately from class members. A property +can be defined only by "setter" and "getter" selectors, and +be calculated anew on each access. Or a property can just be a direct access +to some declared ivar. Finally it can have an ivar "automatically +synthesized" for it by the compiler, in which case the property can be +referred to in user code directly using the standard C dereference syntax as +well as through the property "dot" syntax, but there is no entry in +the @interface declaration corresponding to this ivar. +

    +

    +To facilitate debugging, these properties we will add a new DWARF TAG into the +DW_TAG_structure_type definition for the class to hold the description of a +given property, and a set of DWARF attributes that provide said description. +The property tag will also contain the name and declared type of the property. +

    +

    +If there is a related ivar, there will also be a DWARF property attribute placed +in the DW_TAG_member DIE for that ivar referring back to the property TAG for +that property. And in the case where the compiler synthesizes the ivar directly, +the compiler is expected to generate a DW_TAG_member for that ivar (with the +DW_AT_artificial set to 1), whose name will be the name used to access this +ivar directly in code, and with the property attribute pointing back to the +property it is backing. +

    +

    +The following examples will serve as illustration for our discussion: +

    + +
    +
    +@interface I1 { 
    +  int n2;
    +} 
    +
    +@property int p1; 
    +@property int p2; 
    +@end
    +
    +@implementation I1 
    +@synthesize p1; 
    +@synthesize p2 = n2; 
    +@end
    +
    +
    + +

    +This produces the following DWARF (this is a "pseudo dwarfdump" output): +

    +
    +
    +0x00000100:  TAG_structure_type [7] * 
    +               AT_APPLE_runtime_class( 0x10 )
    +               AT_name( "I1" )
    +               AT_decl_file( "Objc_Property.m" ) 
    +               AT_decl_line( 3 )
    +
    +0x00000110    TAG_APPLE_property
    +                AT_name ( "p1" )
    +                AT_type ( {0x00000150} ( int ) )
    +
    +0x00000120:   TAG_APPLE_property
    +                AT_name ( "p2" )
    +                AT_type ( {0x00000150} ( int ) )
    +
    +0x00000130:   TAG_member [8] 
    +                AT_name( "_p1" )
    +                AT_APPLE_property ( {0x00000110} "p1" )
    +                AT_type( {0x00000150} ( int ) )
    +                AT_artificial ( 0x1 )
    +
    +0x00000140:    TAG_member [8] 
    +                 AT_name( "n2" )
    +                 AT_APPLE_property ( {0x00000120} "p2" )
    +                 AT_type( {0x00000150} ( int ) )
    +
    +0x00000150:  AT_type( ( int ) )
    +
    +
    + +

    Note, the current convention is that the name of the ivar for an +auto-synthesized property is the name of the property from which it derives with +an underscore prepended, as is shown in the example. +But we actually don't need to know this convention, since we are given the name +of the ivar directly. +

    + +

    +Also, it is common practice in ObjC to have different property declarations in +the @interface and @implementation - e.g. to provide a read-only property in +the interface,and a read-write interface in the implementation. In that case, +the compiler should emit whichever property declaration will be in force in the +current translation unit. +

    + +

    Developers can decorate a property with attributes which are encoded using +DW_AT_APPLE_property_attribute. +

    + +
    +
    +@property (readonly, nonatomic) int pr;
    +
    +
    +

    +Which produces a property tag: +

    +

    +
    +TAG_APPLE_property [8] 
    +  AT_name( "pr" ) 
    +  AT_type ( {0x00000147} (int) ) 
    +  AT_APPLE_property_attribute (DW_APPLE_PROPERTY_readonly, DW_APPLE_PROPERTY_nonatomic)
    +
    +
    + +

    The setter and getter method names are attached to the property using +DW_AT_APPLE_property_setter and DW_AT_APPLE_property_getter attributes. +

    +
    +
    +@interface I1 
    +@property (setter=myOwnP3Setter:) int p3; 
    +-(void)myOwnP3Setter:(int)a; 
    +@end
    +
    +@implementation I1 
    +@synthesize p3;
    +-(void)myOwnP3Setter:(int)a{ } 
    +@end
    +
    +
    + +

    +The DWARF for this would be: +

    +
    +
    +0x000003bd: TAG_structure_type [7] * 
    +              AT_APPLE_runtime_class( 0x10 )
    +              AT_name( "I1" )
    +              AT_decl_file( "Objc_Property.m" ) 
    +              AT_decl_line( 3 )
    +
    +0x000003cd      TAG_APPLE_property
    +                  AT_name ( "p3" )
    +                  AT_APPLE_property_setter ( "myOwnP3Setter:" )
    +                  AT_type( {0x00000147} ( int ) )
    +              
    +0x000003f3:     TAG_member [8] 
    +                  AT_name( "_p3" ) 
    +                  AT_type ( {0x00000147} ( int ) )
    +                  AT_APPLE_property ( {0x000003cd} )
    +                  AT_artificial ( 0x1 )
    +
    +
    + +
    + + +

    + New DWARF Tags +

    + + +
    + + + + + + + + + +
    TAGValue
    DW_TAG_APPLE_property0x4200
    + +
    + + +

    + New DWARF Attributes +

    + + +
    + + + + + + + + + + + + + + + + + + + + + + + + + + +
    AttributeValueClasses
    DW_AT_APPLE_property0x3fedReference
    DW_AT_APPLE_property_getter0x3fe9String
    DW_AT_APPLE_property_setter0x3feaString
    DW_AT_APPLE_property_attribute0x3febConstant
    + +
    + + +

    + New DWARF Constants +

    + + +
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameValue
    DW_AT_APPLE_PROPERTY_readonly0x1
    DW_AT_APPLE_PROPERTY_readwrite0x2
    DW_AT_APPLE_PROPERTY_assign0x4
    DW_AT_APPLE_PROPERTY_retain0x8
    DW_AT_APPLE_PROPERTY_copy0x10
    DW_AT_APPLE_PROPERTY_nonatomic0x20
    + +
    +
    +
    +