Trusted-AI / adversarial-robustness-toolbox

Adversarial Robustness Toolbox (ART) - Python Library for Machine Learning Security - Evasion, Poisoning, Extraction, Inference - Red and Blue Teams
https://adversarial-robustness-toolbox.readthedocs.io/en/latest/
MIT License
4.75k stars 1.15k forks source link

Issue with using KerasClassifier: Following Poison Frogs Example in Tensorflow(Keras) #1977

Open Rock910 opened 1 year ago

Rock910 commented 1 year ago

Hi, I'm using my own image dataset which is similar to CIFAR-10, and I've done all the preprocessing and cleaning. I'm using a CNN architecture: model = tf.keras.Sequential([ tf.keras.layers.Rescaling(1./255), tf.keras.layers.Conv2D(32, 3, activation='relu'), tf.keras.layers.MaxPooling2D(), tf.keras.layers.Conv2D(32, 3, activation='relu'), tf.keras.layers.MaxPooling2D(), tf.keras.layers.Conv2D(32, 3, activation='relu'), tf.keras.layers.MaxPooling2D(), tf.keras.layers.Flatten(), tf.keras.layers.Dense(128, activation='relu'), tf.keras.layers.Dense(2) to perform classification, there are two classes. I trained this model and saved it as a .h5 file, and then loaded it. Then, I called KerasClassifier on it, in the same way that this is done in the poison frog, clean-label attack example. I get an error: "maximum recursion depth exceeded while calling a Python object", after doing this. Would you be able to help me debug this issue?

beat-buesser commented 1 year ago

Hi @Rock910 That's interesting, can you share a code example that reproduces the issue?

christian-westbrook commented 1 year ago

Hi! I'm also running to a recursion error when attempting to pass a Keras model into KerasClassifier. I'll attach an example you can use.

beat-buesser commented 1 year ago

Hi @christian-westbrook Thank you, an example would be great!

christian-westbrook commented 1 year ago

classifier.zip is a simple feedforward network for a classification problem created using Keras. I load the model using keras.models.load_model() and am trying to figure out how to correctly pass it into an art.estimators.classification.KerasClassifier so that I can use this model (and dozens of others like it) with ART attacks and defenses.

When I try to pass this model into KerasClassifier, the first error I receive is ValueError: TensorFlow is executing eagerly. Please disable eager execution. I use tf.compat.v1.disable_eager_execution() to turn off eager execution, and then the next error I get is RecursionError: maximum recursion depth exceeded at the line art_dnn = KerasClassifier(dnn), where dnn is the example model I provided loaded using keras.models.load_model().

christian-westbrook commented 1 year ago

Here is an example model summary for one of the models, not necessarily the one I provided. They all have the same basic structure except for variable sizes in the input and output layers.

image

christian-westbrook commented 1 year ago

I followed my stack trace and found this:

[/usr/local/lib/python3.10/dist-packages/keras/losses.py](https://localhost:8080/#) in sparse_categorical_crossentropy(y_true, y_pred, from_logits, axis, ignore_class)
   2076       Sparse categorical crossentropy loss value.
   2077     """
-> 2078     return backend.sparse_categorical_crossentropy(
   2079         y_true,
   2080         y_pred,

[/usr/local/lib/python3.10/dist-packages/keras/backend.py](https://localhost:8080/#) in sparse_categorical_crossentropy(target, output, from_logits, axis, ignore_class)
   5606     """
   5607     target = tf.convert_to_tensor(target)
-> 5608     output = tf.convert_to_tensor(output)
   5609 
   5610     target = cast(target, "int64")

[/usr/local/lib/python3.10/dist-packages/keras/layers/core/tf_op_layer.py](https://localhost:8080/#) in handle(self, op, args, kwargs)
    117             for x in tf.nest.flatten([args, kwargs])
    118         ):
--> 119             return TFOpLambda(op)(*args, **kwargs)
    120         else:
    121             return self.NOT_SUPPORTED`

Once you hit the last frame a series of four frames including this call at line 119 repeats until the error is triggered. Maybe you could confirm seeing the same behavior when passing my model to a KerasClassifier?

christian-westbrook commented 1 year ago

Another issue that looks like it might help with debugging: https://github.com/keras-team/keras/issues/12081

christian-westbrook commented 1 year ago

It looks like this error happens specifically when I pass a pre-trained model into the KerasClassifier constructor. It appears that KerasClassifier wants to take in a compiled Keras model rather than a fitted Keras model. This may be your problem @Rock910, are you passing a pre-trained Keras model into a KerasClassifier?

Does anyone know if it's true that KerasClassifier assumes the user will use its fit function rather than the Keras equivalent? Does KerasClassifier call the Keras fit() function in its own fit() function?

SamanehShamshiri commented 1 year ago

Hi, I have the same problem, I did the same problem but couldn't solve it. Would you please let me know if you find any solution? thank you very much

NicolaLepore0 commented 1 year ago

I had the same error, and it fixed me by running "tf.compat.v1.disable_eager_execution()" before any other instruction in the main (i.e. generate/load model).

christian-westbrook commented 1 year ago

I had the same error, and it fixed me by running "tf.compat.v1.disable_eager_execution()" before any other instruction in the main (i.e. generate/load model).

NicolaLepore0 did you experience the maximum recursion depth reached error or the eager execution not supported error?

NicolaLepore0 commented 1 year ago

The error I tried to fix is: KerasClassifier error of conversion: maximum recursion depth exceeded while calling a Python object This happens if I enter: tf.compat.v1.disable_eager_execution(), before creating the KerasClassifier. But if I put it at the start of the main function this doesn't happen. If I don't insert it, the error is that of eager execution