fix(gcp): make gen2 Cloud Functions IAM policy query thread-safe#12107
fix(gcp): make gen2 Cloud Functions IAM policy query thread-safe#12107stefanobaldo wants to merge 1 commit into
Conversation
CloudFunction._get_function_iam_policy runs once per function across a thread pool (GCPService.__threading_call__), and httplib2 is not thread-safe. The gen1 branch isolates each thread with its own AuthorizedHttp via .execute(http=self.__get_AuthorizedHttp_client__()), but the gen2 branch calls .execute() on the shared self._run_client. When a project has several gen2 functions the concurrent requests corrupt the process heap and abort the scan (SIGABRT/SIGSEGV, "malloc(): unsorted double linked list corrupted"). Pass a per-request http client to the gen2 getIamPolicy().execute(), mirroring the gen1 branch. This removes the shared-client data race while keeping the per-resource parallelism. Adds a regression test and a changelog fragment.
|
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: Organization UI Review profile: ASSERTIVE Plan: Pro Plus Run ID: 📒 Files selected for processing (3)
📝 WalkthroughWalkthroughCloud Functions Gen2 IAM policy retrieval now passes a per-request authorized HTTP client to Cloud Run’s ChangesCloud Functions Gen2 IAM thread safety
Estimated code review effort: 2 (Simple) | ~10 minutes Possibly related PRs
Suggested reviewers: 🚥 Pre-merge checks | ✅ 5✅ Passed checks (5 passed)
✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
|
✅ No Conflicts No conflict markers, and the branch merges cleanly into its base. |
|
Thanks @stefanobaldo! We'll review this as soon as possible. |
Context
Fix #12106
CloudFunction._get_function_iam_policyis fanned out one thread per function byGCPService.__threading_call__(prowler/providers/gcp/lib/service/service.py:44,which starts a raw
threading.Threadper item).httplib2is not thread-safe.Every other threaded GCP call isolates each thread by passing a fresh transport to
.execute(http=self.__get_AuthorizedHttp_client__(), ...)— including the gen1branch of this very method. The gen2 branch does not: it calls
.execute()onthe shared
self._run_clientdiscovery client(
prowler/providers/gcp/services/cloudfunction/cloudfunction_service.py). When aproject has several gen2 Cloud Functions, the threads issue concurrent requests
through that one shared client and corrupt the process heap, aborting the whole
scan. It reproduces reliably in containerized, multi-vCPU environments (e.g. Cloud
Run). Captured with
PYTHONFAULTHANDLER=1— every crashing thread shares the sameframe, the classic non-thread-safe-
httplib2signature:An audit of every
__threading_call__target in the GCP provider confirms this isthe only threaded call that shares a client instead of passing a per-request
http.Description
prowler/providers/gcp/services/cloudfunction/cloudfunction_service.py— pass aper-request HTTP client to the gen2
getIamPolicy().execute()call, exactly as thegen1 branch immediately below already does:
This gives each thread its own
httplib2transport, removing the shared-client datarace. Parallelism is unchanged (no serialization) and findings are unaffected.
Steps to review
cloudfunction_service.py— the gen2.execute()now receiveshttp=self.__get_AuthorizedHttp_client__(), matching the gen1 branch a few linesbelow.
New regression test asserts the gen2 IAM lookup is executed with a per-request
http(a shared-client call would omit it):(7 passed)
Optional real-world repro: scan a GCP project with several gen2 Cloud
Functions from a multi-vCPU container. Before: intermittent heap-corruption abort
during the cloudfunction service. After: the scan completes and reports Cloud
Function IAM findings.
Checklist
SDK/CLI
License
By submitting this pull request, I confirm that my contribution is made under the terms of the Apache 2.0 license.
Summary by CodeRabbit
Bug Fixes
Tests