ld: Write globals stream in PDB

This commit is contained in:
Mark Harmstone 2022-12-09 01:52:38 +00:00 committed by Alan Modra
parent 817840046a
commit 81814b6f5b
9 changed files with 2234 additions and 44 deletions

1008
ld/pdb.c

File diff suppressed because it is too large Load Diff

View File

@ -70,7 +70,21 @@
#define LF_QUADWORD 0x8009 #define LF_QUADWORD 0x8009
#define LF_UQUADWORD 0x800a #define LF_UQUADWORD 0x800a
#define S_END 0x0006
#define S_CONSTANT 0x1107
#define S_UDT 0x1108
#define S_LDATA32 0x110c
#define S_GDATA32 0x110d
#define S_PUB32 0x110e #define S_PUB32 0x110e
#define S_LPROC32 0x110f
#define S_GPROC32 0x1110
#define S_LTHREAD32 0x1112
#define S_GTHREAD32 0x1113
#define S_PROCREF 0x1125
#define S_LPROCREF 0x1127
#define S_LPROC32_ID 0x1146
#define S_GPROC32_ID 0x1147
#define S_PROC_ID_END 0x114f
/* PDBStream70 in pdb1.h */ /* PDBStream70 in pdb1.h */
struct pdb_stream_70 struct pdb_stream_70
@ -109,6 +123,8 @@ struct pdb_tpi_stream_header
#define TPI_FIRST_INDEX 0x1000 #define TPI_FIRST_INDEX 0x1000
#define NUM_TPI_HASH_BUCKETS 0x3ffff #define NUM_TPI_HASH_BUCKETS 0x3ffff
#define NUM_GLOBALS_HASH_BUCKETS 4096
/* NewDBIHdr in dbi.h */ /* NewDBIHdr in dbi.h */
struct pdb_dbi_stream_header struct pdb_dbi_stream_header
{ {
@ -198,6 +214,7 @@ struct optional_dbg_header
#define CV_SIGNATURE_C13 4 #define CV_SIGNATURE_C13 4
#define DEBUG_S_SYMBOLS 0xf1
#define DEBUG_S_LINES 0xf2 #define DEBUG_S_LINES 0xf2
#define DEBUG_S_STRINGTABLE 0xf3 #define DEBUG_S_STRINGTABLE 0xf3
#define DEBUG_S_FILECHKSMS 0xf4 #define DEBUG_S_FILECHKSMS 0xf4
@ -540,6 +557,66 @@ struct lf_udt_mod_src_line
uint16_t module_no; uint16_t module_no;
} ATTRIBUTE_PACKED; } ATTRIBUTE_PACKED;
/* DATASYM32 in cvinfo.h */
struct datasym
{
uint16_t size;
uint16_t kind;
uint32_t type;
uint32_t offset;
uint16_t section;
char name[];
} ATTRIBUTE_PACKED;
/* PROCSYM32 in cvinfo.h */
struct procsym
{
uint16_t size;
uint16_t kind;
uint32_t parent;
uint32_t end;
uint32_t next;
uint32_t proc_len;
uint32_t debug_start;
uint32_t debug_end;
uint32_t type;
uint32_t offset;
uint16_t section;
uint8_t flags;
char name[];
} ATTRIBUTE_PACKED;
/* REFSYM2 in cvinfo.h */
struct refsym
{
uint16_t size;
uint16_t kind;
uint32_t sum_name;
uint32_t symbol_offset;
uint16_t mod;
char name[];
} ATTRIBUTE_PACKED;
/* UDTSYM in cvinfo.h */
struct udtsym
{
uint16_t size;
uint16_t kind;
uint32_t type;
char name[];
} ATTRIBUTE_PACKED;
/* CONSTSYM in cvinfo.h */
struct constsym
{
uint16_t size;
uint16_t kind;
uint32_t type;
uint16_t value;
/* then actual value if value >= 0x8000 */
char name[];
} ATTRIBUTE_PACKED;
extern bool create_pdb_file (bfd *, const char *, const unsigned char *); extern bool create_pdb_file (bfd *, const char *, const unsigned char *);
#endif #endif

View File

