Print this page
5688 ELF tools need to be more careful with dwarf data

*** 535,545 **** fde_count = 0; for (APLIST_TRAVERSE(ofl->ofl_unwind, idx, osp)) { uchar_t *data; size_t size; ! uint64_t off = 0; uint_t cieRflag = 0, ciePflag = 0; Shdr *shdr; /* * remember first UNWIND section to --- 535,546 ---- fde_count = 0; for (APLIST_TRAVERSE(ofl->ofl_unwind, idx, osp)) { uchar_t *data; size_t size; ! uint64_t off = 0, ujunk; ! int64_t sjunk; uint_t cieRflag = 0, ciePflag = 0; Shdr *shdr; /* * remember first UNWIND section to
*** 599,645 **** ndx += strlen(cieaugstr) + 1; /* * calign & dalign */ ! (void) uleb_extract(&data[off], &ndx); ! (void) sleb_extract(&data[off], &ndx); /* * retreg */ ! if (cieversion == 1) ndx++; ! else ! (void) uleb_extract(&data[off], &ndx); /* * we walk through the augmentation * section now looking for the Rflag */ for (cieaugndx = 0; cieaugstr[cieaugndx]; cieaugndx++) { /* BEGIN CSTYLED */ switch (cieaugstr[cieaugndx]) { case 'z': /* size */ ! (void) uleb_extract(&data[off], ! &ndx); break; case 'P': /* personality */ ciePflag = data[off + ndx]; ndx++; /* * Just need to extract the * value to move on to the next * field. */ ! (void) dwarf_ehe_extract( ! &data[off], ! &ndx, ciePflag, ofl->ofl_dehdr->e_ident, B_FALSE, ! shdr->sh_addr, off + ndx, 0); break; case 'R': /* code encoding */ cieRflag = data[off + ndx]; ndx++; --- 600,692 ---- ndx += strlen(cieaugstr) + 1; /* * calign & dalign */ ! if (uleb_extract(&data[off], &ndx, ! size - off, &ujunk) == DW_OVERFLOW) { ! ld_eprintf(ofl, ERR_FATAL, ! MSG_INTL(MSG_SCN_DWFOVRFLW), ! ofl->ofl_name, ! osp->os_name); ! return (S_ERROR); ! } ! ! if (sleb_extract(&data[off], &ndx, ! size - off, &sjunk) == DW_OVERFLOW) { ! ld_eprintf(ofl, ERR_FATAL, ! MSG_INTL(MSG_SCN_DWFOVRFLW), ! ofl->ofl_name, ! osp->os_name); ! return (S_ERROR); ! } /* * retreg */ ! if (cieversion == 1) { ndx++; ! } else { ! if (uleb_extract(&data[off], &ndx, ! size - off, &ujunk) == ! DW_OVERFLOW) { ! ld_eprintf(ofl, ERR_FATAL, ! MSG_INTL(MSG_SCN_DWFOVRFLW), ! ofl->ofl_name, ! osp->os_name); ! return (S_ERROR); ! } ! } /* * we walk through the augmentation * section now looking for the Rflag */ for (cieaugndx = 0; cieaugstr[cieaugndx]; cieaugndx++) { /* BEGIN CSTYLED */ switch (cieaugstr[cieaugndx]) { case 'z': /* size */ ! if (uleb_extract(&data[off], ! &ndx, size - off, &ujunk) == ! DW_OVERFLOW) { ! ld_eprintf(ofl, ERR_FATAL, ! MSG_INTL(MSG_SCN_DWFOVRFLW), ! ofl->ofl_name, ! osp->os_name); ! return (S_ERROR); ! } break; case 'P': /* personality */ ciePflag = data[off + ndx]; ndx++; /* * Just need to extract the * value to move on to the next * field. */ ! switch (dwarf_ehe_extract( ! &data[off], size - off, ! &ndx, &ujunk, ciePflag, ofl->ofl_dehdr->e_ident, B_FALSE, ! shdr->sh_addr, off + ndx, 0)) { ! case DW_OVERFLOW: ! ld_eprintf(ofl, ERR_FATAL, ! MSG_INTL(MSG_SCN_DWFOVRFLW), ! ofl->ofl_name, ! osp->os_name); ! return (S_ERROR); ! case DW_BAD_ENCODING: ! ld_eprintf(ofl, ERR_FATAL, ! MSG_INTL(MSG_SCN_DWFBADENC), ! ofl->ofl_name, ! osp->os_name, ciePflag); ! return (S_ERROR); ! case DW_SUCCESS: ! break; ! } break; case 'R': /* code encoding */ cieRflag = data[off + ndx]; ndx++;
*** 659,673 **** if (ofl->ofl_osgot != NULL) gotaddr = ofl->ofl_osgot->os_shdr->sh_addr; ! initloc = dwarf_ehe_extract(&data[off], ! &ndx, cieRflag, ofl->ofl_dehdr->e_ident, ! B_FALSE, ! shdr->sh_addr, off + ndx, ! gotaddr); /* * Ignore FDEs with initloc set to 0. * initloc will not be 0 unless this FDE was * abandoned due to GNU linkonce processing. --- 706,734 ---- if (ofl->ofl_osgot != NULL) gotaddr = ofl->ofl_osgot->os_shdr->sh_addr; ! switch (dwarf_ehe_extract(&data[off], ! size - off, &ndx, &initloc, cieRflag, ! ofl->ofl_dehdr->e_ident, B_FALSE, ! shdr->sh_addr, off + ndx, gotaddr)) { ! case DW_OVERFLOW: ! ld_eprintf(ofl, ERR_FATAL, ! MSG_INTL(MSG_SCN_DWFOVRFLW), ! ofl->ofl_name, ! osp->os_name); ! return (S_ERROR); ! case DW_BAD_ENCODING: ! ld_eprintf(ofl, ERR_FATAL, ! MSG_INTL(MSG_SCN_DWFBADENC), ! ofl->ofl_name, ! osp->os_name, cieRflag); ! return (S_ERROR); ! case DW_SUCCESS: ! break; ! } /* * Ignore FDEs with initloc set to 0. * initloc will not be 0 unless this FDE was * abandoned due to GNU linkonce processing.