Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Python testing #1473

Merged
merged 4 commits into from
Jan 22, 2015
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,8 @@ install:
- sudo -E $SCRIPTS/travis_install.sh

before_script:
- export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/usr/local/lib
- export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/usr/local/lib:/usr/local/cuda/lib64
- export PATH=/home/travis/miniconda/bin:$PATH
- if ! $WITH_CMAKE; then $SCRIPTS/travis_setup_makefile_config.sh; fi

script: $SCRIPTS/travis_build_and_test.sh
Expand Down
3 changes: 3 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -434,6 +434,9 @@ runtest: $(TEST_ALL_BIN) $(TEST_ALL_DYNLINK_BIN)
$(TEST_ALL_BIN) $(TEST_GPUID) --gtest_shuffle $(TEST_FILTER) && \
$(TEST_ALL_DYNLINK_BIN) $(TEST_GPUID) --gtest_shuffle $(TEST_FILTER)

pytest: py
cd python; python -m unittest discover -s caffe/test

warn: $(EMPTY_WARN_REPORT)

$(EMPTY_WARN_REPORT): $(ALL_WARNS) | $(BUILD_DIR)
Expand Down
77 changes: 77 additions & 0 deletions python/caffe/test/test_net.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
import unittest
import tempfile
import os
import numpy as np

import caffe

def simple_net_file(num_output):
"""Make a simple net prototxt, based on test_net.cpp, returning the name
of the (temporary) file."""

f = tempfile.NamedTemporaryFile(delete=False)
f.write("""name: 'testnet' force_backward: true
layers { type: DUMMY_DATA name: 'data' top: 'data' top: 'label'
dummy_data_param { num: 5 channels: 2 height: 3 width: 4
num: 5 channels: 1 height: 1 width: 1
data_filler { type: 'gaussian' std: 1 }
data_filler { type: 'constant' } } }
layers { type: CONVOLUTION name: 'conv' bottom: 'data' top: 'conv'
convolution_param { num_output: 11 kernel_size: 2 pad: 3
weight_filler { type: 'gaussian' std: 1 }
bias_filler { type: 'constant' value: 2 } }
weight_decay: 1 weight_decay: 0 }
layers { type: INNER_PRODUCT name: 'ip' bottom: 'conv' top: 'ip'
inner_product_param { num_output: """ + str(num_output) + """
weight_filler { type: 'gaussian' std: 2.5 }
bias_filler { type: 'constant' value: -3 } } }
layers { type: SOFTMAX_LOSS name: 'loss' bottom: 'ip' bottom: 'label'
top: 'loss' }""")
f.close()
return f.name

class TestNet(unittest.TestCase):
def setUp(self):
self.num_output = 13
net_file = simple_net_file(self.num_output)
self.net = caffe.Net(net_file)
# fill in valid labels
self.net.blobs['label'].data[...] = \
np.random.randint(self.num_output,
size=self.net.blobs['label'].data.shape)
os.remove(net_file)

def test_memory(self):
"""Check that holding onto blob data beyond the life of a Net is OK"""

params = sum(map(list, self.net.params.itervalues()), [])
blobs = self.net.blobs.values()
del self.net

# now sum everything (forcing all memory to be read)
total = 0
for p in params:
total += p.data.sum() + p.diff.sum()
for bl in blobs:
total += bl.data.sum() + bl.diff.sum()

def test_forward_backward(self):
self.net.forward()
self.net.backward()

def test_inputs_outputs(self):
self.assertEqual(self.net.inputs, [])
self.assertEqual(self.net.outputs, ['loss'])

def test_save_and_read(self):
f = tempfile.NamedTemporaryFile(delete=False)
f.close()
self.net.save(f.name)
net_file = simple_net_file(self.num_output)
net2 = caffe.Net(net_file, f.name)
os.remove(net_file)
os.remove(f.name)
for name in self.net.params:
for i in range(len(self.net.params[name])):
self.assertEqual(abs(self.net.params[name][i].data
- net2.params[name][i].data).sum(), 0)
49 changes: 49 additions & 0 deletions python/caffe/test/test_solver.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
import unittest
import tempfile
import os
import numpy as np