@ -0,0 +1,57 @@
*: file format binary
Contents of section .data:
0000 ffffffff 1a092ff1 d0000000 64020000 ....../.....d...
0010 fd000000 01000000 35010000 01000000 ........5.......
0020 15000000 01000000 19010000 01000000 ................
0030 c1000000 01000000 b9010000 01000000 ................
0040 d5000000 01000000 61010000 01000000 ........a.......
0050 e9000000 01000000 11020000 01000000 ................
0060 e9010000 01000000 d5010000 01000000 ................
0070 49010000 01000000 a5010000 01000000 I...............
0080 99010000 01000000 85000000 01000000 ................
0090 01000000 01000000 99000000 01000000 ................
00a0 7d010000 01000000 ad000000 01000000 }...............
00b0 5d000000 01000000 49000000 01000000 ].......I.......
00c0 21000000 02000000 35000000 01000000 !.......5.......
00d0 fd010000 01000000 71000000 01000000 ........q.......
00e0 00000000 00000000 00000000 00000000 ................
00f0 00000000 00000000 00000000 00000000 ................
0100 00000000 00000000 00000000 00000000 ................
0110 00000000 00000000 00000000 00000000 ................
0120 00000000 00000000 00000000 00000000 ................
0130 00000000 00000000 00000000 00000000 ................
0140 00000000 00000000 00000000 00000000 ................
0150 00000002 00000000 00000000 00000000 ................
0160 00000000 00000000 00000000 00000000 ................
0170 00000000 00020000 00000000 00000000 ................
0180 00000000 00000000 00000000 00000000 ................
0190 00000000 00000001 00000000 00000000 ................
01a0 00000000 00000000 00000000 00000000 ................
01b0 00000000 00000000 00000000 00000000 ................
01c0 00000000 00000000 00000000 00000000 ................
01d0 00000000 00000000 00000000 00000000 ................
01e0 08001000 00000000 00000000 00000040 ...............@
01f0 04002000 00000000 00000000 00000000 .. .............
0200 00000000 00000001 00000000 00000000 ................
0210 00000000 00000000 00000000 00000000 ................
0220 00000000 00000000 00000000 00000000 ................
0230 00000000 00000000 00080000 00004000 ..............@.
0240 00000000 00000000 00100010 00000000 ................
0250 40000000 00000000 00000000 00000000 @...............
0260 00000000 00000800 00000000 00000000 ................
0270 00000008 00000000 00000000 00000000 ................
0280 00000000 02004000 00000000 00000000 ......@.........
0290 00000000 00008000 00000000 00000000 ................
02a0 00000000 00000000 10000000 00000000 ................
02b0 00000000 00000000 00000000 00800000 ................
02c0 00000000 00000000 00002000 00010000 .......... .....
02d0 00000000 00000000 00000000 00000040 ...............@
02e0 00000000 00000000 0c000000 18000000 ................
02f0 24000000 30000000 3c000000 48000000 $...0...<...H...
0300 54000000 60000000 6c000000 78000000 T...`...l...x...
0310 84000000 90000000 9c000000 a8000000 ................
0320 b4000000 c0000000 d8000000 e4000000 ................
0330 f0000000 fc000000 08010000 20010000 ............ ...
0340 2c010000 ,...

View File

@ -0,0 +1,61 @@
*: file format binary
Contents of section .data:
0000 12002511 00000000 04000000 01007072 ..%...........pr
0010 6f633200 0a000811 04100000 62617200 oc2.........bar.
0020 12000c11 00100000 08000000 02006c76 ..............lv
0030 61723100 12000c11 00100000 0c000000 ar1.............
0040 02006c76 61723100 12000c11 00100000 ..lvar1.........
0050 00000000 03006c76 61723200 12000d11 ......lvar2.....
0060 00100000 18000000 02006776 61723100 ..........gvar1.
0070 12000d11 00100000 04000000 03006776 ..............gv
0080 61723200 12002511 00000000 54000000 ar2...%.....T...
0090 02007072 6f633100 12002511 00000000 ..proc1...%.....
00a0 88000000 02007072 6f633200 12002711 ......proc2...'.
00b0 00000000 f0000000 02007072 6f633300 ..........proc3.
00c0 12002711 00000000 24010000 02007072 ..'.....$.....pr
00d0 6f633400 12002511 00000000 58010000 oc4...%.....X...
00e0 02007072 6f633500 12002511 00000000 ..proc5...%.....
00f0 8c010000 02007072 6f633600 1a002511 ......proc6...%.
0100 00000000 c0010000 0200666f 6f3a3a6d ..........foo::m
0110 6574686f 64000000 1a002511 00000000 ethod.....%.....
0120 f8010000 0200666f 6f3a3a6d 6574686f ......foo::metho
0130 64320000 12002711 00000000 30020000 d2....'.....0...
0140 02007072 6f633900 16002511 00000000 ..proc9...%.....
0150 64020000 02007072 6f633130 00000000 d.....proc10....
0160 1a002711 00000000 98020000 0200666f ..'...........fo
0170 6f3a3a6d 6574686f 64330000 1a002711 o::method3....'.
0180 00000000 d0020000 0200666f 6f3a3a6d ..........foo::m
0190 6574686f 64340000 0a000811 0a100000 ethod4..........
01a0 666f6f00 12000711 75000000 2a00616e foo.....u...*.an
01b0 73776572 00f3f2f1 1a000711 23000000 swer........#...
01c0 0a80efcd ab896745 2301616e 73776572 ......gE#.answer
01d0 3200f2f1 12001211 00100000 20000000 2........... ...
01e0 02006c76 61723500 12001211 00100000 ..lvar5.........
01f0 12000000 03006c76 61723600 12001311 ......lvar6.....
0200 00100000 1c000000 02006776 61723300 ..........gvar3.
0210 12001311 00100000 08000000 03006776 ..............gv
0220 61723400 12000e11 00000000 18000000 ar4.............
0230 02006776 61723100 12000e11 00000000 ..gvar1.........
0240 04000000 03006776 61723200 12000e11 ......gvar2.....
0250 00000000 0c000000 03007072 6f633100 ..........proc1.
0260 12000e11 02000000 06000000 01007072 ..............pr
0270 6f633200 12000e11 00000000 0d000000 oc2.............
0280 03007072 6f633300 12000e11 02000000 ..proc3.........
0290 07000000 01007072 6f633400 12000e11 ......proc4.....
02a0 00000000 0e000000 03007072 6f633500 ..........proc5.
02b0 12000e11 02000000 08000000 01007072 ..............pr
02c0 6f633600 12000e11 00000000 0f000000 oc6.............
02d0 03007072 6f633700 12000e11 02000000 ..proc7.........
02e0 09000000 01007072 6f633800 12000e11 ......proc8.....
02f0 00000000 10000000 03007072 6f633900 ..........proc9.
0300 16000e11 02000000 0a000000 01007072 ..............pr
0310 6f633130 00000000 16000e11 00000000 oc10............
0320 11000000 03007072 6f633131 00000000 ......proc11....
0330 16000e11 02000000 0b000000 01007072 ..............pr
0340 6f633132 00000000 12000e11 00000000 oc12............
0350 1c000000 02006776 61723300 12000e11 ......gvar3.....
0360 00000000 08000000 03006776 61723400 ..........gvar4.
0370 12000e11 02000000 00000000 01006d61 ..............ma
0380 696e0000 in..

View File

@ -0,0 +1,8 @@
*: file format binary
Contents of section .data:
0000 04000000 2e001011 00000000 34000000 ............4...
0010 00000000 01000000 00000000 00000000 ................
0020 02100000 06000000 01000070 726f6332 ...........proc2
0030 00f3f2f1 02000600 00000000 ............

View File

@ -0,0 +1,56 @@
*: file format binary
Contents of section .data:
0000 04000000 12000c11 00100000 08000000 ................
0010 02006c76 61723100 12000c11 00100000 ..lvar1.........
0020 08000000 02006c76 61723100 12000c11 ......lvar1.....
0030 00100000 0c000000 02006c76 61723100 ..........lvar1.
0040 12000c11 00100000 00000000 03006c76 ..............lv
0050 61723200 2e001011 00000000 84000000 ar2.............
0060 00000000 01000000 00000000 00000000 ................
0070 05100000 0c000000 03000070 726f6331 ...........proc1
0080 00f3f2f1 02000600 2e001011 00000000 ................
0090 ec000000 00000000 01000000 00000000 ................
00a0 00000000 05100000 06000000 01000070 ...............p
00b0 726f6332 00f3f2f1 0a000811 04100000 roc2............
00c0 62617200 12000c11 00100000 10000000 bar.............
00d0 02006c76 61723300 12001211 00100000 ..lvar3.........
00e0 14000000 02006c76 61723400 02000600 ......lvar4.....
00f0 2e000f11 00000000 20010000 00000000 ........ .......
0100 01000000 00000000 00000000 05100000 ................
0110 0d000000 03000070 726f6333 00f3f2f1 .......proc3....
0120 02000600 2e000f11 00000000 54010000 ............T...
0130 00000000 01000000 00000000 00000000 ................
0140 05100000 07000000 01000070 726f6334 ...........proc4
0150 00f3f2f1 02000600 2e001011 00000000 ................
0160 88010000 00000000 01000000 00000000 ................
0170 00000000 05100000 0e000000 03000070 ...............p
0180 726f6335 00f3f2f1 02000600 2e001011 roc5............
0190 00000000 bc010000 00000000 01000000 ................
01a0 00000000 00000000 05100000 08000000 ................
01b0 01000070 726f6336 00f3f2f1 02000600 ...proc6........
01c0 32001011 00000000 f4010000 00000000 2...............
01d0 01000000 00000000 00000000 05100000 ................
01e0 0f000000 03000066 6f6f3a3a 6d657468 .......foo::meth
01f0 6f6400f1 02000600 32001011 00000000 od......2.......
0200 2c020000 00000000 01000000 00000000 ,...............
0210 00000000 05100000 09000000 01000066 ...............f
0220 6f6f3a3a 6d657468 6f643200 02000600 oo::method2.....
0230 2e000f11 00000000 60020000 00000000 ........`.......
0240 01000000 00000000 00000000 05100000 ................
0250 10000000 03000070 726f6339 00f3f2f1 .......proc9....
0260 02000600 2e001011 00000000 94020000 ................
0270 00000000 01000000 00000000 00000000 ................
0280 05100000 0a000000 01000070 726f6331 ...........proc1
0290 3000f2f1 02000600 32000f11 00000000 0.......2.......
02a0 cc020000 00000000 01000000 00000000 ................
02b0 00000000 05100000 11000000 03000066 ...............f
02c0 6f6f3a3a 6d657468 6f643300 02000600 oo::method3.....
02d0 32000f11 00000000 04030000 00000000 2...............
02e0 01000000 00000000 00000000 05100000 ................
02f0 0b000000 01000066 6f6f3a3a 6d657468 .......foo::meth
0300 6f643400 02000600 12001211 00100000 od4.............
0310 20000000 02006c76 61723500 12001211 .....lvar5.....
0320 00100000 12000000 03006c76 61723600 ..........lvar6.
0330 00000000 ....

