CTF containers use the ctf_dtoldid field as a threshold type index which
indicates the range of type indices which have been committed to the container by ctf_update(). However, the top bit of the dtd_type field is not part of the type index; rather, it is a flag used to indicate that the corresponding CTF container is a parent. This is why the maximum CTF type index is 2^15 - 1 rather than 2^16 - 1. Therefore, this flag must be masked off (using the CTF_TYPE_TO_INDEX macro) when comparing a type index with the ctf_dtoldid field of a container. This bug was causing libctf to erroneously free committed type definitions in ctf_discard(). libdtrace holds some references to such types, resulting in a use-after-free. MFC after: 2 weeks Sponsored by: EMC / Isilon Storage Division
This commit is contained in:
parent
2bb7e77385
commit
b0ee912984
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=279864
@ -584,7 +584,7 @@ ctf_discard(ctf_file_t *fp)
|
|||||||
|
|
||||||
for (dtd = ctf_list_prev(&fp->ctf_dtdefs); dtd != NULL; dtd = ntd) {
|
for (dtd = ctf_list_prev(&fp->ctf_dtdefs); dtd != NULL; dtd = ntd) {
|
||||||
ntd = ctf_list_prev(dtd);
|
ntd = ctf_list_prev(dtd);
|
||||||
if (dtd->dtd_type <= fp->ctf_dtoldid)
|
if (CTF_TYPE_TO_INDEX(dtd->dtd_type) <= fp->ctf_dtoldid)
|
||||||
continue; /* skip types that have been committed */
|
continue; /* skip types that have been committed */
|
||||||
|
|
||||||
ctf_dtd_delete(fp, dtd);
|
ctf_dtd_delete(fp, dtd);
|
||||||
@ -1328,7 +1328,7 @@ ctf_add_type(ctf_file_t *dst_fp, ctf_file_t *src_fp, ctf_id_t src_type)
|
|||||||
*/
|
*/
|
||||||
if (dst_type == CTF_ERR && name[0] != '\0') {
|
if (dst_type == CTF_ERR && name[0] != '\0') {
|
||||||
for (dtd = ctf_list_prev(&dst_fp->ctf_dtdefs); dtd != NULL &&
|
for (dtd = ctf_list_prev(&dst_fp->ctf_dtdefs); dtd != NULL &&
|
||||||
dtd->dtd_type > dst_fp->ctf_dtoldid;
|
CTF_TYPE_TO_INDEX(dtd->dtd_type) > dst_fp->ctf_dtoldid;
|
||||||
dtd = ctf_list_prev(dtd)) {
|
dtd = ctf_list_prev(dtd)) {
|
||||||
if (CTF_INFO_KIND(dtd->dtd_data.ctt_info) == kind &&
|
if (CTF_INFO_KIND(dtd->dtd_data.ctt_info) == kind &&
|
||||||
dtd->dtd_name != NULL &&
|
dtd->dtd_name != NULL &&
|
||||||
|
Loading…
Reference in New Issue
Block a user