| 62 | } |
| 63 | |
| 64 | bool cacheNeedsReset(dl_phdr_info *PInfo) { |
| 65 | // C libraries increment dl_phdr_info.adds and dl_phdr_info.subs when |
| 66 | // loading and unloading shared libraries. If these values change between |
| 67 | // iterations of dl_iterate_phdr, then invalidate the cache. |
| 68 | |
| 69 | // These are static to avoid needing an initializer, and unsigned long long |
| 70 | // because that is their type within the extended dl_phdr_info. Initialize |
| 71 | // these to something extremely unlikely to be found upon the first call to |
| 72 | // dl_iterate_phdr. |
| 73 | static unsigned long long LastAdds = ULLONG_MAX; |
| 74 | static unsigned long long LastSubs = ULLONG_MAX; |
| 75 | if (PInfo->dlpi_adds != LastAdds || PInfo->dlpi_subs != LastSubs) { |
| 76 | // Resetting the entire cache is a big hammer, but this path is rare-- |
| 77 | // usually just on the very first call, when the cache is empty anyway--so |
| 78 | // added complexity doesn't buy much. |
| 79 | LastAdds = PInfo->dlpi_adds; |
| 80 | LastSubs = PInfo->dlpi_subs; |
| 81 | resetCache(); |
| 82 | return true; |
| 83 | } |
| 84 | return false; |
| 85 | } |
| 86 | |
| 87 | public: |
| 88 | bool find(dl_phdr_info *PInfo, size_t, void *data) { |
no test coverage detected