View File

@ -0,0 +1,110 @@
.equ CV_SIGNATURE_C13, 4
.equ DEBUG_S_SYMBOLS, 0xf1
.equ T_UINT4, 0x0075
.equ LF_MODIFIER, 0x1001
.equ LF_PROCEDURE, 0x1008
.equ LF_ARGLIST, 0x1201
.equ LF_FIELDLIST, 0x1203
.equ LF_STRUCTURE, 0x1505
.equ LF_MEMBER, 0x150d
.equ S_END, 0x0006
.equ S_UDT, 0x1108
.equ S_GPROC32, 0x1110
.section ".debug$S", "rn"
.long CV_SIGNATURE_C13
.long DEBUG_S_SYMBOLS
.long .syms_end - .syms_start
.syms_start:
.gproc2:
.short .gproc2_end - .gproc2 - 2
.short S_GPROC32
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long 1 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x1002 # type
.secrel32 proc2
.secidx proc2
.byte 0 # flags
.asciz "proc2"
.byte 0xf3 # padding
.byte 0xf2 # padding
.byte 0xf1 # padding
.gproc2_end:
.short .udt1 - .gproc2_end - 2
.short S_END
.udt1:
.short .syms_end - .udt1 - 2
.short S_UDT
.long 0x1004 # struct bar
.asciz "bar"
.syms_end:
.section ".debug$T", "rn"
.long CV_SIGNATURE_C13
# Type 1000, const uint32_t
.mod1:
.short .arglist1 - .mod1 - 2
.short LF_MODIFIER
.long T_UINT4
.short 1 # const
.p2align 2
# Type 1001, arglist (uint32_t)
.arglist1:
.short .proctype1 - .arglist1 - 2
.short LF_ARGLIST
.long 1 # no. entries
.long T_UINT4
# Type 1002, procedure (return type T_VOID, arglist 1001)
.proctype1:
.short .fieldlist1 - .proctype1 - 2
.short LF_PROCEDURE
.long T_VOID
.byte 0 # calling convention
.byte 0 # attributes
.short 1 # no. parameters
.long 0x1001
# Type 1003, field list for struct bar
.fieldlist1:
.short .struct1 - .fieldlist1 - 2
.short LF_FIELDLIST
.short LF_MEMBER
.short 3 # public
.long T_UINT4
.short 0 # offset
.asciz "num1"
.byte 0xf1 # padding
# Type 1004, declaration of struct bar
.struct1:
.short .types_end - .struct1 - 2
.short LF_STRUCTURE
.short 1 # no. members
.short 0 # property
.long 0x1003 # field list
.long 0 # type derived from
.long 0 # type of vshape table
.short 4 # size
.asciz "bar" # name
.byte 0xf2 # padding
.byte 0xf1 # padding
.types_end:

