Skip to content

Commit f3780ff

Browse files
author
Manish Bhattarai
committed
uploads
0 parents  commit f3780ff

File tree

982 files changed

+10563
-0
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

982 files changed

+10563
-0
lines changed

.gitignore

+147
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,147 @@
1+
# mac
2+
results/
3+
.DS_Store
4+
# contains the data for the project
5+
# data/
6+
# swap files
7+
*.swp
8+
# matlab/output
9+
10+
# Created by https://www.toptal.com/developers/gitignore/api/python
11+
# Edit at https://www.toptal.com/developers/gitignore?templates=python
12+
13+
### Python ###
14+
# Byte-compiled / optimized / DLL files
15+
__pycache__/
16+
*.py[cod]
17+
*$py.class
18+
19+
# C extensions
20+
*.so
21+
22+
# Distribution / packaging
23+
.Python
24+
build/
25+
develop-eggs/
26+
dist/
27+
downloads/
28+
eggs/
29+
.eggs/
30+
lib/
31+
lib64/
32+
parts/
33+
sdist/
34+
var/
35+
wheels/
36+
pip-wheel-metadata/
37+
share/python-wheels/
38+
*.egg-info/
39+
.installed.cfg
40+
*.egg
41+
MANIFEST
42+
43+
# PyInstaller
44+
# Usually these files are written by a python script from a template
45+
# before PyInstaller builds the exe, so as to inject date/other infos into it.
46+
*.manifest
47+
*.spec
48+
49+
# Installer logs
50+
pip-log.txt
51+
pip-delete-this-directory.txt
52+
53+
# Unit test / coverage reports
54+
htmlcov/
55+
.tox/
56+
.nox/
57+
.coverage
58+
.coverage.*
59+
.cache
60+
nosetests.xml
61+
coverage.xml
62+
*.cover
63+
*.py,cover
64+
.hypothesis/
65+
.pytest_cache/
66+
67+
# Translations
68+
*.mo
69+
*.pot
70+
71+
# Django stuff:
72+
*.log
73+
local_settings.py
74+
db.sqlite3
75+
db.sqlite3-journal
76+
77+
# Flask stuff:
78+
instance/
79+
.webassets-cache
80+
81+
# Scrapy stuff:
82+
.scrapy
83+
84+
# Sphinx documentation
85+
docs/_build/
86+
87+
# PyBuilder
88+
target/
89+
90+
# Jupyter Notebook
91+
.ipynb_checkpoints
92+
93+
# IPython
94+
profile_default/
95+
ipython_config.py
96+
97+
# pyenv
98+
.python-version
99+
100+
# pipenv
101+
# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
102+
# However, in case of collaboration, if having platform-specific dependencies or dependencies
103+
# having no cross-platform support, pipenv may install dependencies that don't work, or not
104+
# install all needed dependencies.
105+
#Pipfile.lock
106+
107+
# PEP 582; used by e.g. github.com/David-OConnor/pyflow
108+
__pypackages__/
109+
110+
# Celery stuff
111+
celerybeat-schedule
112+
celerybeat.pid
113+
114+
# SageMath parsed files
115+
*.sage.py
116+
117+
# Environments
118+
.env
119+
.venv
120+
env/
121+
venv/
122+
ENV/
123+
env.bak/
124+
venv.bak/
125+
126+
# Spyder project settings
127+
.spyderproject
128+
.spyproject
129+
130+
# Rope project settings
131+
.ropeproject
132+
133+
# mkdocs documentation
134+
/site
135+
136+
# mypy
137+
.mypy_cache/
138+
.dmypy.json
139+
dmypy.json
140+
141+
# Pyre type checker
142+
.pyre/
143+
144+
# pytype static type analyzer
145+
.pytype/
146+
147+
# End of https://www.toptal.com/developers/gitignore/api/python

LICENSE

+29
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
BSD 3-Clause License
2+
3+
Copyright (c) 2025, Los Alamos National Laboratory
4+
All rights reserved.
5+
6+
Redistribution and use in source and binary forms, with or without
7+
modification, are permitted provided that the following conditions are met:
8+
9+
1. Redistributions of source code must retain the above copyright notice, this
10+
list of conditions and the following disclaimer.
11+
12+
2. Redistributions in binary form must reproduce the above copyright notice,
13+
this list of conditions and the following disclaimer in the documentation
14+
and/or other materials provided with the distribution.
15+
16+
3. Neither the name of the copyright holder nor the names of its
17+
contributors may be used to endorse or promote products derived from
18+
this software without specific prior written permission.
19+
20+
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
21+
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22+
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
23+
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
24+
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
25+
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
26+
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
27+
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
28+
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29+
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