import caffe
from test_net import simple_net_file

class TestSolver(unittest.TestCase):
def setUp(self):
self.num_output = 13
net_f = simple_net_file(self.num_output)
f = tempfile.NamedTemporaryFile(delete=False)
f.write("""net: '""" + net_f + """'
test_iter: 10 test_interval: 10 base_lr: 0.01 momentum: 0.9
weight_decay: 0.0005 lr_policy: 'inv' gamma: 0.0001 power: 0.75
display: 100 max_iter: 100 snapshot_after_train: false""")
f.close()
self.solver = caffe.SGDSolver(f.name)
self.solver.net.set_mode_cpu()
# fill in valid labels
self.solver.net.blobs['label'].data[...] = \
np.random.randint(self.num_output,
size=self.solver.net.blobs['label'].data.shape)
self.solver.test_nets[0].blobs['label'].data[...] = \
np.random.randint(self.num_output,
size=self.solver.test_nets[0].blobs['label'].data.shape)
os.remove(f.name)
os.remove(net_f)

def test_solve(self):
self.assertEqual(self.solver.iter, 0)
self.solver.solve()
self.assertEqual(self.solver.iter, 100)

def test_net_memory(self):
"""Check that nets survive after the solver is destroyed."""

nets = [self.solver.net] + list(self.solver.test_nets)
self.assertEqual(len(nets), 2)
del self.solver

total = 0
for net in nets:
for ps in net.params.itervalues():
for p in ps:
total += p.data.sum() + p.diff.sum()
for bl in net.blobs.itervalues():
total += bl.data.sum() + bl.diff.sum()
1 change: 1 addition & 0 deletions scripts/travis/travis_build_and_test.sh
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ else
$MAKE all
$MAKE test
$MAKE pycaffe
$MAKE pytest
$MAKE warn
if ! $WITH_CUDA; then
$MAKE lint
Expand Down
11 changes: 11 additions & 0 deletions scripts/travis/travis_install.sh
Original file line number Diff line number Diff line change
Expand Up @@ -57,3 +57,14 @@ $MAKE
$MAKE install
popd
rm -f $LMDB_FILE

# Install the Python runtime dependencies via miniconda (this is much faster
# than using pip for everything).
wget http://repo.continuum.io/miniconda/Miniconda-latest-Linux-x86_64.sh -O miniconda.sh
chmod +x miniconda.sh
./miniconda.sh -b
export PATH=/home/travis/miniconda/bin:$PATH
conda update --yes conda
conda install --yes numpy scipy matplotlib scikit-image pip
pip install protobuf
rm /home/travis/miniconda/lib/libm.*
14 changes: 11 additions & 3 deletions scripts/travis/travis_setup_makefile_config.sh
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,18 @@ set -e
mv Makefile.config.example Makefile.config

if $WITH_CUDA; then
# Remove default gencode set; only generate compute_50.
sed -i 's/-gencode arch=.*\\//' Makefile.config
sed -i 's/CUDA_ARCH :=//' Makefile.config
# Only generate compute_50.
GENCODE="-gencode arch=compute_50,code=sm_50"
GENCODE="$GENCODE -gencode arch=compute_50,code=compute_50"
echo "CUDA_ARCH := $GENCODE" >> Makefile.config
fi

cat << 'EOF' >> Makefile.config
ANACONDA_HOME := $(HOME)/miniconda
PYTHON_INCLUDE := $(ANACONDA_HOME)/include \
$(ANACONDA_HOME)/include/python2.7 \
$(ANACONDA_HOME)/lib/python2.7/site-packages/numpy/core/include
PYTHON_LIB := $(ANACONDA_HOME)/lib
INCLUDE_DIRS := $(PYTHON_INCLUDE) /usr/local/include
LIBRARY_DIRS := $(PYTHON_LIB) /usr/local/lib /usr/lib
EOF