View File

@ -0,0 +1,737 @@
.equ CV_SIGNATURE_C13, 4
.equ DEBUG_S_SYMBOLS, 0xf1
.equ T_VOID, 0x0003
.equ T_UQUAD, 0x0023
.equ T_UINT4, 0x0075
.equ LF_MODIFIER, 0x1001
.equ LF_POINTER, 0x1002
.equ LF_PROCEDURE, 0x1008
.equ LF_MFUNCTION, 0x1009
.equ LF_ARGLIST, 0x1201
.equ LF_FIELDLIST, 0x1203
.equ LF_CLASS, 0x1504
.equ LF_STRUCTURE, 0x1505
.equ LF_MEMBER, 0x150d
.equ LF_ONEMETHOD, 0x1511
.equ LF_FUNC_ID, 0x1601
.equ LF_MFUNC_ID, 0x1602
.equ LF_UQUADWORD, 0x800a
.equ S_END, 0x0006
.equ S_CONSTANT, 0x1107
.equ S_UDT, 0x1108
.equ S_LDATA32, 0x110c
.equ S_GDATA32, 0x110d
.equ S_LPROC32, 0x110f
.equ S_GPROC32, 0x1110
.equ S_LTHREAD32, 0x1112
.equ S_GTHREAD32, 0x1113
.equ S_LPROC32_ID, 0x1146
.equ S_GPROC32_ID, 0x1147
.equ S_PROC_ID_END, 0x114f
.equ CV_PTR_64, 0xc
.section ".debug$S", "rn"
.long CV_SIGNATURE_C13
.long DEBUG_S_SYMBOLS
.long .syms_end - .syms_start
.syms_start:
.ldata1:
.short .ldata1a - .ldata1 - 2
.short S_LDATA32
.long 0x1000 # const uint32_t
.secrel32 lvar1
.secidx lvar1
.asciz "lvar1"
.ldata1a: # duplicate with same address
.short .ldata1b - .ldata1a - 2
.short S_LDATA32
.long 0x1000 # const uint32_t
.secrel32 lvar1
.secidx lvar1
.asciz "lvar1"
.ldata1b: # duplicate with different address
.short .ldata2 - .ldata1b - 2
.short S_LDATA32
.long 0x1000 # const uint32_t
.secrel32 lvar1a
.secidx lvar1a
.asciz "lvar1"
.ldata2:
.short .gdata1 - .ldata2 - 2
.short S_LDATA32
.long 0x1000 # const uint32_t
.secrel32 lvar2
.secidx lvar2
.asciz "lvar2"
.gdata1:
.short .gdata2 - .gdata1 - 2
.short S_GDATA32
.long 0x1000 # const uint32_t
.secrel32 gvar1
.secidx gvar1
.asciz "gvar1"
.gdata2:
.short .gproc1 - .gdata2 - 2
.short S_GDATA32
.long 0x1000 # const uint32_t
.secrel32 gvar2
.secidx gvar2
.asciz "gvar2"
.gproc1:
.short .gproc1_end - .gproc1 - 2
.short S_GPROC32
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc1_end - proc1 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x1002 # type
.secrel32 proc1
.secidx proc1
.byte 0 # flags
.asciz "proc1"
.byte 0xf3 # padding
.byte 0xf2 # padding
.byte 0xf1 # padding
.gproc1_end:
.short .gproc2 - .gproc1_end - 2
.short S_END
.gproc2:
.short .udt1 - .gproc2 - 2
.short S_GPROC32
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc2_end - proc2 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x1002 # type
.secrel32 proc2
.secidx proc2
.byte 0 # flags
.asciz "proc2"
.byte 0xf3 # padding
.byte 0xf2 # padding
.byte 0xf1 # padding
.udt1:
.short .ldata3 - .udt1 - 2
.short S_UDT
.long 0x1011 # struct bar
.asciz "bar"
.ldata3:
.short .lthread1 - .ldata3 - 2
.short S_LDATA32
.long 0x1000 # const uint32_t
.secrel32 lvar3
.secidx lvar3
.asciz "lvar3"
.lthread1:
.short .gproc2_end - .lthread1 - 2
.short S_LTHREAD32
.long 0x1000 # const uint32_t
.secrel32 lvar4
.secidx lvar4
.asciz "lvar4"
.gproc2_end:
.short .gproc3 - .gproc2_end - 2
.short S_END
.gproc3:
.short .gproc3_end - .gproc3 - 2
.short S_LPROC32
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc3_end - proc3 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x1002 # type
.secrel32 proc3
.secidx proc3
.byte 0 # flags
.asciz "proc3"
.byte 0xf3 # padding
.byte 0xf2 # padding
.byte 0xf1 # padding
.gproc3_end:
.short .gproc4 - .gproc3_end - 2
.short S_END
.gproc4:
.short .gproc4_end - .gproc4 - 2
.short S_LPROC32
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc4_end - proc4 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x1002 # type
.secrel32 proc4
.secidx proc4
.byte 0 # flags
.asciz "proc4"
.byte 0xf3 # padding
.byte 0xf2 # padding
.byte 0xf1 # padding
.gproc4_end:
.short .gproc5 - .gproc4_end - 2
.short S_END
.gproc5:
.short .gproc5_end - .gproc5 - 2
.short S_GPROC32_ID
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc5_end - proc5 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x1003 # func ID
.secrel32 proc5
.secidx proc5
.byte 0 # flags
.asciz "proc5"
.byte 0xf3 # padding
.byte 0xf2 # padding
.byte 0xf1 # padding
.gproc5_end:
.short .gproc6 - .gproc5_end - 2
.short S_PROC_ID_END
.gproc6:
.short .gproc6_end - .gproc6 - 2
.short S_GPROC32_ID
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc6_end - proc6 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x1004 # func ID
.secrel32 proc6
.secidx proc6
.byte 0 # flags
.asciz "proc6"
.byte 0xf3 # padding
.byte 0xf2 # padding
.byte 0xf1 # padding
.gproc6_end:
.short .gproc7 - .gproc6_end - 2
.short S_PROC_ID_END
.gproc7:
.short .gproc7_end - .gproc7 - 2
.short S_GPROC32_ID
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc7_end - proc7 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x100a # func ID
.secrel32 proc7
.secidx proc7
.byte 0 # flags
.asciz "foo::method"
.byte 0xf1 # padding
.gproc7_end:
.short .gproc8 - .gproc7_end - 2
.short S_PROC_ID_END
.gproc8:
.short .gproc8_end - .gproc8 - 2
.short S_GPROC32_ID
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc8_end - proc8 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x100b # func ID
.secrel32 proc8
.secidx proc8
.byte 0 # flags
.asciz "foo::method2"
.gproc8_end:
.short .gproc9 - .gproc8_end - 2
.short S_PROC_ID_END
.gproc9:
.short .gproc9_end - .gproc9 - 2
.short S_LPROC32_ID
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc9_end - proc9 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x100c # func ID
.secrel32 proc9
.secidx proc9
.byte 0 # flags
.asciz "proc9"
.byte 0xf3 # padding
.byte 0xf2 # padding
.byte 0xf1 # padding
.gproc9_end:
.short .gproc10 - .gproc9_end - 2
.short S_PROC_ID_END
.gproc10:
.short .gproc10_end - .gproc10 - 2
.short S_GPROC32_ID
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc10_end - proc10 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x100d # func ID
.secrel32 proc10
.secidx proc10
.byte 0 # flags
.asciz "proc10"
.byte 0xf2 # padding
.byte 0xf1 # padding
.gproc10_end:
.short .gproc11 - .gproc10_end - 2
.short S_PROC_ID_END
.gproc11:
.short .gproc11_end - .gproc11 - 2
.short S_LPROC32_ID
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc11_end - proc11 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x100e # func ID
.secrel32 proc11
.secidx proc11
.byte 0 # flags
.asciz "foo::method3"
.gproc11_end:
.short .gproc12 - .gproc11_end - 2
.short S_PROC_ID_END
.gproc12:
.short .gproc12_end - .gproc12 - 2
.short S_LPROC32_ID
.long 0 # parent
.long 0 # end
.long 0 # next symbol
.long .proc12_end - proc12 # length
.long 0 # debug start offset
.long 0 # debug end offset
.long 0x100f # func ID
.secrel32 proc12
.secidx proc12
.byte 0 # flags
.asciz "foo::method4"
.gproc12_end:
.short .udt2 - .gproc12_end - 2
.short S_PROC_ID_END
.udt2:
.short .constant1 - .udt2 - 2
.short S_UDT
.long 0x1009 # class foo
.asciz "foo"
.constant1:
.short .constant2 - .constant1 - 2
.short S_CONSTANT
.long T_UINT4
.short 42
.asciz "answer"
.byte 0xf3 # padding
.byte 0xf2 # padding
.byte 0xf1 # padding
.constant2:
.short .lthread2 - .constant2 - 2
.short S_CONSTANT
.long T_UQUAD
.short LF_UQUADWORD
.quad 0x0123456789abcdef
.asciz "answer2"
.byte 0xf2 # padding
.byte 0xf1 # padding
.lthread2:
.short .lthread3 - .lthread2 - 2
.short S_LTHREAD32
.long 0x1000 # const uint32_t
.secrel32 lvar5
.secidx lvar5
.asciz "lvar5"
.lthread3:
.short .gthread1 - .lthread3 - 2
.short S_LTHREAD32
.long 0x1000 # const uint32_t
.secrel32 lvar6
.secidx lvar6
.asciz "lvar6"
.gthread1:
.short .gthread2 - .gthread1 - 2
.short S_GTHREAD32
.long 0x1000 # const uint32_t
.secrel32 gvar3
.secidx gvar3
.asciz "gvar3"
.gthread2:
.short .syms_end - .gthread2 - 2
.short S_GTHREAD32
.long 0x1000 # const uint32_t
.secrel32 gvar4
.secidx gvar4
.asciz "gvar4"
.p2align 2
.syms_end:
.section ".debug$T", "rn"
.long CV_SIGNATURE_C13
# Type 1000, const uint32_t
.mod1:
.short .arglist1 - .mod1 - 2
.short LF_MODIFIER
.long T_UINT4
.short 1 # const
.p2align 2
# Type 1001, arglist (uint32_t)
.arglist1:
.short .proctype1 - .arglist1 - 2
.short LF_ARGLIST
.long 1 # no. entries
.long T_UINT4
# Type 1002, procedure (return type T_VOID, arglist 1001)
.proctype1:
.short .funcid1 - .proctype1 - 2
.short LF_PROCEDURE
.long T_VOID
.byte 0 # calling convention
.byte 0 # attributes
.short 1 # no. parameters
.long 0x1001
# Type 1003, func ID for proc5
.funcid1:
.short .funcid2 - .funcid1 - 2
.short LF_FUNC_ID
.long 0 # parent scope
.long 0x1002 # type
.asciz "proc5"
.byte 0xf2 # padding
.byte 0xf1 # padding
# Type 1004, func ID for proc6
.funcid2:
.short .class1 - .funcid2 - 2
.short LF_FUNC_ID
.long 0 # parent scope
.long 0x1002 # type
.asciz "proc6"
.byte 0xf2 # padding
.byte 0xf1 # padding
# Type 1005, forward declaration of class foo
.class1:
.short .ptr1 - .class1 - 2
.short LF_CLASS
.short 0 # no. members
.short 0x80 # property (forward declaration)
.long 0 # field list
.long 0 # type derived from
.long 0 # type of vshape table
.short 0 # size
.asciz "foo" # name
.byte 0xf2 # padding
.byte 0xf1 # padding
# Type 1006, pointer to 1005
.ptr1:
.short .mfunction1 - .ptr1 - 2
.short LF_POINTER
.long 0x1005
.long (8 << 13) | CV_PTR_64
# Type 1007, member function of 1005, return type void, arg list 1001
.mfunction1:
.short .fieldlist1 - .mfunction1 - 2
.short LF_MFUNCTION
.long T_VOID
.long 0x1005
.long 0x1006 # type of "this" pointer
.byte 0 # calling convention
.byte 0 # attributes
.short 1 # no. parameters
.long 0x1001 # arg list
.long 0 # "this" adjustment
# Type 1008, field list for class foo
.fieldlist1:
.short .class2 - .fieldlist1 - 2
.short LF_FIELDLIST
.short LF_ONEMETHOD
.short 0 # method attribute
.long 0x1007 # method type
.asciz "method"
.byte 0xf1 # padding
.short LF_ONEMETHOD
.short 0 # method attribute
.long 0x1007 # method type
.asciz "method2"
.short LF_ONEMETHOD
.short 0 # method attribute
.long 0x1007 # method type
.asciz "method3"
.short LF_ONEMETHOD
.short 0 # method attribute
.long 0x1007 # method type
.asciz "method4"
# Type 1009, actual declaration of class foo
.class2:
.short .mfunc1 - .class2 - 2
.short LF_CLASS
.short 0 # no. members
.short 0 # property
.long 0x1008 # field list
.long 0 # type derived from
.long 0 # type of vshape table
.short 0 # size
.asciz "foo" # name
.byte 0xf2 # padding
.byte 0xf1 # padding
# Type 100a, function "method" within class "foo"
.mfunc1:
.short .mfunc2 - .mfunc1 - 2
.short LF_MFUNC_ID
.long 0x1009 # parent class
.long 0x1002 # function type
.asciz "method"
.byte 0xf1 # padding
# Type 100b, function "method2" within class "foo"
.mfunc2:
.short .funcid3 - .mfunc2 - 2
.short LF_MFUNC_ID
.long 0x1009 # parent class
.long 0x1002 # function type
.asciz "method2"
# Type 100c, func ID for proc9
.funcid3:
.short .funcid4 - .funcid3 - 2
.short LF_FUNC_ID
.long 0 # parent scope
.long 0x1002 # type
.asciz "proc9"
.byte 0xf2 # padding
.byte 0xf1 # padding
# Type 100d, func ID for proc10
.funcid4:
.short .mfunc3 - .funcid4 - 2
.short LF_FUNC_ID
.long 0 # parent scope
.long 0x1002 # type
.asciz "proc10"
.byte 0xf1 # padding
# Type 100e, function "method3" within class "foo"
.mfunc3:
.short .mfunc4 - .mfunc3 - 2
.short LF_MFUNC_ID
.long 0x1009 # parent class
.long 0x1002 # function type
.asciz "method3"
# Type 100f, function "method4" within class "foo"
.mfunc4:
.short .fieldlist2 - .mfunc4 - 2
.short LF_MFUNC_ID
.long 0x1009 # parent class
.long 0x1002 # function type
.asciz "method4"
# Type 1010, field list for struct bar
.fieldlist2:
.short .struct1 - .fieldlist2 - 2
.short LF_FIELDLIST
.short LF_MEMBER
.short 3 # public
.long T_UINT4
.short 0 # offset
.asciz "num1"
.byte 0xf1 # padding
# Type 1011, declaration of struct bar
.struct1:
.short .types_end - .struct1 - 2
.short LF_STRUCTURE
.short 1 # no. members
.short 0 # property
.long 0x1010 # field list
.long 0 # type derived from
.long 0 # type of vshape table
.short 4 # size
.asciz "bar" # name
.byte 0xf2 # padding
.byte 0xf1 # padding
.types_end:
.data
.long 0x12345678
.long 0x12345678
lvar1:
.long 42
lvar1a:
.long 0x12345678
lvar3:
.long 84
lvar4:
.long 85
.global gvar1
gvar1:
.long 43
.global gvar3
gvar3:
.long 41
lvar5:
.long 86
.text
.global main
main:
jmp main
.secrel32 .data
.global proc2
proc2:
nop
.proc2_end:
.global proc4
proc4:
nop
.proc4_end:
.global proc6
proc6:
nop
.proc6_end:
.global proc8
proc8:
nop
.proc8_end:
.global proc10
proc10:
nop
.proc10_end:
.global proc12
proc12:
nop
.proc12_end:
.section "gcsect"
lvar2:
.long 84
.global gvar2
gvar2:
.long 85
.global gvar4
gvar4:
.long 86
.global proc1
proc1:
nop
.proc1_end:
.global proc3
proc3:
nop
.proc3_end:
.global proc5
proc5:
nop
.proc5_end:
.global proc7
proc7:
nop
.proc7_end:
.global proc9
proc9:
nop
.proc9_end:
.global proc11
proc11:
nop
.proc11_end:
lvar6:
.long 86

