Road Trip Attack (RTA) creates targeted adversarial images for GeoCLIP. You provide an image, its real coordinates, and the coordinates where you want GeoCLIP to place it. RTA returns a modified image.
This repository contains the attack used in the paper and a second version that strictly limits the final pixel changes.
RTA can run on a CPU, but it will be much slower. GeoCLIP downloads its model weights the first time you run the attack.
Clone this repository, enter its directory, and run:
python -m pip install .
To install the test tools too:
python -m pip install ".[test]"
The exact dependency versions used for validation are listed in
requirements-lock.txt.
import rta
adversarial = rta.attack(
"photo.jpg",
ground_truth=(32.325436, -64.764404),
target=(31.249600, 36.788300),
epsilon=4 / 255,
)
adversarial.save("photo_adversarial.png")
rta.close()
ground_truth and target use (latitude, longitude) order. The input can be
a file path or a PIL image. The result is a 224 by 224 RGB PIL image.
CUDA device 0 is used by default. To use a CPU, pass device="cpu":
adversarial = rta.attack(
"photo.jpg",
ground_truth=(32.325436, -64.764404),
target=(31.249600, 36.788300),
device="cpu",
)
Loading GeoCLIP takes time. Use an RTA session when attacking several
images:
import rta
with rta.RTA(device="cuda:0", seed=131) as attacker:
adversarial = attacker.attack(
"photo.jpg",
ground_truth=(32.325436, -64.764404),
target=(31.249600, 36.788300),
epsilon=2 / 255,
)
The session keeps the random sequence used by the original experiment. When reproducing the paper, do not reset the seed before every image.
RTA provides two variants:
legacy is the default. It matches the attack used in the paper. Its
epsilon limits each local update, but several updates can add up. The final
image is therefore not guaranteed to stay inside the same pixel limit.final_clamp runs the legacy attack and then limits the final image to the
requested pixel distance from the original image.Select a variant with the variant argument:
adversarial = rta.attack(
"photo.jpg",
ground_truth=(32.325436, -64.764404),
target=(31.249600, 36.788300),
epsilon=4 / 255,
variant="final_clamp",
)
On the full 2,997-image Im2GPS test set, the largest measured changes for the
legacy 2/255 and 4/255 settings were about 3/255 and 6/255. final_clamp kept
the largest changes at 2/255 and 4/255, with similar overall attack results.
See the variant notes for details and the validation record for the full results.
The public API uses the original settings:
epsilon, unless alpha is providedGPU calculations can vary slightly across hardware, CUDA versions, and dependency versions. Small differences can change the beam search path, so separate runs may not create identical image files.
Run the tests with:
python -m pytest
Build the source and wheel packages with:
python -m build
The code is available under the MIT License. The bundled Natural Earth land data is in the public domain. Its original README and version files are included with the data.
1 commits
Python
88.7%
HTML
11.3%
Road Trip Attack (RTA) creates targeted adversarial images for GeoCLIP. You provide an image, its real coordinates, and the coordinates where you want GeoCLIP to place it. RTA returns a modified image.
This repository contains the attack used in the paper and a second version that strictly limits the final pixel changes.
RTA can run on a CPU, but it will be much slower. GeoCLIP downloads its model weights the first time you run the attack.
Clone this repository, enter its directory, and run:
python -m pip install .
To install the test tools too:
python -m pip install ".[test]"
The exact dependency versions used for validation are listed in
requirements-lock.txt.
import rta
adversarial = rta.attack(
"photo.jpg",
ground_truth=(32.325436, -64.764404),
target=(31.249600, 36.788300),
epsilon=4 / 255,
)
adversarial.save("photo_adversarial.png")
rta.close()
ground_truth and target use (latitude, longitude) order. The input can be
a file path or a PIL image. The result is a 224 by 224 RGB PIL image.
CUDA device 0 is used by default. To use a CPU, pass device="cpu":
adversarial = rta.attack(
"photo.jpg",
ground_truth=(32.325436, -64.764404),
target=(31.249600, 36.788300),
device="cpu",
)
Loading GeoCLIP takes time. Use an RTA session when attacking several
images:
import rta
with rta.RTA(device="cuda:0", seed=131) as attacker:
adversarial = attacker.attack(
"photo.jpg",
ground_truth=(32.325436, -64.764404),
target=(31.249600, 36.788300),
epsilon=2 / 255,
)
The session keeps the random sequence used by the original experiment. When reproducing the paper, do not reset the seed before every image.
RTA provides two variants:
legacy is the default. It matches the attack used in the paper. Its
epsilon limits each local update, but several updates can add up. The final
image is therefore not guaranteed to stay inside the same pixel limit.final_clamp runs the legacy attack and then limits the final image to the
requested pixel distance from the original image.Select a variant with the variant argument:
adversarial = rta.attack(
"photo.jpg",
ground_truth=(32.325436, -64.764404),
target=(31.249600, 36.788300),
epsilon=4 / 255,
variant="final_clamp",
)
On the full 2,997-image Im2GPS test set, the largest measured changes for the
legacy 2/255 and 4/255 settings were about 3/255 and 6/255. final_clamp kept
the largest changes at 2/255 and 4/255, with similar overall attack results.
See the variant notes for details and the validation record for the full results.
The public API uses the original settings:
epsilon, unless alpha is providedGPU calculations can vary slightly across hardware, CUDA versions, and dependency versions. Small differences can change the beam search path, so separate runs may not create identical image files.
Run the tests with:
python -m pytest
Build the source and wheel packages with:
python -m build
The code is available under the MIT License. The bundled Natural Earth land data is in the public domain. Its original README and version files are included with the data.
1 commits
Python
88.7%
HTML
11.3%