library: refactor flawed function fatal_proc_unmounted
This commit addresses a potentially disastrous flaw in that fatal_proc_unmounted() function wherein requested item(s) might not have been returned to the caller yet were specified at the time of a 'new' or 'reset' call. The root cause, uncovered by Craig, was due to the old library look_up_our_self() support function which only would populate a proc_t with limited 'stat' file data. This routine will now act the same as all other <pids> functions which return a stack or stacks. Whatever was specified with a 'new' or 'reset' will be returned, if the passed 'return_self' parameter is other than zero. [ as is so often the case, when flawed code is fixed ] [ former complexity can be reduced as a side benefit ] Reference(s): https://www.freelists.org/post/procps/issue-245-plus-one,2 Signed-off-by: Jim Warner <james.warner@comcast.net>
This commit is contained in:
parent
116ce62304
commit
52bd019d8c
34
proc/pids.c
34
proc/pids.c
@ -82,8 +82,8 @@ struct pids_info {
|
|||||||
int curitems; // includes 'logical_end' delimiter
|
int curitems; // includes 'logical_end' delimiter
|
||||||
enum pids_item *items; // includes 'logical_end' delimiter
|
enum pids_item *items; // includes 'logical_end' delimiter
|
||||||
struct stacks_extent *extents; // anchor for all resettable extents
|
struct stacks_extent *extents; // anchor for all resettable extents
|
||||||
struct stacks_extent *otherexts; // anchor for single stack invariant extents
|
struct stacks_extent *otherexts; // anchor for invariant extents // <=== currently unused
|
||||||
struct fetch_support fetch; // support for procps_pids_reap & select
|
struct fetch_support fetch; // support for procps_pids_reap, select, fatal
|
||||||
int history_yes; // need historical data
|
int history_yes; // need historical data
|
||||||
struct history_info *hist; // pointer to historical support data
|
struct history_info *hist; // pointer to historical support data
|
||||||
proc_t*(*read_something)(PROCTAB*, proc_t*); // readproc/readeither via which
|
proc_t*(*read_something)(PROCTAB*, proc_t*); // readproc/readeither via which
|
||||||
@ -900,6 +900,7 @@ static inline void pids_cleanup_stacks_all (
|
|||||||
} // end: pids_cleanup_stacks_all
|
} // end: pids_cleanup_stacks_all
|
||||||
|
|
||||||
|
|
||||||
|
#if 0 // not currently needed after 'fatal_proc_unmounted' was refactored
|
||||||
/*
|
/*
|
||||||
* This routine exists in case we ever want to offer something like
|
* This routine exists in case we ever want to offer something like
|
||||||
* 'static' or 'invarient' results stacks. By unsplicing an extent
|
* 'static' or 'invarient' results stacks. By unsplicing an extent
|
||||||
@ -925,6 +926,7 @@ static struct stacks_extent *pids_extent_cut (
|
|||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
} // end: pids_extent_cut
|
} // end: pids_extent_cut
|
||||||
|
#endif // ----------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
static inline struct pids_result *pids_itemize_stack (
|
static inline struct pids_result *pids_itemize_stack (
|
||||||
@ -1377,8 +1379,9 @@ PROCPS_EXPORT struct pids_stack *fatal_proc_unmounted (
|
|||||||
struct pids_info *info,
|
struct pids_info *info,
|
||||||
int return_self)
|
int return_self)
|
||||||
{
|
{
|
||||||
static __thread proc_t self;
|
struct pids_fetch *fetched;
|
||||||
struct stacks_extent *ext;
|
unsigned tid;
|
||||||
|
proc_t self;
|
||||||
|
|
||||||
/* this is very likely the *only* newlib function where the
|
/* this is very likely the *only* newlib function where the
|
||||||
context (pids_info) of NULL will ever be permitted */
|
context (pids_info) of NULL will ever be permitted */
|
||||||
@ -1386,27 +1389,10 @@ PROCPS_EXPORT struct pids_stack *fatal_proc_unmounted (
|
|||||||
|| (!return_self))
|
|| (!return_self))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
errno = EINVAL;
|
tid = getpid();
|
||||||
if (info == NULL)
|
if (!(fetched = procps_pids_select(info, &tid, 1, PIDS_SELECT_PID)))
|
||||||
return NULL;
|
return NULL;
|
||||||
/* with items & numitems technically optional at 'new' time, it's
|
return fetched->stacks[0];
|
||||||
expected 'reset' will have been called -- but just in case ... */
|
|
||||||
if (!info->curitems)
|
|
||||||
return NULL;
|
|
||||||
errno = 0;
|
|
||||||
|
|
||||||
if (!(ext = pids_stacks_alloc(info, 1)))
|
|
||||||
return NULL;
|
|
||||||
if (!pids_extent_cut(info, ext)) {
|
|
||||||
errno = EADDRNOTAVAIL;
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
ext->next = info->otherexts;
|
|
||||||
info->otherexts = ext;
|
|
||||||
if (!pids_assign_results(info, ext->stacks[0], &self))
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
return ext->stacks[0];
|
|
||||||
} // end: fatal_proc_unmounted
|
} // end: fatal_proc_unmounted
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user