View File

@ -1451,6 +1451,169 @@ proc test7 { } {
} }
} }
proc test8 { } {
global as
global ar
global ld
global objdump
global srcdir
global subdir
if ![ld_assemble $as $srcdir/$subdir/pdb-syms1a.s tmpdir/pdb-syms1a.o] {
unsupported "Build pdb-syms1a.o"
return
}
if ![ld_assemble $as $srcdir/$subdir/pdb-syms1b.s tmpdir/pdb-syms1b.o] {
unsupported "Build pdb-syms1b.o"
return
}
if ![ld_link $ld "tmpdir/pdb-syms1.exe" "--pdb=tmpdir/pdb-syms1.pdb tmpdir/pdb-syms1a.o tmpdir/pdb-syms1b.o"] {
unsupported "Create PE image with PDB file"
return
}
# get index of globals stream and records stream
set exec_output [run_host_cmd "$ar" "x --output tmpdir tmpdir/pdb-syms1.pdb 0003"]
if ![string match "" $exec_output] {
fail "Could not extract DBI stream"
return
} else {
pass "Extracted DBI stream"
}
set fi [open tmpdir/0003]
fconfigure $fi -translation binary
seek $fi 12
set data [read $fi 2]
binary scan $data s globals_index
seek $fi 6 current
set data [read $fi 2]
binary scan $data s records_index
seek $fi 2 current
set data [read $fi 4]
binary scan $data i mod_info_size
seek $fi 36 current
set mod_info [read $fi $mod_info_size]
close $fi
# get index of first and second module streams
binary scan [string range $mod_info 34 35] s mod1_index
set off 64
set obj1 [string range $mod_info $off [expr [string first \000 $mod_info $off] - 1]]
incr off [expr [string length $obj1] + 1]
set ar1 [string range $mod_info $off [expr [string first \000 $mod_info $off] - 1]]
incr off [expr [string length $ar1] + 1]
if { [expr $off % 4] != 0 } {
set off [expr $off + 4 - ($off % 4)]
}
incr off 34
binary scan [string range $mod_info $off [expr $off + 1]] s mod2_index
# check globals stream
set index_str [format "%04x" $globals_index]
set exec_output [run_host_cmd "$ar" "x --output tmpdir tmpdir/pdb-syms1.pdb $index_str"]
if ![string match "" $exec_output] {
fail "Could not extract globals stream"
return
} else {
pass "Extracted globals stream"
}
set exp [file_contents "$srcdir/$subdir/pdb-syms1-globals.d"]
set got [run_host_cmd "$objdump" "-s --target=binary tmpdir/$index_str"]
if [string match $exp $got] {
pass "Correct globals stream"
} else {
fail "Incorrect globals stream"
}
# check records stream
set index_str [format "%04x" $records_index]
set exec_output [run_host_cmd "$ar" "x --output tmpdir tmpdir/pdb-syms1.pdb $index_str"]
if ![string match "" $exec_output] {
fail "Could not extract records stream"
return
} else {
pass "Extracted records stream"
}
set exp [file_contents "$srcdir/$subdir/pdb-syms1-records.d"]
set got [run_host_cmd "$objdump" "-s --target=binary tmpdir/$index_str"]
if [string match $exp $got] {
pass "Correct records stream"
} else {
fail "Incorrect records stream"
}
# check symbols in first module
set index_str [format "%04x" $mod1_index]
set exec_output [run_host_cmd "$ar" "x --output tmpdir tmpdir/pdb-syms1.pdb $index_str"]
if ![string match "" $exec_output] {
fail "Could not extract first module's symbols"
return
} else {
pass "Extracted first module's symbols"
}
set exp [file_contents "$srcdir/$subdir/pdb-syms1-symbols1.d"]
set got [run_host_cmd "$objdump" "-s --target=binary tmpdir/$index_str"]
if [string match $exp $got] {
pass "Correct symbols in first module's stream"
} else {
fail "Incorrect symbols in first module's stream"
}
# check symbols in second module
set index_str [format "%04x" $mod2_index]
set exec_output [run_host_cmd "$ar" "x --output tmpdir tmpdir/pdb-syms1.pdb $index_str"]
if ![string match "" $exec_output] {
fail "Could not extract second module's symbols"
return
} else {
pass "Extracted second module's symbols"
}
set exp [file_contents "$srcdir/$subdir/pdb-syms1-symbols2.d"]
set got [run_host_cmd "$objdump" "-s --target=binary tmpdir/$index_str"]
if [string match $exp $got] {
pass "Correct symbols in second module's stream"
} else {
fail "Incorrect symbols in second module's stream"
}
}
test1 test1
test2 test2
test3 test3
@ -1458,3 +1621,4 @@ test4
test5 test5
test6 test6
test7 test7
test8