11/*******************************************************************************
2- * Copyright (c) 2007, 2023 Nokia and others.
2+ * Copyright (c) 2007, 2025 Nokia and others.
33 *
44 * This program and the accompanying materials
55 * are made available under the terms of the Eclipse Public License 2.0
1313 * Ling Wang (Nokia) bug 201000
1414 * Serge Beauchamp (Freescale Semiconductor) - Bug 421070
1515 * Red Hat Inc. - add debuginfo and macro section support
16- * John Dallaway - support DWARF v5 content form data (#443)
16+ * John Dallaway - support DWARF v5 content form data (#443, #1135 )
1717 *******************************************************************************/
1818
1919package org .eclipse .cdt .utils .debug .dwarf ;
3737import org .eclipse .cdt .utils .debug .IDebugEntryRequestor ;
3838import org .eclipse .cdt .utils .elf .Elf ;
3939import org .eclipse .cdt .utils .elf .Elf .Section ;
40+ import org .eclipse .core .runtime .ILog ;
4041import org .eclipse .core .runtime .IPath ;
4142import org .eclipse .core .runtime .IProgressMonitor ;
4243import org .eclipse .core .runtime .Path ;
@@ -50,7 +51,7 @@ public class DwarfReader extends Dwarf implements ISymbolReader, ICompileOptions
5051 // These are sections that need be parsed to get the source file list.
5152 final static String [] DWARF_SectionsToParse = { DWARF_DEBUG_INFO , DWARF_DEBUG_LINE , DWARF_DEBUG_ABBREV ,
5253 DWARF_DEBUG_STR , // this is optional. Some compilers don't generate it.
53- DWARF_DEBUG_MACRO , DWARF_DEBUG_LINE_STR };
54+ DWARF_DEBUG_MACRO , DWARF_DEBUG_LINE_STR , DWARF_DEBUG_STR_OFFSETS };
5455
5556 final static String [] DWARF_ALT_SectionsToParse = { DWARF_DEBUG_STR , DWARF_DEBUG_MACRO };
5657
@@ -368,8 +369,8 @@ private void addSourceFilesDwarf5(String cuCompDir, ByteBuffer data, byte offset
368369 data .get (dcf_count );
369370 List <ContentForm > directoryContentForms = new ArrayList <>();
370371 for (int fmt = 0 ; fmt < dcf_count [0 ]; fmt ++) {
371- ContentForm def = readContentForm (data );
372- directoryContentForms .add (def );
372+ ContentForm dcf = readContentForm (data );
373+ directoryContentForms .add (dcf );
373374 }
374375
375376 // read directories
@@ -386,7 +387,10 @@ private void addSourceFilesDwarf5(String cuCompDir, ByteBuffer data, byte offset
386387 dir = new Path (cuCompDir ).append (path );
387388 }
388389 directories .add (dir .toString ());
389- } // TODO: support other DW_LNCT_path forms
390+ } else {
391+ ILog .get ().warn (String .format ("DWARF directory content 0x%x form 0x%x not handled" , //$NON-NLS-1$
392+ contentForm .lnct , contentForm .form ));
393+ }
390394 }
391395 }
392396
@@ -395,8 +399,8 @@ private void addSourceFilesDwarf5(String cuCompDir, ByteBuffer data, byte offset
395399 data .get (fncf_count );
396400 List <ContentForm > fileNameContentForms = new ArrayList <>();
397401 for (int fmt = 0 ; fmt < fncf_count [0 ]; fmt ++) {
398- ContentForm fnef = readContentForm (data );
399- fileNameContentForms .add (fnef );
402+ ContentForm fncf = readContentForm (data );
403+ fileNameContentForms .add (fncf );
400404 }
401405
402406 // read file names
@@ -409,12 +413,17 @@ private void addSourceFilesDwarf5(String cuCompDir, ByteBuffer data, byte offset
409413 && (DwarfConstants .DW_LNCT_path == contentForm .lnct )) {
410414 long offset = readOffset (data , offsetSize );
411415 filename = getPathInLineStr (offset );
412- } // TODO: support other DW_LNCT_path forms
413- if ((DwarfConstants .DW_FORM_udata == contentForm .form )
416+ } else if ((DwarfConstants .DW_FORM_udata == contentForm .form )
414417 && (DwarfConstants .DW_LNCT_directory_index == contentForm .lnct )) {
415418 long directory_index = read_unsigned_leb128 (data );
416419 directory = directories .get ((int ) directory_index );
417- } // TODO: support other DW_LNCT_directory_index forms
420+ } else if ((DwarfConstants .DW_FORM_data16 == contentForm .form )
421+ && (DwarfConstants .DW_LNCT_MD5 == contentForm .lnct )) {
422+ data .get (new byte [16 ]); // skip MD5 digest
423+ } else {
424+ ILog .get ().warn (String .format ("DWARF file content 0x%x form 0x%x not handled" , //$NON-NLS-1$
425+ contentForm .lnct , contentForm .form ));
426+ }
418427 }
419428 if ((null != directory ) && (null != filename )) {
420429 addSourceFile (directory , filename );
@@ -704,8 +713,8 @@ private String addSourceFile(String dir, String name) {
704713
705714 // Override parent: only handle TAG_Compile_Unit.
706715 @ Override
707- void processDebugInfoEntry (IDebugEntryRequestor requestor , AbbreviationEntry entry ,
708- List < Dwarf . AttributeValue > list ) {
716+ void processDebugInfoEntry (IDebugEntryRequestor requestor , AbbreviationEntry entry , List < Dwarf . AttributeValue > list )
717+ throws IOException {
709718 int tag = (int ) entry .tag ;
710719 switch (tag ) {
711720 case DwarfConstants .DW_TAG_compile_unit :
@@ -720,10 +729,14 @@ void processDebugInfoEntry(IDebugEntryRequestor requestor, AbbreviationEntry ent
720729 // Just get the file name of the CU.
721730 // Argument "requestor" is ignored.
722731 @ Override
723- void processCompileUnit (IDebugEntryRequestor requestor , List <AttributeValue > list ) {
732+ void processCompileUnit (IDebugEntryRequestor requestor , List <AttributeValue > list ) throws IOException {
724733
725734 String cuName , cuCompDir ;
726735 int stmtList = -1 ;
736+ ByteBuffer strings = dwarfSections .get (DWARF_DEBUG_STR );
737+ ByteBuffer offsets = dwarfSections .get (DWARF_DEBUG_STR_OFFSETS );
738+ byte offsetSize = (offsets != null ) ? readInitialLengthField (offsets ).offsetSize : -1 ;
739+ long offsetsBase = -1L ;
727740
728741 cuName = cuCompDir = "" ; //$NON-NLS-1$
729742
@@ -736,11 +749,30 @@ void processCompileUnit(IDebugEntryRequestor requestor, List<AttributeValue> lis
736749 cuName = (String ) av .value ;
737750 break ;
738751 case DwarfConstants .DW_AT_comp_dir :
739- cuCompDir = (String ) av .value ;
752+ if ((av .attribute .form == DwarfConstants .DW_FORM_strp )
753+ || (av .attribute .form == DwarfConstants .DW_FORM_line_strp )) {
754+ cuCompDir = (String ) av .value ;
755+ } else if ((av .attribute .form == DwarfConstants .DW_FORM_strx1 ) && (offsets != null )
756+ && (offsetsBase != -1L )) {
757+ int index = ((Number ) av .value ).intValue ();
758+ // read the pointer into .debug_str from .debug_str_offsets
759+ long offset = offsetsBase + (index * offsetSize );
760+ offsets .position ((int ) offset );
761+ long strp = readOffset (offsets , offsetSize );
762+ // read the string from .debug_str
763+ strings .position ((int ) strp );
764+ cuCompDir = readString (strings );
765+ } else {
766+ ILog .get ().warn (String .format ("DW_AT_comp_dir form 0x%x not handled" , av .attribute .form )); //$NON-NLS-1$
767+ }
740768 break ;
741769 case DwarfConstants .DW_AT_stmt_list :
742770 stmtList = ((Number ) av .value ).intValue ();
743771 break ;
772+ case DwarfConstants .DW_AT_str_offsets_base :
773+ // read the base of all offsets into .debug_str_offsets
774+ offsetsBase = (offsetSize == 8 ) ? ((Number ) av .value ).longValue () : ((Number ) av .value ).intValue ();
775+ break ;
744776 default :
745777 break ;
746778 }
0 commit comments