LaFA/__init__.py

+2
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
from LaFA.utils import file_name_gens, grad_attacks
2+
from LaFA.experiments import experiments

LaFA/experiments/__init__.py

+6
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
from .exp_face import *
2+
from .exp_mnist import *
3+
from .exp_swim import *
4+
from .exp_synthetic import *
5+
from .exp_wtsi import *
6+
from .experiments import *

LaFA/experiments/exp_face.py

+177
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,177 @@
1+
import time
2+
import torch
3+
from numpy import linspace as linspace
4+
import numpy.linalg as la
5+
import numpy as np
6+
from scipy.io import loadmat
7+
import LaFA.utils.file_name_gens as file_name_gens
8+
import pandas as pd
9+
import pickle
10+
import tqdm
11+
import os
12+
import glob
13+
14+
# from grad_attacks_dev import *
15+
from LaFA.utils.grad_attacks import *
16+
17+
if torch.cuda.is_available():
18+
device=torch.device('cuda:0')
19+
else:
20+
device=torch.device('cpu')
21+
22+
def read_pgm(pgmf):
23+
"""Return a raster of integers from a PGM as a list of lists."""
24+
header = pgmf.readline()
25+
header1 = pgmf.readline()
26+
header2 = pgmf.readline()
27+
assert header[:2] == b'P5'
28+
(width, height) = [int(i) for i in header1.split()[:2]]
29+
depth = int(header2)
30+
assert depth <= 65535
31+
32+
raster = []
33+
for y in range(height):
34+
row = []
35+
for y in range(width):
36+
row.append(ord(pgmf.read(1)))
37+
raster.append(row)
38+
return raster
39+
40+
def experiment(args):
41+
print(args)
42+
print("FACE experiment")
43+
log_file = file_name_gens.log_name_gen(args)
44+
print("Log is saved to: ", log_file)
45+
if os.path.isfile(log_file):
46+
log = pd.read_pickle(log_file)
47+
else:
48+
log = pd.DataFrame()
49+
50+
print("Load data")
51+
allFace = []
52+
for curF in glob.glob('data/face/*.pgm'):
53+
file = open(curF, 'rb')
54+
im = np.array(read_pgm(file))
55+
file.close()
56+
allFace.append(im.flatten())
57+
allFace = np.array(allFace)
58+
X = allFace.astype(np.float32)
59+
X = X/np.max(X)
60+
61+
XorigT = Tcons(X,device).float()
62+
print("-------------------------")
63+
print("* DATA STATS *")
64+
print("Min: ", torch.min(XorigT).cpu().detach().numpy())
65+
print("Max: ", torch.max(XorigT).cpu().detach().numpy())
66+
print("Shape: ", XorigT.shape)
67+
print("Data type: ", XorigT.dtype)
68+
print("-------------------------")
69+
70+
np.random.seed(seed=args.seed)
71+
Winit = np.random.rand(X.shape[0],args.rank)
72+
Hinit = np.random.rand(args.rank,X.shape[1])
73+
Winit = torch.Tensor(Winit)
74+
Hinit = torch.Tensor(Hinit)
75+
WinitT = Tcons(Winit,device).float()
76+
HinitT = Tcons(Hinit,device).float()
77+
78+
Wstay,Hstay = NMFiter_KL(XorigT,args.base_iter,WinitT,HinitT)
79+
80+
# Test stationary condition of base:
81+
Wnext,Hnext = NMFiter_KL(XorigT,100,Wstay,Hstay)
82+
X0 = Wstay@Hstay
83+
Xnext = Wnext@Hnext
84+
print("-------------------------")
85+
print("* SETUP STATIONARY BASE STATE *")
86+
print("Reconstruction error Linf: ", torch.max(torch.abs(X0-XorigT)).cpu().detach().numpy())
87+
print("Reconstruction error L2: ", (torch.norm(X0-XorigT)/torch.norm(XorigT)).cpu().detach().numpy())
88+
print("Recon base error: ", torch.max(torch.abs(X0-Xnext)).cpu().detach().numpy())
89+
print("W stationary error: ", torch.max(torch.abs(Wstay-Wnext)).cpu().detach().numpy())
90+
print("H stationary error: ", torch.max(torch.abs(Hstay-Hnext)).cpu().detach().numpy())
91+
print("-------------------------")
92+
93+
print("Generate attacker")
94+
95+
min_eps = args.eps_min
96+
no_eps = args.no_eps
97+
max_eps = args.eps_max
98+
norm = args.norm
99+
eps_range = max_eps - min_eps
100+
nmf_rank = args.rank
101+
nmf_iter = args.nmf_iter
102+
103+
attacker = Gradient_based_attack(XorigT,
104+
nmf_rank = nmf_rank,
105+
base_nmf_iters = nmf_iter,
106+
use_cuda = True,
107+
implicit_func = args.implicit,
108+
taylor = args.taylor,
109+
norm = norm,
110+
rec_loss = args.recloss,
111+
verbose = True)
112+
113+
for step in tqdm.tqdm(range(no_eps)):
114+
115+
eps = step/no_eps * (eps_range) + min_eps
116+
print("Generate attack for eps = ", eps)
117+
118+
# Attack
119+
start_time = time.time()
120+
torch.cuda.reset_peak_memory_stats()
121+
start_mem_allocated = torch.cuda.memory_stats()['active_bytes.all.peak']
122+
Xperturb = attacker.pgd_attack(eps=eps, alpha=args.alpha, iters= args.no_iter, record = False, average_grad = args.average)
123+
end_mem_allocated = torch.cuda.memory_stats()['active_bytes.all.peak']
124+
duration = time.time()-start_time
125+
memory = end_mem_allocated
126+
memory_Mb_ifunc = memory/1000000
127+
128+
# Stats
129+
in_X_dist = (torch.norm(Xperturb - XorigT)/torch.norm(XorigT)).cpu().detach().numpy()
130+
Wp,Hp = NMFiter_KL(Xperturb,10000,WinitT,HinitT)
131+
out_X_dist = (torch.norm(Wp@Hp - XorigT)/torch.norm(XorigT)).cpu().detach().numpy()
132+
out_FE_dist = loss_wh(Wstay,Wp,Hstay,Hp).cpu().detach().numpy()
133+
Hstay = Hstay + 1e-10
134+
Hp = Hp + 1e-10
135+
Wstay = Wstay + 1e-10
136+
Wp = Wp + 1e-10
137+
out_W_dist = loss_w(Wstay,Wp).cpu().detach().numpy()
138+
out_H_dist = loss_w(Hstay,Hp).cpu().detach().numpy()
139+
140+
# Log
141+
print("Input distortion: ", in_X_dist)
142+
print("FE distortion: ", out_FE_dist)
143+
print("W distortion: ", out_W_dist)
144+
print("H distortion: ", out_H_dist)
145+
print("Duration (sec): ", duration)
146+
print("Memory (Mb): ", memory_Mb_ifunc)
147+
print("----")
148+
149+
result = {
150+
'eps': eps,
151+
'alpha': args.alpha,
152+
'pgd iters': args.no_iter,
153+
'in': in_X_dist,
154+
'out rec': out_X_dist,
155+
'out fe': out_FE_dist,
156+
'out W': out_W_dist,
157+
'out H': out_H_dist,
158+
'duration': duration,
159+
'memory': memory,
160+
'Implicit gradient': args.implicit,
161+
'norm': args.norm,
162+
'NMF iters': args.nmf_iter,
163+
'Seed': args.seed
164+
}
165+
log = pd.concat([log, pd.DataFrame.from_records([result])])
166+
with open(log_file, 'wb') as logfile:
167+
pickle.dump(log, logfile)
168+
169+
Hp_np = Hp.cpu().detach().numpy()
170+
FEATURE_FILES = file_name_gens.feature_name_gen(args, eps = eps)
171+
with open(FEATURE_FILES, 'wb') as f:
172+
np.save(f, Hp_np)
173+
174+
return
175+
176+
177+

0 commit comments

Comments
 (0)