summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--CMakeLists.txt16
-rw-r--r--CONTRIBUTORS.md2
-rw-r--r--Makefile2
-rw-r--r--README.md6
-rw-r--r--cmake/Dependencies.cmake2
-rw-r--r--cmake/Uninstall.cmake.in26
-rw-r--r--docker/cpu/Dockerfile3
-rw-r--r--docker/gpu/Dockerfile5
-rw-r--r--docs/_layouts/default.html2
-rw-r--r--docs/development.md4
-rw-r--r--docs/index.md47
-rw-r--r--docs/install_apt.md2
-rw-r--r--docs/model_zoo.md24
-rw-r--r--docs/multigpu.md4
-rw-r--r--docs/performance_hardware.md73
-rw-r--r--docs/tutorial/interfaces.md4
-rw-r--r--examples/CMakeLists.txt3
-rw-r--r--examples/cifar10/cifar10_quick_solver.prototxt1
-rwxr-xr-xexamples/cifar10/train_full.sh4
-rwxr-xr-xexamples/cifar10/train_quick.sh2
-rw-r--r--examples/finetune_flickr_style/readme.md2
-rw-r--r--include/caffe/layers/infogain_loss_layer.hpp35
-rw-r--r--include/caffe/layers/window_data_layer.hpp3
-rw-r--r--include/caffe/util/math_functions.hpp6
-rw-r--r--include/caffe/util/mkl_alternate.hpp1
-rw-r--r--models/bvlc_alexnet/readme.md2
-rw-r--r--models/bvlc_googlenet/readme.md2
-rw-r--r--models/bvlc_reference_caffenet/readme.md2
-rw-r--r--models/bvlc_reference_rcnn_ilsvrc13/readme.md2
-rw-r--r--python/caffe/io.py2
-rw-r--r--python/caffe/net_spec.py4
-rw-r--r--python/caffe/pycaffe.py4
-rw-r--r--python/caffe/test/test_net.py45
-rw-r--r--python/caffe/test/test_net_spec.py8
-rw-r--r--scripts/caffe73
-rwxr-xr-xscripts/travis/install-deps.sh8
-rw-r--r--src/caffe/CMakeLists.txt6
-rw-r--r--src/caffe/layers/batch_norm_layer.cpp6
-rw-r--r--src/caffe/layers/batch_norm_layer.cu8
-rw-r--r--src/caffe/layers/infogain_loss_layer.cpp172
-rw-r--r--src/caffe/layers/lstm_unit_layer.cpp1
-rw-r--r--src/caffe/layers/pooling_layer.cu4
-rw-r--r--src/caffe/layers/sigmoid_layer.cpp2
-rw-r--r--src/caffe/layers/sigmoid_layer.cu2
-rw-r--r--src/caffe/proto/caffe.proto1
-rw-r--r--src/caffe/test/test_convolution_layer.cpp2
-rw-r--r--src/caffe/test/test_gradient_based_solver.cpp12
-rw-r--r--src/caffe/test/test_infogain_loss_layer.cpp83
-rw-r--r--src/caffe/test/test_neuron_layer.cpp11
-rw-r--r--src/caffe/util/math_functions.cpp10
-rw-r--r--src/caffe/util/math_functions.cu21
-rw-r--r--tools/CMakeLists.txt3
-rw-r--r--tools/compute_image_mean.cpp8
-rwxr-xr-xtools/extra/parse_log.sh2
-rwxr-xr-xtools/extra/resize_and_crop_images.py2
55 files changed, 572 insertions, 215 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 3056d75..08f56a3 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -10,14 +10,15 @@ endif()
project(Caffe C CXX)
# ---[ Caffe version
-set(CAFFE_TARGET_VERSION "1.0.0-rc5" CACHE STRING "Caffe logical version")
-set(CAFFE_TARGET_SOVERSION "1.0.0-rc5" CACHE STRING "Caffe soname version")
+set(CAFFE_TARGET_VERSION "1.0.0" CACHE STRING "Caffe logical version")
+set(CAFFE_TARGET_SOVERSION "1.0.0" CACHE STRING "Caffe soname version")
add_definitions(-DCAFFE_VERSION=${CAFFE_TARGET_VERSION})
# ---[ Using cmake scripts and modules
list(APPEND CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/cmake/Modules)
include(ExternalProject)
+include(GNUInstallDirs)
include(cmake/Utils.cmake)
include(cmake/Targets.cmake)
@@ -103,8 +104,19 @@ if(BUILD_python)
add_dependencies(pytest pycaffe)
endif()
+# ---[ uninstall target
+configure_file(
+ ${CMAKE_CURRENT_SOURCE_DIR}/cmake/Uninstall.cmake.in
+ ${CMAKE_CURRENT_BINARY_DIR}/cmake/Uninstall.cmake
+ IMMEDIATE @ONLY)
+
+add_custom_target(uninstall
+ COMMAND ${CMAKE_COMMAND} -P
+ ${CMAKE_CURRENT_BINARY_DIR}/cmake/Uninstall.cmake)
+
# ---[ Configuration summary
caffe_print_configuration_summary()
# ---[ Export configs generation
caffe_generate_export_configs()
+
diff --git a/CONTRIBUTORS.md b/CONTRIBUTORS.md
index 8db66ea..3fd7678 100644
--- a/CONTRIBUTORS.md
+++ b/CONTRIBUTORS.md
@@ -1,6 +1,6 @@
# Contributors
-Caffe is developed by a core set of BVLC members and the open-source community.
+Caffe is developed by a core set of BAIR members and the open-source community.
We thank all of our [contributors](https://github.com/BVLC/caffe/graphs/contributors)!
diff --git a/Makefile b/Makefile
index 77900b6..4d32416 100644
--- a/Makefile
+++ b/Makefile
@@ -34,7 +34,7 @@ LIB_BUILD_DIR := $(BUILD_DIR)/lib
STATIC_NAME := $(LIB_BUILD_DIR)/lib$(LIBRARY_NAME).a
DYNAMIC_VERSION_MAJOR := 1
DYNAMIC_VERSION_MINOR := 0
-DYNAMIC_VERSION_REVISION := 0-rc5
+DYNAMIC_VERSION_REVISION := 0
DYNAMIC_NAME_SHORT := lib$(LIBRARY_NAME).so
#DYNAMIC_SONAME_SHORT := $(DYNAMIC_NAME_SHORT).$(DYNAMIC_VERSION_MAJOR)
DYNAMIC_VERSIONED_NAME_SHORT := $(DYNAMIC_NAME_SHORT).$(DYNAMIC_VERSION_MAJOR).$(DYNAMIC_VERSION_MINOR).$(DYNAMIC_VERSION_REVISION)
diff --git a/README.md b/README.md
index 44b9e62..0ae3616 100644
--- a/README.md
+++ b/README.md
@@ -4,13 +4,13 @@
[![License](https://img.shields.io/badge/license-BSD-blue.svg)](LICENSE)
Caffe is a deep learning framework made with expression, speed, and modularity in mind.
-It is developed by the Berkeley Vision and Learning Center ([BVLC](http://bvlc.eecs.berkeley.edu)) and community contributors.
+It is developed by Berkeley AI Research ([BAIR](http://bair.berkeley.edu))/The Berkeley Vision and Learning Center (BVLC) and community contributors.
Check out the [project site](http://caffe.berkeleyvision.org) for all the details like
- [DIY Deep Learning for Vision with Caffe](https://docs.google.com/presentation/d/1UeKXVgRvvxg9OUdh_UiC5G71UMscNPlvArsWER41PsU/edit#slide=id.p)
- [Tutorial Documentation](http://caffe.berkeleyvision.org/tutorial/)
-- [BVLC reference models](http://caffe.berkeleyvision.org/model_zoo.html) and the [community model zoo](https://github.com/BVLC/caffe/wiki/Model-Zoo)
+- [BAIR reference models](http://caffe.berkeleyvision.org/model_zoo.html) and the [community model zoo](https://github.com/BVLC/caffe/wiki/Model-Zoo)
- [Installation instructions](http://caffe.berkeleyvision.org/installation.html)
and step-by-step examples.
@@ -25,7 +25,7 @@ Happy brewing!
## License and Citation
Caffe is released under the [BSD 2-Clause license](https://github.com/BVLC/caffe/blob/master/LICENSE).
-The BVLC reference models are released for unrestricted use.
+The BAIR/BVLC reference models are released for unrestricted use.
Please cite Caffe in your publications if it helps your research:
diff --git a/cmake/Dependencies.cmake b/cmake/Dependencies.cmake
index 02c8152..4a5bac4 100644
--- a/cmake/Dependencies.cmake
+++ b/cmake/Dependencies.cmake
@@ -5,7 +5,7 @@ set(Caffe_DEFINITIONS "")
set(Caffe_COMPILE_OPTIONS "")
# ---[ Boost
-find_package(Boost 1.46 REQUIRED COMPONENTS system thread filesystem)
+find_package(Boost 1.55 REQUIRED COMPONENTS system thread filesystem)
list(APPEND Caffe_INCLUDE_DIRS PUBLIC ${Boost_INCLUDE_DIRS})
list(APPEND Caffe_LINKER_LIBS PUBLIC ${Boost_LIBRARIES})
diff --git a/cmake/Uninstall.cmake.in b/cmake/Uninstall.cmake.in
new file mode 100644
index 0000000..bb8e296
--- /dev/null
+++ b/cmake/Uninstall.cmake.in
@@ -0,0 +1,26 @@
+if(NOT EXISTS "@CMAKE_CURRENT_BINARY_DIR@/install_manifest.txt")
+ message(FATAL_ERROR "Cannot find install manifest: @CMAKE_CURRENT_BINARY_DIR@/install_manifest.txt")
+endif(NOT EXISTS "@CMAKE_CURRENT_BINARY_DIR@/install_manifest.txt")
+
+if (NOT DEFINED CMAKE_INSTALL_PREFIX)
+ set (CMAKE_INSTALL_PREFIX "@CMAKE_INSTALL_PREFIX@")
+endif ()
+ message(${CMAKE_INSTALL_PREFIX})
+
+file(READ "@CMAKE_CURRENT_BINARY_DIR@/install_manifest.txt" files)
+string(REGEX REPLACE "\n" ";" files "${files}")
+foreach(file ${files})
+ message(STATUS "Uninstalling $ENV{DESTDIR}${file}")
+ if(IS_SYMLINK "$ENV{DESTDIR}${file}" OR EXISTS "$ENV{DESTDIR}${file}")
+ exec_program(
+ "@CMAKE_COMMAND@" ARGS "-E remove \"$ENV{DESTDIR}${file}\""
+ OUTPUT_VARIABLE rm_out
+ RETURN_VALUE rm_retval
+ )
+ if(NOT "${rm_retval}" STREQUAL 0)
+ message(FATAL_ERROR "Problem when removing $ENV{DESTDIR}${file}")
+ endif(NOT "${rm_retval}" STREQUAL 0)
+ else(IS_SYMLINK "$ENV{DESTDIR}${file}" OR EXISTS "$ENV{DESTDIR}${file}")
+ message(STATUS "File $ENV{DESTDIR}${file} does not exist.")
+ endif(IS_SYMLINK "$ENV{DESTDIR}${file}" OR EXISTS "$ENV{DESTDIR}${file}")
+endforeach(file) \ No newline at end of file
diff --git a/docker/cpu/Dockerfile b/docker/cpu/Dockerfile
index af6c03c..67e2e61 100644
--- a/docker/cpu/Dockerfile
+++ b/docker/cpu/Dockerfile
@@ -28,7 +28,8 @@ ENV CAFFE_ROOT=/opt/caffe
WORKDIR $CAFFE_ROOT
# FIXME: use ARG instead of ENV once DockerHub supports this
-ENV CLONE_TAG=rc4
+# https://github.com/docker/hub-feedback/issues/460
+ENV CLONE_TAG=1.0
RUN git clone -b ${CLONE_TAG} --depth 1 https://github.com/BVLC/caffe.git . && \
pip install --upgrade pip && \
diff --git a/docker/gpu/Dockerfile b/docker/gpu/Dockerfile
index 0785b10..dcdbdf3 100644
--- a/docker/gpu/Dockerfile
+++ b/docker/gpu/Dockerfile
@@ -1,4 +1,4 @@
-FROM nvidia/cuda:8.0-cudnn5-devel-ubuntu16.04
+FROM nvidia/cuda:8.0-cudnn6-devel-ubuntu16.04
LABEL maintainer caffe-maint@googlegroups.com
RUN apt-get update && apt-get install -y --no-install-recommends \
@@ -28,7 +28,8 @@ ENV CAFFE_ROOT=/opt/caffe
WORKDIR $CAFFE_ROOT
# FIXME: use ARG instead of ENV once DockerHub supports this
-ENV CLONE_TAG=rc4
+# https://github.com/docker/hub-feedback/issues/460
+ENV CLONE_TAG=1.0
RUN git clone -b ${CLONE_TAG} --depth 1 https://github.com/BVLC/caffe.git . && \
pip install --upgrade pip && \
diff --git a/docs/_layouts/default.html b/docs/_layouts/default.html
index b8efe60..3799e95 100644
--- a/docs/_layouts/default.html
+++ b/docs/_layouts/default.html
@@ -36,7 +36,7 @@
<header>
<h1 class="header"><a href="/">Caffe</a></h1>
<p class="header">
- Deep learning framework by the <a class="header name" href="http://bvlc.eecs.berkeley.edu/">BVLC</a>
+ Deep learning framework by <a class="header name" href="http://bair.berkeley.edu/">BAIR</a>
</p>
<p class="header">
Created by
diff --git a/docs/development.md b/docs/development.md
index 107c2c3..ec05bbe 100644
--- a/docs/development.md
+++ b/docs/development.md
@@ -4,7 +4,7 @@ title: Developing and Contributing
# Development and Contributing
Caffe is developed with active participation of the community.<br>
-The [BVLC](http://bvlc.eecs.berkeley.edu/) brewers welcome all contributions!
+The [BAIR](http://bair.berkeley.edu/)/BVLC brewers welcome all contributions!
The exact details of contributions are recorded by versioning and cited in our [acknowledgements](http://caffe.berkeleyvision.org/#acknowledgements).
This method is impartial and always up-to-date.
@@ -37,7 +37,7 @@ We absolutely appreciate any contribution to this effort!
The `master` branch receives all new development including community contributions.
We try to keep it in a reliable state, but it is the bleeding edge, and things do get broken every now and then.
-BVLC maintainers will periodically make releases by marking stable checkpoints as tags and maintenance branches. [Past releases](https://github.com/BVLC/caffe/releases) are catalogued online.
+BAIR maintainers will periodically make releases by marking stable checkpoints as tags and maintenance branches. [Past releases](https://github.com/BVLC/caffe/releases) are catalogued online.
#### Issues & Pull Request Protocol
diff --git a/docs/index.md b/docs/index.md
index 932b3b5..b633f7c 100644
--- a/docs/index.md
+++ b/docs/index.md
@@ -5,7 +5,7 @@ title: Deep Learning Framework
# Caffe
Caffe is a deep learning framework made with expression, speed, and modularity in mind.
-It is developed by the Berkeley Vision and Learning Center ([BVLC](http://bvlc.eecs.berkeley.edu)) and by community contributors.
+It is developed by Berkeley AI Research ([BAIR](http://bair.berkeley.edu)) and by community contributors.
[Yangqing Jia](http://daggerfs.com) created the project during his PhD at UC Berkeley.
Caffe is released under the [BSD 2-Clause license](https://github.com/BVLC/caffe/blob/master/LICENSE).
@@ -23,21 +23,20 @@ Thanks to these contributors the framework tracks the state-of-the-art in both c
**Speed** makes Caffe perfect for research experiments and industry deployment.
Caffe can process **over 60M images per day** with a single NVIDIA K40 GPU\*.
-That's 1 ms/image for inference and 4 ms/image for learning.
-We believe that Caffe is the fastest convnet implementation available.
+That's 1 ms/image for inference and 4 ms/image for learning and more recent library versions and hardware are faster still.
+We believe that Caffe is among the fastest convnet implementations available.
**Community**: Caffe already powers academic research projects, startup prototypes, and even large-scale industrial applications in vision, speech, and multimedia.
Join our community of brewers on the [caffe-users group](https://groups.google.com/forum/#!forum/caffe-users) and [Github](https://github.com/BVLC/caffe/).
<p class="footnote" markdown="1">
-\* With the ILSVRC2012-winning [SuperVision](http://www.image-net.org/challenges/LSVRC/2012/supervision.pdf) model and caching IO.
-Consult performance [details](/performance_hardware.html).
+\* With the ILSVRC2012-winning [SuperVision](http://www.image-net.org/challenges/LSVRC/2012/supervision.pdf) model and prefetching IO.
</p>
## Documentation
-- [DIY Deep Learning for Vision with Caffe](https://docs.google.com/presentation/d/1UeKXVgRvvxg9OUdh_UiC5G71UMscNPlvArsWER41PsU/edit#slide=id.p)<br>
-Tutorial presentation.
+- [DIY Deep Learning for Vision with Caffe](https://docs.google.com/presentation/d/1UeKXVgRvvxg9OUdh_UiC5G71UMscNPlvArsWER41PsU/edit#slide=id.p) and [Caffe in a Day](https://docs.google.com/presentation/d/1HxGdeq8MPktHaPb-rlmYYQ723iWzq9ur6Gjo71YiG0Y/edit#slide=id.gc2fcdcce7_216_0)<br>
+Tutorial presentation of the framework and a full-day crash course.
- [Tutorial Documentation](/tutorial)<br>
Practical guide and framework reference.
- [arXiv / ACM MM '14 paper](http://arxiv.org/abs/1408.5093)<br>
@@ -45,18 +44,13 @@ A 4-page report for the ACM Multimedia Open Source competition (arXiv:1408.5093v
- [Installation instructions](/installation.html)<br>
Tested on Ubuntu, Red Hat, OS X.
* [Model Zoo](/model_zoo.html)<br>
-BVLC suggests a standard distribution format for Caffe models, and provides trained models.
+BAIR suggests a standard distribution format for Caffe models, and provides trained models.
* [Developing & Contributing](/development.html)<br>
Guidelines for development and contributing to Caffe.
* [API Documentation](/doxygen/annotated.html)<br>
Developer documentation automagically generated from code comments.
-
-### Examples
-
-{% assign examples = site.pages | where:'category','example' | sort: 'priority' %}
-{% for page in examples %}
-- <div><a href="{{page.url}}">{{page.title}}</a><br>{{page.description}}</div>
-{% endfor %}
+* [Benchmarking](https://docs.google.com/spreadsheets/d/1Yp4rqHpT7mKxOPbpzYeUfEFLnELDAgxSSBQKp5uKDGQ/edit#gid=0)<br>
+Comparison of inference and learning for different networks and GPUs.
### Notebook Examples
@@ -65,6 +59,13 @@ Developer documentation automagically generated from code comments.
- <div><a href="http://nbviewer.ipython.org/github/BVLC/caffe/blob/master/{{page.original_path}}">{{page.title}}</a><br>{{page.description}}</div>
{% endfor %}
+### Command Line Examples
+
+{% assign examples = site.pages | where:'category','example' | sort: 'priority' %}
+{% for page in examples %}
+- <div><a href="{{page.url}}">{{page.title}}</a><br>{{page.description}}</div>
+{% endfor %}
+
## Citing Caffe
Please cite Caffe in your publications if it helps your research:
@@ -76,8 +77,7 @@ Please cite Caffe in your publications if it helps your research:
Year = {2014}
}
-If you do publish a paper where Caffe helped your research, we encourage you to update the [publications wiki](https://github.com/BVLC/caffe/wiki/Publications).
-Citations are also tracked automatically by [Google Scholar](http://scholar.google.com/scholar?oi=bibs&hl=en&cites=17333247995453974016).
+If you do publish a paper where Caffe helped your research, we encourage you to cite the framework for tracking by [Google Scholar](https://scholar.google.com/citations?view_op=view_citation&hl=en&citation_for_view=-ltRSM0AAAAJ:u5HHmVD_uO8C).
## Contacting Us
@@ -85,17 +85,12 @@ Join the [caffe-users group](https://groups.google.com/forum/#!forum/caffe-users
Framework development discussions and thorough bug reports are collected on [Issues](https://github.com/BVLC/caffe/issues).
-Contact [caffe-dev](mailto:caffe-dev@googlegroups.com) if you have a confidential proposal for the framework *and the ability to act on it*.
-Requests for features, explanations, or personal help will be ignored; post to [caffe-users](https://groups.google.com/forum/#!forum/caffe-users) instead.
-
-The core Caffe developers offer [consulting services](mailto:caffe-coldpress@googlegroups.com) for appropriate projects.
-
## Acknowledgements
-The BVLC Caffe developers would like to thank NVIDIA for GPU donation, A9 and Amazon Web Services for a research grant in support of Caffe development and reproducible research in deep learning, and BVLC PI [Trevor Darrell](http://www.eecs.berkeley.edu/~trevor/) for guidance.
+The BAIR Caffe developers would like to thank NVIDIA for GPU donation, A9 and Amazon Web Services for a research grant in support of Caffe development and reproducible research in deep learning, and BAIR PI [Trevor Darrell](http://www.eecs.berkeley.edu/~trevor/) for guidance.
-The BVLC members who have contributed to Caffe are (alphabetical by first name):
-[Eric Tzeng](https://github.com/erictzeng), [Evan Shelhamer](http://imaginarynumber.net/), [Jeff Donahue](http://jeffdonahue.com/), [Jon Long](https://github.com/longjon), [Ross Girshick](http://www.cs.berkeley.edu/~rbg/), [Sergey Karayev](http://sergeykarayev.com/), [Sergio Guadarrama](http://www.eecs.berkeley.edu/~sguada/), and [Yangqing Jia](http://daggerfs.com/).
+The BAIR members who have contributed to Caffe are (alphabetical by first name):
+[Carl Doersch](http://www.carldoersch.com/), [Eric Tzeng](https://github.com/erictzeng), [Evan Shelhamer](http://imaginarynumber.net/), [Jeff Donahue](http://jeffdonahue.com/), [Jon Long](https://github.com/longjon), [Philipp Krähenbühl](http://www.philkr.net/), [Ronghang Hu](http://ronghanghu.com/), [Ross Girshick](http://www.cs.berkeley.edu/~rbg/), [Sergey Karayev](http://sergeykarayev.com/), [Sergio Guadarrama](http://www.eecs.berkeley.edu/~sguada/), [Takuya Narihira](https://github.com/tnarihi), and [Yangqing Jia](http://daggerfs.com/).
The open-source community plays an important and growing role in Caffe's development.
Check out the Github [project pulse](https://github.com/BVLC/caffe/pulse) for recent activity and the [contributors](https://github.com/BVLC/caffe/graphs/contributors) for the full list.
@@ -103,4 +98,4 @@ Check out the Github [project pulse](https://github.com/BVLC/caffe/pulse) for re
We sincerely appreciate your interest and contributions!
If you'd like to contribute, please read the [developing & contributing](development.html) guide.
-Yangqing would like to give a personal thanks to the NVIDIA Academic program for providing GPUs, [Oriol Vinyals](http://www1.icsi.berkeley.edu/~vinyals/) for discussions along the journey, and BVLC PI [Trevor Darrell](http://www.eecs.berkeley.edu/~trevor/) for advice.
+Yangqing would like to give a personal thanks to the NVIDIA Academic program for providing GPUs, [Oriol Vinyals](http://www1.icsi.berkeley.edu/~vinyals/) for discussions along the journey, and BAIR PI [Trevor Darrell](http://www.eecs.berkeley.edu/~trevor/) for advice.
diff --git a/docs/install_apt.md b/docs/install_apt.md
index bc1566b..ee2cd28 100644
--- a/docs/install_apt.md
+++ b/docs/install_apt.md
@@ -14,7 +14,7 @@ The NVIDIA package tends to follow more recent library and driver versions, but
If installing from packages, install the library and latest driver separately; the driver bundled with the library is usually out-of-date.
This can be skipped for CPU-only installation.
-**BLAS**: install ATLAS by `sudo apt-get install libatlas-base-dev` or install OpenBLAS or MKL for better CPU performance.
+**BLAS**: install ATLAS by `sudo apt-get install libatlas-base-dev` or install OpenBLAS by `sudo apt-get install libopenblas-dev` or MKL for better CPU performance.
**Python** (optional): if you use the default Python you will need to `sudo apt-get install` the `python-dev` package to have the Python headers for building the pycaffe interface.
diff --git a/docs/model_zoo.md b/docs/model_zoo.md
index 06dc0a4..3f77e82 100644
--- a/docs/model_zoo.md
+++ b/docs/model_zoo.md
@@ -3,7 +3,7 @@ title: Model Zoo
---
# Caffe Model Zoo
-Lots of researchers and engineers have made Caffe models for different tasks with all kinds of architectures and data.
+Lots of researchers and engineers have made Caffe models for different tasks with all kinds of architectures and data: check out the [model zoo](https://github.com/BVLC/caffe/wiki/Model-Zoo)!
These models are learned and applied for problems ranging from simple regression, to large-scale visual classification, to Siamese networks for image similarity, to speech and robotics applications.
To help share these models, we introduce the model zoo framework:
@@ -14,17 +14,17 @@ To help share these models, we introduce the model zoo framework:
## Where to get trained models
-First of all, we bundle BVLC-trained models for unrestricted, out of the box use.
+First of all, we bundle BAIR-trained models for unrestricted, out of the box use.
<br>
-See the [BVLC model license](#bvlc-model-license) for details.
+See the [BAIR model license](#bair-model-license) for details.
Each one of these can be downloaded by running `scripts/download_model_binary.py <dirname>` where `<dirname>` is specified below:
-- **BVLC Reference CaffeNet** in `models/bvlc_reference_caffenet`: AlexNet trained on ILSVRC 2012, with a minor variation from the version as described in [ImageNet classification with deep convolutional neural networks](http://papers.nips.cc/paper/4824-imagenet-classification-with-deep-convolutional-neural-networks) by Krizhevsky et al. in NIPS 2012. (Trained by Jeff Donahue @jeffdonahue)
-- **BVLC AlexNet** in `models/bvlc_alexnet`: AlexNet trained on ILSVRC 2012, almost exactly as described in [ImageNet classification with deep convolutional neural networks](http://papers.nips.cc/paper/4824-imagenet-classification-with-deep-convolutional-neural-networks) by Krizhevsky et al. in NIPS 2012. (Trained by Evan Shelhamer @shelhamer)
-- **BVLC Reference R-CNN ILSVRC-2013** in `models/bvlc_reference_rcnn_ilsvrc13`: pure Caffe implementation of [R-CNN](https://github.com/rbgirshick/rcnn) as described by Girshick et al. in CVPR 2014. (Trained by Ross Girshick @rbgirshick)
-- **BVLC GoogLeNet** in `models/bvlc_googlenet`: GoogLeNet trained on ILSVRC 2012, almost exactly as described in [Going Deeper with Convolutions](http://arxiv.org/abs/1409.4842) by Szegedy et al. in ILSVRC 2014. (Trained by Sergio Guadarrama @sguada)
+- **BAIR Reference CaffeNet** in `models/bvlc_reference_caffenet`: AlexNet trained on ILSVRC 2012, with a minor variation from the version as described in [ImageNet classification with deep convolutional neural networks](http://papers.nips.cc/paper/4824-imagenet-classification-with-deep-convolutional-neural-networks) by Krizhevsky et al. in NIPS 2012. (Trained by Jeff Donahue @jeffdonahue)
+- **BAIR AlexNet** in `models/bvlc_alexnet`: AlexNet trained on ILSVRC 2012, almost exactly as described in [ImageNet classification with deep convolutional neural networks](http://papers.nips.cc/paper/4824-imagenet-classification-with-deep-convolutional-neural-networks) by Krizhevsky et al. in NIPS 2012. (Trained by Evan Shelhamer @shelhamer)
+- **BAIR Reference R-CNN ILSVRC-2013** in `models/bvlc_reference_rcnn_ilsvrc13`: pure Caffe implementation of [R-CNN](https://github.com/rbgirshick/rcnn) as described by Girshick et al. in CVPR 2014. (Trained by Ross Girshick @rbgirshick)
+- **BAIR GoogLeNet** in `models/bvlc_googlenet`: GoogLeNet trained on ILSVRC 2012, almost exactly as described in [Going Deeper with Convolutions](http://arxiv.org/abs/1409.4842) by Szegedy et al. in ILSVRC 2014. (Trained by Sergio Guadarrama @sguada)
-**Community models** made by Caffe users are posted to a publicly editable [wiki page](https://github.com/BVLC/caffe/wiki/Model-Zoo).
+**Community models** made by Caffe users are posted to a publicly editable [model zoo wiki page](https://github.com/BVLC/caffe/wiki/Model-Zoo).
These models are subject to conditions of their respective authors such as citation and license.
Thank you for sharing your models!
@@ -42,6 +42,8 @@ A caffe model is distributed as a directory containing:
- License information.
- [optional] Other helpful scripts.
+This simple format can be handled through bundled scripts or manually if need be.
+
### Hosting model info
Github Gist is a good format for model info distribution because it can contain multiple files, is versionable, and has in-browser syntax highlighting and markdown rendering.
@@ -55,14 +57,14 @@ Downloading model info is done just as easily with `scripts/download_model_from_
### Hosting trained models
It is up to the user where to host the `.caffemodel` file.
-We host our BVLC-provided models on our own server.
+We host our BAIR-provided models on our own server.
Dropbox also works fine (tip: make sure that `?dl=1` is appended to the end of the URL).
`scripts/download_model_binary.py <dirname>` downloads the `.caffemodel` from the URL specified in the `<dirname>/readme.md` frontmatter and confirms SHA1.
-## BVLC model license
+## BAIR model license
-The Caffe models bundled by the BVLC are released for unrestricted use.
+The Caffe models bundled by the BAIR are released for unrestricted use.
These models are trained on data from the [ImageNet project](http://www.image-net.org/) and training data includes internet photos that may be subject to copyright.
diff --git a/docs/multigpu.md b/docs/multigpu.md
index d91acef..e04ebb0 100644
--- a/docs/multigpu.md
+++ b/docs/multigpu.md
@@ -13,7 +13,7 @@ The GPUs to be used for training can be set with the "-gpu" flag on the command
# Hardware Configuration Assumptions
The current implementation uses a tree reduction strategy. e.g. if there are 4 GPUs in the system, 0:1, 2:3 will exchange gradients, then 0:2 (top of the tree) will exchange gradients, 0 will calculate
-updated model, 0\-\>2, and then 0\-\>1, 2\-\>3.
+updated model, 0\-\>2, and then 0\-\>1, 2\-\>3.
For best performance, P2P DMA access between devices is needed. Without P2P access, for example crossing PCIe root complex, data is copied through host and effective exchange bandwidth is greatly reduced.
@@ -23,4 +23,4 @@ Current implementation has a "soft" assumption that the devices being used are h
# Scaling Performance
-Performance is **heavily** dependent on the PCIe topology of the system, the configuration of the neural network you are training, and the speed of each of the layers. Systems like the DIGITS DevBox have an optimized PCIe topology (X99-E WS chipset). In general, scaling on 2 GPUs tends to be ~1.8X on average for networks like AlexNet, CaffeNet, VGG, GoogleNet. 4 GPUs begins to have falloff in scaling. Generally with "weak scaling" where the batchsize increases with the number of GPUs you will see 3.5x scaling or so. With "strong scaling", the system can become communication bound, especially with layer performance optimizations like those in [cuDNNv3](http://nvidia.com/cudnn), and you will likely see closer to mid 2.x scaling in performance. Networks that have heavy computation compared to the number of parameters tend to have the best scaling performance. \ No newline at end of file
+Performance is **heavily** dependent on the PCIe topology of the system, the configuration of the neural network you are training, and the speed of each of the layers. Systems like the DIGITS DevBox have an optimized PCIe topology (X99-E WS chipset). In general, scaling on 2 GPUs tends to be ~1.8X on average for networks like AlexNet, CaffeNet, VGG, GoogleNet. 4 GPUs begins to have falloff in scaling. Generally with "weak scaling" where the batchsize increases with the number of GPUs you will see 3.5x scaling or so. With "strong scaling", the system can become communication bound, especially with layer performance optimizations like those in [cuDNNv3](http://nvidia.com/cudnn), and you will likely see closer to mid 2.x scaling in performance. Networks that have heavy computation compared to the number of parameters tend to have the best scaling performance.
diff --git a/docs/performance_hardware.md b/docs/performance_hardware.md
deleted file mode 100644
index cdd4b36..0000000
--- a/docs/performance_hardware.md
+++ /dev/null
@@ -1,73 +0,0 @@
----
-title: Performance and Hardware Configuration
----
-
-# Performance and Hardware Configuration
-
-To measure performance on different NVIDIA GPUs we use CaffeNet, the Caffe reference ImageNet model.
-
-For training, each time point is 20 iterations/minibatches of 256 images for 5,120 images total. For testing, a 50,000 image validation set is classified.
-
-**Acknowledgements**: BVLC members are very grateful to NVIDIA for providing several GPUs to conduct this research.
-
-## NVIDIA K40
-
-Performance is best with ECC off and boost clock enabled. While ECC makes a negligible difference in speed, disabling it frees ~1 GB of GPU memory.
-
-Best settings with ECC off and maximum clock speed in standard Caffe:
-
-* Training is 26.5 secs / 20 iterations (5,120 images)
-* Testing is 100 secs / validation set (50,000 images)
-
-Best settings with Caffe + [cuDNN acceleration](http://nvidia.com/cudnn):
-
-* Training is 19.2 secs / 20 iterations (5,120 images)
-* Testing is 60.7 secs / validation set (50,000 images)
-
-Other settings:
-
-* ECC on, max speed: training 26.7 secs / 20 iterations, test 101 secs / validation set
-* ECC on, default speed: training 31 secs / 20 iterations, test 117 secs / validation set
-* ECC off, default speed: training 31 secs / 20 iterations, test 118 secs / validation set
-
-### K40 configuration tips
-
-For maximum K40 performance, turn off ECC and boost the clock speed (at your own risk).
-
-To turn off ECC, do
-
- sudo nvidia-smi -i 0 --ecc-config=0 # repeat with -i x for each GPU ID
-
-then reboot.
-
-Set the "persistence" mode of the GPU settings by
-
- sudo nvidia-smi -pm 1
-
-and then set the clock speed with
-
- sudo nvidia-smi -i 0 -ac 3004,875 # repeat with -i x for each GPU ID
-
-but note that this configuration resets across driver reloading / rebooting. Include these commands in a boot script to initialize these settings. For a simple fix, add these commands to `/etc/rc.local` (on Ubuntu).
-
-## NVIDIA Titan
-
-Training: 26.26 secs / 20 iterations (5,120 images).
-Testing: 100 secs / validation set (50,000 images).
-
-cuDNN Training: 20.25 secs / 20 iterations (5,120 images).
-cuDNN Testing: 66.3 secs / validation set (50,000 images).
-
-
-## NVIDIA K20
-
-Training: 36.0 secs / 20 iterations (5,120 images).
-Testing: 133 secs / validation set (50,000 images).
-
-## NVIDIA GTX 770
-
-Training: 33.0 secs / 20 iterations (5,120 images).
-Testing: 129 secs / validation set (50,000 images).
-
-cuDNN Training: 24.3 secs / 20 iterations (5,120 images).
-cuDNN Testing: 104 secs / validation set (50,000 images).
diff --git a/docs/tutorial/interfaces.md b/docs/tutorial/interfaces.md
index d7ff378..b5a4f1a 100644
--- a/docs/tutorial/interfaces.md
+++ b/docs/tutorial/interfaces.md
@@ -91,7 +91,7 @@ In MatCaffe, you can
* Run for a certain number of iterations and give back control to Matlab
* Intermingle arbitrary Matlab code with gradient steps
-An ILSVRC image classification demo is in caffe/matlab/demo/classification_demo.m (you need to download BVLC CaffeNet from [Model Zoo](http://caffe.berkeleyvision.org/model_zoo.html) to run it).
+An ILSVRC image classification demo is in caffe/matlab/demo/classification_demo.m (you need to download BAIR CaffeNet from [Model Zoo](http://caffe.berkeleyvision.org/model_zoo.html) to run it).
### Build MatCaffe
@@ -114,7 +114,7 @@ You can save your Matlab search PATH by running `savepath` so that you don't hav
MatCaffe is very similar to PyCaffe in usage.
-Examples below shows detailed usages and assumes you have downloaded BVLC CaffeNet from [Model Zoo](http://caffe.berkeleyvision.org/model_zoo.html) and started `matlab` from caffe root folder.
+Examples below shows detailed usages and assumes you have downloaded BAIR CaffeNet from [Model Zoo](http://caffe.berkeleyvision.org/model_zoo.html) and started `matlab` from caffe root folder.
model = './models/bvlc_reference_caffenet/deploy.prototxt';
weights = './models/bvlc_reference_caffenet/bvlc_reference_caffenet.caffemodel';
diff --git a/examples/CMakeLists.txt b/examples/CMakeLists.txt
index a59e0df..43bbcb8 100644
--- a/examples/CMakeLists.txt
+++ b/examples/CMakeLists.txt
@@ -19,7 +19,8 @@ foreach(source_file ${examples_srcs})
caffe_set_solution_folder(${name} examples)
# install
- install(TARGETS ${name} DESTINATION bin)
+ install(TARGETS ${name} DESTINATION ${CMAKE_INSTALL_BINDIR})
+
if(UNIX OR APPLE)
# Funny command to make tutorials work
diff --git a/examples/cifar10/cifar10_quick_solver.prototxt b/examples/cifar10/cifar10_quick_solver.prototxt
index 5de276f..14b4401 100644
--- a/examples/cifar10/cifar10_quick_solver.prototxt
+++ b/examples/cifar10/cifar10_quick_solver.prototxt
@@ -20,7 +20,6 @@ display: 100
max_iter: 4000
# snapshot intermediate results
snapshot: 4000
-snapshot_format: HDF5
snapshot_prefix: "examples/cifar10/cifar10_quick"
# solver mode: CPU or GPU
solver_mode: GPU
diff --git a/examples/cifar10/train_full.sh b/examples/cifar10/train_full.sh
index 06ecc2d..fe46e60 100755
--- a/examples/cifar10/train_full.sh
+++ b/examples/cifar10/train_full.sh
@@ -9,9 +9,9 @@ $TOOLS/caffe train \
# reduce learning rate by factor of 10
$TOOLS/caffe train \
--solver=examples/cifar10/cifar10_full_solver_lr1.prototxt \
- --snapshot=examples/cifar10/cifar10_full_iter_60000.solverstate.h5 $@
+ --snapshot=examples/cifar10/cifar10_full_iter_60000.solverstate $@
# reduce learning rate by factor of 10
$TOOLS/caffe train \
--solver=examples/cifar10/cifar10_full_solver_lr2.prototxt \
- --snapshot=examples/cifar10/cifar10_full_iter_65000.solverstate.h5 $@
+ --snapshot=examples/cifar10/cifar10_full_iter_65000.solverstate $@
diff --git a/examples/cifar10/train_quick.sh b/examples/cifar10/train_quick.sh
index d2b8753..257479e 100755
--- a/examples/cifar10/train_quick.sh
+++ b/examples/cifar10/train_quick.sh
@@ -9,4 +9,4 @@ $TOOLS/caffe train \
# reduce learning rate by factor of 10 after 8 epochs
$TOOLS/caffe train \
--solver=examples/cifar10/cifar10_quick_solver_lr1.prototxt \
- --snapshot=examples/cifar10/cifar10_quick_iter_4000.solverstate.h5 $@
+ --snapshot=examples/cifar10/cifar10_quick_iter_4000.solverstate $@
diff --git a/examples/finetune_flickr_style/readme.md b/examples/finetune_flickr_style/readme.md
index 188dedf..dacfd01 100644
--- a/examples/finetune_flickr_style/readme.md
+++ b/examples/finetune_flickr_style/readme.md
@@ -9,7 +9,7 @@ priority: 5
# Fine-tuning CaffeNet for Style Recognition on "Flickr Style" Data
Fine-tuning takes an already learned model, adapts the architecture, and resumes training from the already learned model weights.
-Let's fine-tune the BVLC-distributed CaffeNet model on a different dataset, [Flickr Style](http://sergeykarayev.com/files/1311.3715v3.pdf), to predict image style instead of object category.
+Let's fine-tune the BAIR-distributed CaffeNet model on a different dataset, [Flickr Style](http://sergeykarayev.com/files/1311.3715v3.pdf), to predict image style instead of object category.
## Explanation
diff --git a/include/caffe/layers/infogain_loss_layer.hpp b/include/caffe/layers/infogain_loss_layer.hpp
index 633f339..edecde8 100644
--- a/include/caffe/layers/infogain_loss_layer.hpp
+++ b/include/caffe/layers/infogain_loss_layer.hpp
@@ -8,6 +8,7 @@
#include "caffe/proto/caffe.pb.h"
#include "caffe/layers/loss_layer.hpp"
+#include "caffe/layers/softmax_layer.hpp"
namespace caffe {
@@ -60,6 +61,12 @@ class InfogainLossLayer : public LossLayer<Dtype> {
virtual inline int MinBottomBlobs() const { return 2; }
virtual inline int MaxBottomBlobs() const { return 3; }
+ // InfogainLossLayer computes softmax prob internally.
+ // optional second "top" outputs the softmax prob
+ virtual inline int ExactNumTopBlobs() const { return -1; }
+ virtual inline int MinTopBlobs() const { return 1; }
+ virtual inline int MaxTopBlobs() const { return 2; }
+
virtual inline const char* type() const { return "InfogainLoss"; }
protected:
@@ -102,7 +109,35 @@ class InfogainLossLayer : public LossLayer<Dtype> {
virtual void Backward_cpu(const vector<Blob<Dtype>*>& top,
const vector<bool>& propagate_down, const vector<Blob<Dtype>*>& bottom);
+ /// Read the normalization mode parameter and compute the normalizer based
+ /// on the blob size. If normalization_mode is VALID, the count of valid
+ /// outputs will be read from valid_count, unless it is -1 in which case
+ /// all outputs are assumed to be valid.
+ virtual Dtype get_normalizer(
+ LossParameter_NormalizationMode normalization_mode, int valid_count);
+ /// fill sum_rows_H_ according to matrix H
+ virtual void sum_rows_of_H(const Blob<Dtype>* H);
+
+ /// The internal SoftmaxLayer used to map predictions to a distribution.
+ shared_ptr<Layer<Dtype> > softmax_layer_;
+ /// prob stores the output probability predictions from the SoftmaxLayer.
+ Blob<Dtype> prob_;
+ /// bottom vector holder used in call to the underlying SoftmaxLayer::Forward
+ vector<Blob<Dtype>*> softmax_bottom_vec_;
+ /// top vector holder used in call to the underlying SoftmaxLayer::Forward
+ vector<Blob<Dtype>*> softmax_top_vec_;
+
Blob<Dtype> infogain_;
+ Blob<Dtype> sum_rows_H_; // cache the row sums of H.
+
+ /// Whether to ignore instances with a certain label.
+ bool has_ignore_label_;
+ /// The label indicating that an instance should be ignored.
+ int ignore_label_;
+ /// How to normalize the output loss.
+ LossParameter_NormalizationMode normalization_;
+
+ int infogain_axis_, outer_num_, inner_num_, num_labels_;
};
} // namespace caffe
diff --git a/include/caffe/layers/window_data_layer.hpp b/include/caffe/layers/window_data_layer.hpp
index 35f41b8..b9b66b7 100644
--- a/include/caffe/layers/window_data_layer.hpp
+++ b/include/caffe/layers/window_data_layer.hpp
@@ -16,7 +16,8 @@ namespace caffe {
/**
* @brief Provides data to the Net from windows of images files, specified
- * by a window data file.
+ * by a window data file. This layer is *DEPRECATED* and only kept for
+ * archival purposes for use by the original R-CNN.
*
* TODO(dox): thorough documentation for Forward and proto params.
*/
diff --git a/include/caffe/util/math_functions.hpp b/include/caffe/util/math_functions.hpp
index 37abce5..e549120 100644
--- a/include/caffe/util/math_functions.hpp
+++ b/include/caffe/util/math_functions.hpp
@@ -53,6 +53,9 @@ template <typename Dtype>
void caffe_sqr(const int N, const Dtype* a, Dtype* y);
template <typename Dtype>
+void caffe_sqrt(const int N, const Dtype* a, Dtype* y);
+
+template <typename Dtype>
void caffe_add(const int N, const Dtype* a, const Dtype* b, Dtype* y);
template <typename Dtype>
@@ -214,6 +217,9 @@ void caffe_gpu_log(const int n, const Dtype* a, Dtype* y);
template <typename Dtype>
void caffe_gpu_powx(const int n, const Dtype* a, const Dtype b, Dtype* y);
+template <typename Dtype>
+void caffe_gpu_sqrt(const int n, const Dtype* a, Dtype* y);
+
// caffe_gpu_rng_uniform with two arguments generates integers in the range
// [0, UINT_MAX].
void caffe_gpu_rng_uniform(const int n, unsigned int* r);
diff --git a/include/caffe/util/mkl_alternate.hpp b/include/caffe/util/mkl_alternate.hpp
index 79b2c32..8c2294c 100644
--- a/include/caffe/util/mkl_alternate.hpp
+++ b/include/caffe/util/mkl_alternate.hpp
@@ -37,6 +37,7 @@ extern "C" {
}
DEFINE_VSL_UNARY_FUNC(Sqr, y[i] = a[i] * a[i])
+DEFINE_VSL_UNARY_FUNC(Sqrt, y[i] = sqrt(a[i]))
DEFINE_VSL_UNARY_FUNC(Exp, y[i] = exp(a[i]))
DEFINE_VSL_UNARY_FUNC(Ln, y[i] = log(a[i]))
DEFINE_VSL_UNARY_FUNC(Abs, y[i] = fabs(a[i]))
diff --git a/models/bvlc_alexnet/readme.md b/models/bvlc_alexnet/readme.md
index 008d690..a83e3d4 100644
--- a/models/bvlc_alexnet/readme.md
+++ b/models/bvlc_alexnet/readme.md
@@ -1,5 +1,5 @@
---
-name: BVLC AlexNet Model
+name: BAIR/BVLC AlexNet Model
caffemodel: bvlc_alexnet.caffemodel
caffemodel_url: http://dl.caffe.berkeleyvision.org/bvlc_alexnet.caffemodel
license: unrestricted
diff --git a/models/bvlc_googlenet/readme.md b/models/bvlc_googlenet/readme.md
index 061b6d7..ef04db6 100644
--- a/models/bvlc_googlenet/readme.md
+++ b/models/bvlc_googlenet/readme.md
@@ -1,5 +1,5 @@
---
-name: BVLC GoogleNet Model
+name: BAIR/BVLC GoogleNet Model
caffemodel: bvlc_googlenet.caffemodel
caffemodel_url: http://dl.caffe.berkeleyvision.org/bvlc_googlenet.caffemodel
license: unrestricted
diff --git a/models/bvlc_reference_caffenet/readme.md b/models/bvlc_reference_caffenet/readme.md
index 671e47a..5352e53 100644
--- a/models/bvlc_reference_caffenet/readme.md
+++ b/models/bvlc_reference_caffenet/readme.md
@@ -1,5 +1,5 @@
---
-name: BVLC CaffeNet Model
+name: BAIR/BVLC CaffeNet Model
caffemodel: bvlc_reference_caffenet.caffemodel
caffemodel_url: http://dl.caffe.berkeleyvision.org/bvlc_reference_caffenet.caffemodel
license: unrestricted
diff --git a/models/bvlc_reference_rcnn_ilsvrc13/readme.md b/models/bvlc_reference_rcnn_ilsvrc13/readme.md
index 9a11a24..12543b2 100644
--- a/models/bvlc_reference_rcnn_ilsvrc13/readme.md
+++ b/models/bvlc_reference_rcnn_ilsvrc13/readme.md
@@ -1,5 +1,5 @@
---
-name: BVLC Reference RCNN ILSVRC13 Model
+name: BAIR/BVLC Reference RCNN ILSVRC13 Model
caffemodel: bvlc_reference_rcnn_ilsvrc13.caffemodel
caffemodel_url: http://dl.caffe.berkeleyvision.org/bvlc_reference_rcnn_ilsvrc13.caffemodel
license: unrestricted
diff --git a/python/caffe/io.py b/python/caffe/io.py
index e1759be..966c164 100644
--- a/python/caffe/io.py
+++ b/python/caffe/io.py
@@ -75,7 +75,7 @@ def array_to_datum(arr, label=None):
if arr.dtype == np.uint8:
datum.data = arr.tostring()
else:
- datum.float_data.extend(arr.flat)
+ datum.float_data.extend(arr.astype(float).flat)
if label is not None:
datum.label = label
return datum
diff --git a/python/caffe/net_spec.py b/python/caffe/net_spec.py
index 5fb1f0b..20918f9 100644
--- a/python/caffe/net_spec.py
+++ b/python/caffe/net_spec.py
@@ -103,6 +103,10 @@ class Function(object):
def __init__(self, type_name, inputs, params):
self.type_name = type_name
+ for index, input in enumerate(inputs):
+ if not isinstance(input, Top):
+ raise TypeError('%s input %d is not a Top (type is %s)' %
+ (type_name, index, type(input)))
self.inputs = inputs
self.params = params
self.ntop = self.params.get('ntop', 1)
diff --git a/python/caffe/pycaffe.py b/python/caffe/pycaffe.py
index 6360659..4a7b5a2 100644
--- a/python/caffe/pycaffe.py
+++ b/python/caffe/pycaffe.py
@@ -113,7 +113,7 @@ def _Net_forward(self, blobs=None, start=None, end=None, **kwargs):
if end is not None:
end_ind = list(self._layer_names).index(end)
- outputs = set([end] + blobs)
+ outputs = set(self.top_names[end] + blobs)
else:
end_ind = len(self.layers) - 1
outputs = set(self.outputs + blobs)
@@ -161,7 +161,7 @@ def _Net_backward(self, diffs=None, start=None, end=None, **kwargs):
if end is not None:
end_ind = list(self._layer_names).index(end)
- outputs = set([end] + diffs)
+ outputs = set(self.bottom_names[end] + diffs)
else:
end_ind = 0
outputs = set(self.inputs + diffs)
diff --git a/python/caffe/test/test_net.py b/python/caffe/test/test_net.py
index 24391cc..afd2769 100644
--- a/python/caffe/test/test_net.py
+++ b/python/caffe/test/test_net.py
@@ -25,11 +25,11 @@ def simple_net_file(num_output):
bias_filler { type: 'constant' value: 2 } }
param { decay_mult: 1 } param { decay_mult: 0 }
}
- layer { type: 'InnerProduct' name: 'ip' bottom: 'conv' top: 'ip'
+ layer { type: 'InnerProduct' name: 'ip' bottom: 'conv' top: 'ip_blob'
inner_product_param { num_output: """ + str(num_output) + """
weight_filler { type: 'gaussian' std: 2.5 }
bias_filler { type: 'constant' value: -3 } } }
- layer { type: 'SoftmaxWithLoss' name: 'loss' bottom: 'ip' bottom: 'label'
+ layer { type: 'SoftmaxWithLoss' name: 'loss' bottom: 'ip_blob' bottom: 'label'
top: 'loss' }""")
f.close()
return f.name
@@ -71,6 +71,43 @@ class TestNet(unittest.TestCase):
self.net.forward()
self.net.backward()
+ def test_forward_start_end(self):
+ conv_blob=self.net.blobs['conv'];
+ ip_blob=self.net.blobs['ip_blob'];
+ sample_data=np.random.uniform(size=conv_blob.data.shape);
+ sample_data=sample_data.astype(np.float32);
+ conv_blob.data[:]=sample_data;
+ forward_blob=self.net.forward(start='ip',end='ip');
+ self.assertIn('ip_blob',forward_blob);
+
+ manual_forward=[];
+ for i in range(0,conv_blob.data.shape[0]):
+ dot=np.dot(self.net.params['ip'][0].data,
+ conv_blob.data[i].reshape(-1));
+ manual_forward.append(dot+self.net.params['ip'][1].data);
+ manual_forward=np.array(manual_forward);
+
+ np.testing.assert_allclose(ip_blob.data,manual_forward,rtol=1e-3);
+
+ def test_backward_start_end(self):
+ conv_blob=self.net.blobs['conv'];
+ ip_blob=self.net.blobs['ip_blob'];
+ sample_data=np.random.uniform(size=ip_blob.data.shape)
+ sample_data=sample_data.astype(np.float32);
+ ip_blob.diff[:]=sample_data;
+ backward_blob=self.net.backward(start='ip',end='ip');
+ self.assertIn('conv',backward_blob);
+
+ manual_backward=[];
+ for i in range(0,conv_blob.data.shape[0]):
+ dot=np.dot(self.net.params['ip'][0].data.transpose(),
+ sample_data[i].reshape(-1));
+ manual_backward.append(dot);
+ manual_backward=np.array(manual_backward);
+ manual_backward=manual_backward.reshape(conv_blob.data.shape);
+
+ np.testing.assert_allclose(conv_blob.diff,manual_backward,rtol=1e-3);
+
def test_clear_param_diffs(self):
# Run a forward/backward step to have non-zero diffs
self.net.forward()
@@ -90,13 +127,13 @@ class TestNet(unittest.TestCase):
self.assertEqual(self.net.top_names,
OrderedDict([('data', ['data', 'label']),
('conv', ['conv']),
- ('ip', ['ip']),
+ ('ip', ['ip_blob']),
('loss', ['loss'])]))
self.assertEqual(self.net.bottom_names,
OrderedDict([('data', []),
('conv', ['data']),
('ip', ['conv']),
- ('loss', ['ip', 'label'])]))
+ ('loss', ['ip_blob', 'label'])]))
def test_save_and_read(self):
f = tempfile.NamedTemporaryFile(mode='w+', delete=False)
diff --git a/python/caffe/test/test_net_spec.py b/python/caffe/test/test_net_spec.py
index fee3c0a..ffe71ba 100644
--- a/python/caffe/test/test_net_spec.py
+++ b/python/caffe/test/test_net_spec.py
@@ -79,3 +79,11 @@ class TestNetSpec(unittest.TestCase):
net_proto = silent_net()
net = self.load_net(net_proto)
self.assertEqual(len(net.forward()), 0)
+
+ def test_type_error(self):
+ """Test that a TypeError is raised when a Function input isn't a Top."""
+ data = L.DummyData(ntop=2) # data is a 2-tuple of Tops
+ r = r"^Silence input 0 is not a Top \(type is <(type|class) 'tuple'>\)$"
+ with self.assertRaisesRegexp(TypeError, r):
+ L.Silence(data, ntop=0) # should raise: data is a tuple, not a Top
+ L.Silence(*data, ntop=0) # shouldn't raise: each elt of data is a Top
diff --git a/scripts/caffe b/scripts/caffe
new file mode 100644
index 0000000..8a0b22a
--- /dev/null
+++ b/scripts/caffe
@@ -0,0 +1,73 @@
+# bash completion for Caffe's command line utility -*- shell-script -*-
+# COPYRIGHT (C) 2015,2016 Zhou Mo <cdluminate@gmail.com>
+# License: BSD-2-Clause
+# Originally appeard at https://github.com/BVLC/caffe/issues/3149
+
+# Updated for caffe (1.0.0~rc3+20160715-g42cd785)
+_caffe()
+{
+ local cur prev words cword
+ _init_completion -s || return
+
+ local prototxts='@(prototxt)'
+ local caffemodels='@(caffemodel,binaryproto)'
+ local solverstates='@(solverstate)'
+ local caffefiles='@(prototxt|caffemodel|solverstate)'
+
+ local flags='-gpu -iterations -model -snapshot -solver -weights -sighup_effect -sigint_effect -level -stage -phase'
+
+ if [[ $cword -eq 1 ]]; then
+ COMPREPLY=( $( compgen -W 'train test time device_query' -- "$cur" ) )
+ return 0
+ fi
+
+ if [[ $cword -eq 2 ]]; then
+ case ${words[1]} in
+ train|test|device_query|time)
+ COMPREPLY=( $( compgen -W "$flags" -- "$cur") )
+ return 0
+ ;;
+ *)
+ return 0
+ ;;
+ esac
+ fi
+
+ case $prev in
+ -gpu|-iterations|-version|-level|-stage)
+ return 0
+ ;;
+ -solver|-model)
+ _filedir $prototxts
+ return 0
+ ;;
+ -weights)
+ _filedir $caffemodels
+ return 0
+ ;;
+ -snapshot)
+ _filedir $solverstates
+ return 0
+ ;;
+ -sighup_effect|-sigint_effect)
+ COMPREPLY=( $( compgen -W 'snapshot stop none' -- "$cur") )
+ return 0
+ ;;
+ -phase)
+ COMPREPLY=( $( compgen -W 'TRAIN TEST' -- "$cur") )
+ return 0
+ ;;
+ *)
+ COMPREPLY=( $( compgen -W "$flags" -- "$cur") )
+ return 0
+ ;;
+ esac
+
+ # file completion on relevant files
+ _filedir "$caffefiles"
+
+ return 0
+}
+complete -F _caffe caffe
+
+# vim
diff --git a/scripts/travis/install-deps.sh b/scripts/travis/install-deps.sh
index 2fa2a74..dac5d2f 100755
--- a/scripts/travis/install-deps.sh
+++ b/scripts/travis/install-deps.sh
@@ -9,10 +9,10 @@ apt-get -y update
apt-get install -y --no-install-recommends \
build-essential \
graphviz \
- libboost-filesystem-dev \
- libboost-python-dev \
- libboost-system-dev \
- libboost-thread-dev \
+ libboost-filesystem1.55-dev \
+ libboost-python1.55-dev \
+ libboost-system1.55-dev \
+ libboost-thread1.55-dev \
libgflags-dev \
libgoogle-glog-dev \
libhdf5-serial-dev \
diff --git a/src/caffe/CMakeLists.txt b/src/caffe/CMakeLists.txt
index 7b25a98..b9152e9 100644
--- a/src/caffe/CMakeLists.txt
+++ b/src/caffe/CMakeLists.txt
@@ -40,9 +40,9 @@ set_target_properties(caffe PROPERTIES
add_subdirectory(test)
# ---[ Install
-install(DIRECTORY ${Caffe_INCLUDE_DIR}/caffe DESTINATION include)
-install(FILES ${proto_hdrs} DESTINATION include/caffe/proto)
-install(TARGETS caffe proto EXPORT CaffeTargets DESTINATION lib)
+install(DIRECTORY ${Caffe_INCLUDE_DIR}/caffe DESTINATION ${CMAKE_INSTALL_INCLUDEDIR})
+install(FILES ${proto_hdrs} DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/caffe/proto)
+install(TARGETS caffe proto EXPORT CaffeTargets DESTINATION ${CMAKE_INSTALL_LIBDIR})
file(WRITE ${PROJECT_BINARY_DIR}/__init__.py)
list(APPEND proto_python ${PROJECT_BINARY_DIR}/__init__.py)
diff --git a/src/caffe/layers/batch_norm_layer.cpp b/src/caffe/layers/batch_norm_layer.cpp
index 0a08ed4..c6a1d5b 100644
--- a/src/caffe/layers/batch_norm_layer.cpp
+++ b/src/caffe/layers/batch_norm_layer.cpp
@@ -124,8 +124,8 @@ void BatchNormLayer<Dtype>::Forward_cpu(const vector<Blob<Dtype>*>& bottom,
if (!use_global_stats_) {
// compute variance using var(X) = E((X-EX)^2)
- caffe_powx(top[0]->count(), top_data, Dtype(2),
- temp_.mutable_cpu_data()); // (X-EX)^2
+ caffe_sqr<Dtype>(top[0]->count(), top_data,
+ temp_.mutable_cpu_data()); // (X-EX)^2
caffe_cpu_gemv<Dtype>(CblasNoTrans, channels_ * num, spatial_dim,
1. / (num * spatial_dim), temp_.cpu_data(),
spatial_sum_multiplier_.cpu_data(), 0.,
@@ -148,7 +148,7 @@ void BatchNormLayer<Dtype>::Forward_cpu(const vector<Blob<Dtype>*>& bottom,
// normalize variance
caffe_add_scalar(variance_.count(), eps_, variance_.mutable_cpu_data());
- caffe_powx(variance_.count(), variance_.cpu_data(), Dtype(0.5),
+ caffe_sqrt(variance_.count(), variance_.cpu_data(),
variance_.mutable_cpu_data());
// replicate variance to input size
diff --git a/src/caffe/layers/batch_norm_layer.cu b/src/caffe/layers/batch_norm_layer.cu
index c21713c..a35e778 100644
--- a/src/caffe/layers/batch_norm_layer.cu
+++ b/src/caffe/layers/batch_norm_layer.cu
@@ -48,14 +48,14 @@ void BatchNormLayer<Dtype>::Forward_gpu(const vector<Blob<Dtype>*>& bottom,
if (!use_global_stats_) {
// compute variance using var(X) = E((X-EX)^2)
- caffe_gpu_powx(top[0]->count(), top_data, Dtype(2),
+ caffe_gpu_mul(top[0]->count(), top[0]->gpu_data(), top[0]->gpu_data(),
temp_.mutable_gpu_data()); // (X-EX)^2
caffe_gpu_gemv<Dtype>(CblasNoTrans, channels_ * num, spatial_dim,
1. / (num * spatial_dim), temp_.gpu_data(),
spatial_sum_multiplier_.gpu_data(), 0.,
num_by_chans_.mutable_gpu_data());
- caffe_gpu_gemv<Dtype>(CblasTrans, num, channels_, 1.,
- num_by_chans_.gpu_data(), batch_sum_multiplier_.gpu_data(), 0.,
+ caffe_gpu_gemv<Dtype>(CblasTrans, num, channels_, Dtype(1.),
+ num_by_chans_.gpu_data(), batch_sum_multiplier_.gpu_data(), Dtype(0.),
variance_.mutable_gpu_data()); // E((X_EX)^2)
// compute and save moving average
@@ -72,7 +72,7 @@ void BatchNormLayer<Dtype>::Forward_gpu(const vector<Blob<Dtype>*>& bottom,
// normalize variance
caffe_gpu_add_scalar(variance_.count(), eps_, variance_.mutable_gpu_data());
- caffe_gpu_powx(variance_.count(), variance_.gpu_data(), Dtype(0.5),
+ caffe_gpu_sqrt(variance_.count(), variance_.gpu_data(),
variance_.mutable_gpu_data());
// replicate variance to input size
diff --git a/src/caffe/layers/infogain_loss_layer.cpp b/src/caffe/layers/infogain_loss_layer.cpp
index 624d311..3c3f460 100644
--- a/src/caffe/layers/infogain_loss_layer.cpp
+++ b/src/caffe/layers/infogain_loss_layer.cpp
@@ -3,7 +3,8 @@
#include <vector>
#include "caffe/layers/infogain_loss_layer.hpp"
-#include "caffe/util/io.hpp"
+#include "caffe/util/io.hpp" // for bolb reading of matrix H
+#include "caffe/util/math_functions.hpp"
namespace caffe {
@@ -11,6 +12,31 @@ template <typename Dtype>
void InfogainLossLayer<Dtype>::LayerSetUp(
const vector<Blob<Dtype>*>& bottom, const vector<Blob<Dtype>*>& top) {
LossLayer<Dtype>::LayerSetUp(bottom, top);
+ // internal softmax layer
+ LayerParameter softmax_layer_param(this->layer_param_);
+ SoftmaxParameter* softmax_param = softmax_layer_param.mutable_softmax_param();
+ softmax_param->set_axis(this->layer_param_.infogain_loss_param().axis());
+ softmax_layer_param.set_type("Softmax");
+ softmax_layer_param.clear_loss_weight();
+ softmax_layer_param.add_loss_weight(1);
+ softmax_layer_ = LayerRegistry<Dtype>::CreateLayer(softmax_layer_param);
+ softmax_bottom_vec_.clear();
+ softmax_bottom_vec_.push_back(bottom[0]);
+ softmax_top_vec_.clear();
+ softmax_top_vec_.push_back(&prob_);
+ softmax_layer_->SetUp(softmax_bottom_vec_, softmax_top_vec_);
+
+ // ignore label
+ has_ignore_label_ =
+ this->layer_param_.loss_param().has_ignore_label();
+ if (has_ignore_label_) {
+ ignore_label_ = this->layer_param_.loss_param().ignore_label();
+ }
+ // normalization
+ CHECK(!this->layer_param_.loss_param().has_normalize())
+ << "normalize is deprecated. use \"normalization\"";
+ normalization_ = this->layer_param_.loss_param().normalization();
+ // matrix H
if (bottom.size() < 3) {
CHECK(this->layer_param_.infogain_loss_param().has_source())
<< "Infogain matrix source must be specified.";
@@ -25,28 +51,86 @@ template <typename Dtype>
void InfogainLossLayer<Dtype>::Reshape(
const vector<Blob<Dtype>*>& bottom, const vector<Blob<Dtype>*>& top) {
LossLayer<Dtype>::Reshape(bottom, top);
+ softmax_layer_->Reshape(softmax_bottom_vec_, softmax_top_vec_);
+ infogain_axis_ =
+ bottom[0]->CanonicalAxisIndex(
+ this->layer_param_.infogain_loss_param().axis());
+ outer_num_ = bottom[0]->count(0, infogain_axis_);
+ inner_num_ = bottom[0]->count(infogain_axis_ + 1);
+ CHECK_EQ(outer_num_ * inner_num_, bottom[1]->count())
+ << "Number of labels must match number of predictions; "
+ << "e.g., if infogain axis == 1 and prediction shape is (N, C, H, W), "
+ << "label count (number of labels) must be N*H*W, "
+ << "with integer values in {0, 1, ..., C-1}.";
+ num_labels_ = bottom[0]->shape(infogain_axis_);
Blob<Dtype>* infogain = NULL;
if (bottom.size() < 3) {
infogain = &infogain_;
} else {
infogain = bottom[2];
}
- CHECK_EQ(bottom[1]->channels(), 1);
- CHECK_EQ(bottom[1]->height(), 1);
- CHECK_EQ(bottom[1]->width(), 1);
- const int num = bottom[0]->num();
- const int dim = bottom[0]->count() / num;
- CHECK_EQ(infogain->num(), 1);
- CHECK_EQ(infogain->channels(), 1);
- CHECK_EQ(infogain->height(), dim);
- CHECK_EQ(infogain->width(), dim);
+ CHECK_EQ(infogain->count(), num_labels_*num_labels_);
+ sum_rows_H_.Reshape(vector<int>(1, num_labels_));
+ if (bottom.size() == 2) {
+ // H is provided as a parameter and will not change. sum rows once
+ sum_rows_of_H(infogain);
+ }
+ if (top.size() >= 2) {
+ // softmax output
+ top[1]->ReshapeLike(*bottom[0]);
+ }
+}
+
+template <typename Dtype>
+Dtype InfogainLossLayer<Dtype>::get_normalizer(
+ LossParameter_NormalizationMode normalization_mode, int valid_count) {
+ Dtype normalizer;
+ switch (normalization_mode) {
+ case LossParameter_NormalizationMode_FULL:
+ normalizer = Dtype(outer_num_ * inner_num_);
+ break;
+ case LossParameter_NormalizationMode_VALID:
+ if (valid_count == -1) {
+ normalizer = Dtype(outer_num_ * inner_num_);
+ } else {
+ normalizer = Dtype(valid_count);
+ }
+ break;
+ case LossParameter_NormalizationMode_BATCH_SIZE:
+ normalizer = Dtype(outer_num_);
+ break;
+ case LossParameter_NormalizationMode_NONE:
+ normalizer = Dtype(1);
+ break;
+ default:
+ LOG(FATAL) << "Unknown normalization mode: "
+ << LossParameter_NormalizationMode_Name(normalization_mode);
+ }
+ // Some users will have no labels for some examples in order to 'turn off' a
+ // particular loss in a multi-task setup. The max prevents NaNs in that case.
+ return std::max(Dtype(1.0), normalizer);
}
+template <typename Dtype>
+void InfogainLossLayer<Dtype>::sum_rows_of_H(const Blob<Dtype>* H) {
+ CHECK_EQ(H->count(), num_labels_*num_labels_)
+ << "H must be " << num_labels_ << "x" << num_labels_;
+ const Dtype* infogain_mat = H->cpu_data();
+ Dtype* sum = sum_rows_H_.mutable_cpu_data();
+ for ( int row = 0; row < num_labels_ ; row++ ) {
+ sum[row] = 0;
+ for ( int col = 0; col < num_labels_ ; col++ ) {
+ sum[row] += infogain_mat[row*num_labels_+col];
+ }
+ }
+}
template <typename Dtype>
void InfogainLossLayer<Dtype>::Forward_cpu(const vector<Blob<Dtype>*>& bottom,
const vector<Blob<Dtype>*>& top) {
- const Dtype* bottom_data = bottom[0]->cpu_data();
+ // The forward pass computes the softmax prob values.
+ softmax_layer_->Forward(softmax_bottom_vec_, softmax_top_vec_);
+ const Dtype* prob_data = prob_.cpu_data();
const Dtype* bottom_label = bottom[1]->cpu_data();
const Dtype* infogain_mat = NULL;
if (bottom.size() < 3) {
@@ -54,17 +138,30 @@ void InfogainLossLayer<Dtype>::Forward_cpu(const vector<Blob<Dtype>*>& bottom,
} else {
infogain_mat = bottom[2]->cpu_data();
}
- int num = bottom[0]->num();
- int dim = bottom[0]->count() / bottom[0]->num();
+ int count = 0;
Dtype loss = 0;
- for (int i = 0; i < num; ++i) {
- int label = static_cast<int>(bottom_label[i]);
- for (int j = 0; j < dim; ++j) {
- Dtype prob = std::max(bottom_data[i * dim + j], Dtype(kLOG_THRESHOLD));
- loss -= infogain_mat[label * dim + j] * log(prob);
+ for (int i = 0; i < outer_num_; ++i) {
+ for (int j = 0; j < inner_num_; j++) {
+ const int label_value =
+ static_cast<int>(bottom_label[i * inner_num_ + j]);
+ if (has_ignore_label_ && label_value == ignore_label_) {
+ continue;
+ }
+ DCHECK_GE(label_value, 0);
+ DCHECK_LT(label_value, num_labels_);
+ for (int l = 0; l < num_labels_; l++) {
+ loss -= infogain_mat[label_value * num_labels_ + l] *
+ log(std::max(
+ prob_data[i * inner_num_*num_labels_ + l * inner_num_ + j],
+ Dtype(kLOG_THRESHOLD)));
+ }
+ ++count;
}
}
- top[0]->mutable_cpu_data()[0] = loss / num;
+ top[0]->mutable_cpu_data()[0] = loss / get_normalizer(normalization_, count);
+ if (top.size() == 2) {
+ top[1]->ShareData(prob_);
+ }
}
template <typename Dtype>
@@ -80,25 +177,44 @@ void InfogainLossLayer<Dtype>::Backward_cpu(const vector<Blob<Dtype>*>& top,
<< " Layer cannot backpropagate to infogain inputs.";
}
if (propagate_down[0]) {
- const Dtype* bottom_data = bottom[0]->cpu_data();
+ const Dtype* prob_data = prob_.cpu_data();
const Dtype* bottom_label = bottom[1]->cpu_data();
const Dtype* infogain_mat = NULL;
if (bottom.size() < 3) {
infogain_mat = infogain_.cpu_data();
} else {
infogain_mat = bottom[2]->cpu_data();
+ // H is provided as a "bottom" and might change. sum rows every time.
+ sum_rows_of_H(bottom[2]);
}
+ const Dtype* sum_rows_H = sum_rows_H_.cpu_data();
Dtype* bottom_diff = bottom[0]->mutable_cpu_diff();
- int num = bottom[0]->num();
- int dim = bottom[0]->count() / bottom[0]->num();
- const Dtype scale = - top[0]->cpu_diff()[0] / num;
- for (int i = 0; i < num; ++i) {
- const int label = static_cast<int>(bottom_label[i]);
- for (int j = 0; j < dim; ++j) {
- Dtype prob = std::max(bottom_data[i * dim + j], Dtype(kLOG_THRESHOLD));
- bottom_diff[i * dim + j] = scale * infogain_mat[label * dim + j] / prob;
+ const int dim = bottom[0]->count() / outer_num_;
+ int count = 0;
+ for (int i = 0; i < outer_num_; ++i) {
+ for (int j = 0; j < inner_num_; ++j) {
+ const int label_value =
+ static_cast<int>(bottom_label[i * inner_num_ + j]);
+ DCHECK_GE(label_value, 0);
+ DCHECK_LT(label_value, num_labels_);
+ if (has_ignore_label_ && label_value == ignore_label_) {
+ for (int l = 0; l < num_labels_; ++l) {
+ bottom_diff[i * dim + l * inner_num_ + j] = 0;
+ }
+ } else {
+ for (int l = 0; l < num_labels_; ++l) {
+ bottom_diff[i * dim + l * inner_num_ + j] =
+ prob_data[i*dim + l*inner_num_ + j]*sum_rows_H[label_value]
+ - infogain_mat[label_value * num_labels_ + l];
+ }
+ ++count;
+ }
}
}
+ // Scale gradient
+ Dtype loss_weight = top[0]->cpu_diff()[0] /
+ get_normalizer(normalization_, count);
+ caffe_scal(bottom[0]->count(), loss_weight, bottom_diff);
}
}
diff --git a/src/caffe/layers/lstm_unit_layer.cpp b/src/caffe/layers/lstm_unit_layer.cpp
index 277c031..d1ab59c 100644
--- a/src/caffe/layers/lstm_unit_layer.cpp
+++ b/src/caffe/layers/lstm_unit_layer.cpp
@@ -31,7 +31,6 @@ void LSTMUnitLayer<Dtype>::Reshape(const vector<Blob<Dtype>*>& bottom,
CHECK_EQ(num_instances, bottom[i]->shape(1));
}
hidden_dim_ = bottom[0]->shape(2);
- CHECK_EQ(num_instances, bottom[1]->shape(1));
CHECK_EQ(4 * hidden_dim_, bottom[1]->shape(2));
top[0]->ReshapeLike(*bottom[0]);
top[1]->ReshapeLike(*bottom[0]);
diff --git a/src/caffe/layers/pooling_layer.cu b/src/caffe/layers/pooling_layer.cu
index 1ea46cc..46eddb9 100644
--- a/src/caffe/layers/pooling_layer.cu
+++ b/src/caffe/layers/pooling_layer.cu
@@ -138,7 +138,7 @@ __global__ void StoPoolForwardTest(const int nthreads,
const int wstart = pw * stride_w;
const int wend = min(wstart + kernel_w, width);
// We set cumsum to be 0 to avoid divide-by-zero problems
- Dtype cumsum = FLT_MIN;
+ Dtype cumsum = 0.;
Dtype cumvalues = 0.;
const Dtype* const bottom_slice =
bottom_data + (n * channels + c) * height * width;
@@ -149,7 +149,7 @@ __global__ void StoPoolForwardTest(const int nthreads,
cumvalues += bottom_slice[h * width + w] * bottom_slice[h * width + w];
}
}
- top_data[index] = cumvalues / cumsum;
+ top_data[index] = (cumsum > 0.) ? cumvalues / cumsum : 0.;
}
}
diff --git a/src/caffe/layers/sigmoid_layer.cpp b/src/caffe/layers/sigmoid_layer.cpp
index 85fd967..f8aa769 100644
--- a/src/caffe/layers/sigmoid_layer.cpp
+++ b/src/caffe/layers/sigmoid_layer.cpp
@@ -7,7 +7,7 @@ namespace caffe {
template <typename Dtype>
inline Dtype sigmoid(Dtype x) {
- return 1. / (1. + exp(-x));
+ return 0.5 * tanh(0.5 * x) + 0.5;
}
template <typename Dtype>
diff --git a/src/caffe/layers/sigmoid_layer.cu b/src/caffe/layers/sigmoid_layer.cu
index 184c61e..8a4ea66 100644
--- a/src/caffe/layers/sigmoid_layer.cu
+++ b/src/caffe/layers/sigmoid_layer.cu
@@ -8,7 +8,7 @@ namespace caffe {
template <typename Dtype>
__global__ void SigmoidForward(const int n, const Dtype* in, Dtype* out) {
CUDA_KERNEL_LOOP(index, n) {
- out[index] = 1. / (1. + exp(-in[index]));
+ out[index] = 0.5 * tanh(0.5 * in[index]) + 0.5;
}
}
diff --git a/src/caffe/proto/caffe.proto b/src/caffe/proto/caffe.proto
index 8e528e8..c96966b 100644
--- a/src/caffe/proto/caffe.proto
+++ b/src/caffe/proto/caffe.proto
@@ -815,6 +815,7 @@ message ImageDataParameter {
message InfogainLossParameter {
// Specify the infogain matrix source.
optional string source = 1;
+ optional int32 axis = 2 [default = 1]; // axis of prob
}
message InnerProductParameter {
diff --git a/src/caffe/test/test_convolution_layer.cpp b/src/caffe/test/test_convolution_layer.cpp
index 9bb19d1..85c10a2 100644
--- a/src/caffe/test/test_convolution_layer.cpp
+++ b/src/caffe/test/test_convolution_layer.cpp
@@ -695,7 +695,7 @@ TYPED_TEST(ConvolutionLayerTest, TestNDAgainst2D) {
}
ASSERT_EQ(backward_result_nd.count(), backward_result_2d.count());
for (int i = 0; i < backward_result_2d.count(); ++i) {
- EXPECT_EQ(backward_result_2d.cpu_diff()[i],
+ EXPECT_FLOAT_EQ(backward_result_2d.cpu_diff()[i],
backward_result_nd.cpu_diff()[i]);
}
ASSERT_EQ(backward_weight_result_nd.count(),
diff --git a/src/caffe/test/test_gradient_based_solver.cpp b/src/caffe/test/test_gradient_based_solver.cpp
index 465140f..f4395f5 100644
--- a/src/caffe/test/test_gradient_based_solver.cpp
+++ b/src/caffe/test/test_gradient_based_solver.cpp
@@ -558,9 +558,11 @@ class GradientBasedSolverTest : public MultiDeviceTest<TypeParam> {
const vector<Blob<Dtype>*>& params = solver_->net()->learnable_params();
for (int i = 0; i < params.size(); ++i) {
for (int j = 0; j < params[i]->count(); ++j) {
- EXPECT_EQ(param_copies[i]->cpu_data()[j], params[i]->cpu_data()[j])
+ EXPECT_FLOAT_EQ(param_copies[i]->cpu_data()[j],
+ params[i]->cpu_data()[j])
<< "param " << i << " data differed at dim " << j;
- EXPECT_EQ(param_copies[i]->cpu_diff()[j], params[i]->cpu_diff()[j])
+ EXPECT_FLOAT_EQ(param_copies[i]->cpu_diff()[j],
+ params[i]->cpu_diff()[j])
<< "param " << i << " diff differed at dim " << j;
}
}
@@ -569,9 +571,11 @@ class GradientBasedSolverTest : public MultiDeviceTest<TypeParam> {
const vector<shared_ptr<Blob<Dtype> > >& history = solver_->history();
for (int i = 0; i < history.size(); ++i) {
for (int j = 0; j < history[i]->count(); ++j) {
- EXPECT_EQ(history_copies[i]->cpu_data()[j], history[i]->cpu_data()[j])
+ EXPECT_FLOAT_EQ(history_copies[i]->cpu_data()[j],
+ history[i]->cpu_data()[j])
<< "history blob " << i << " data differed at dim " << j;
- EXPECT_EQ(history_copies[i]->cpu_diff()[j], history[i]->cpu_diff()[j])
+ EXPECT_FLOAT_EQ(history_copies[i]->cpu_diff()[j],
+ history[i]->cpu_diff()[j])
<< "history blob " << i << " diff differed at dim " << j;
}
}
diff --git a/src/caffe/test/test_infogain_loss_layer.cpp b/src/caffe/test/test_infogain_loss_layer.cpp
index a24ac68..34f2127 100644
--- a/src/caffe/test/test_infogain_loss_layer.cpp
+++ b/src/caffe/test/test_infogain_loss_layer.cpp
@@ -1,3 +1,4 @@
+#include <algorithm>
#include <vector>
#include "gtest/gtest.h"
@@ -18,17 +19,22 @@ class InfogainLossLayerTest : public MultiDeviceTest<TypeParam> {
protected:
InfogainLossLayerTest()
- : blob_bottom_data_(new Blob<Dtype>(10, 5, 1, 1)),
- blob_bottom_label_(new Blob<Dtype>(10, 1, 1, 1)),
+ : blob_bottom_data_(new Blob<Dtype>(4, 2, 5, 2)),
+ blob_bottom_label_(new Blob<Dtype>(4, 2, 1, 2)),
blob_bottom_infogain_(new Blob<Dtype>(1, 1, 5, 5)),
- blob_top_loss_(new Blob<Dtype>()) {
+ blob_top_loss_(new Blob<Dtype>()),
+ blob_top_prob_(new Blob<Dtype>()),
+ inner_(2), outer_(4*2), num_labels_(5) {
Caffe::set_random_seed(1701);
FillerParameter filler_param;
- PositiveUnitballFiller<Dtype> filler(filler_param);
+ filler_param.set_min(-0.5);
+ filler_param.set_max(2.0);
+ UniformFiller<Dtype> filler(filler_param);
filler.Fill(this->blob_bottom_data_);
blob_bottom_vec_.push_back(blob_bottom_data_);
for (int i = 0; i < blob_bottom_label_->count(); ++i) {
- blob_bottom_label_->mutable_cpu_data()[i] = caffe_rng_rand() % 5;
+ blob_bottom_label_->mutable_cpu_data()[i] =
+ caffe_rng_rand() % num_labels_;
}
blob_bottom_vec_.push_back(blob_bottom_label_);
filler_param.set_min(0.1);
@@ -37,29 +43,94 @@ class InfogainLossLayerTest : public MultiDeviceTest<TypeParam> {
infogain_filler.Fill(this->blob_bottom_infogain_);
blob_bottom_vec_.push_back(blob_bottom_infogain_);
blob_top_vec_.push_back(blob_top_loss_);
+ blob_top_vec_.push_back(blob_top_prob_);
}
virtual ~InfogainLossLayerTest() {
delete blob_bottom_data_;
delete blob_bottom_label_;
delete blob_bottom_infogain_;
delete blob_top_loss_;
+ delete blob_top_prob_;
}
Blob<Dtype>* const blob_bottom_data_;
Blob<Dtype>* const blob_bottom_label_;
Blob<Dtype>* const blob_bottom_infogain_;
Blob<Dtype>* const blob_top_loss_;
+ Blob<Dtype>* const blob_top_prob_;
vector<Blob<Dtype>*> blob_bottom_vec_;
vector<Blob<Dtype>*> blob_top_vec_;
+ int inner_, outer_, num_labels_;
};
TYPED_TEST_CASE(InfogainLossLayerTest, TestDtypesAndDevices);
+TYPED_TEST(InfogainLossLayerTest, TestInfogainLoss) {
+ typedef typename TypeParam::Dtype Dtype;
+ LayerParameter layer_param;
+ layer_param.mutable_infogain_loss_param()->set_axis(2);
+ layer_param.clear_loss_weight();
+ layer_param.add_loss_weight(1);
+ layer_param.add_loss_weight(0);
+ /*vector<float>* lw = layer_param.mutable_loss_weight();
+ lw->clear();
+ lw->push_back(1);
+ lw->push_back(1);*/
+ InfogainLossLayer<Dtype> layer(layer_param);
+ layer.SetUp(this->blob_bottom_vec_, this->blob_top_vec_);
+ layer.Forward(this->blob_bottom_vec_, this->blob_top_vec_);
+ // Now, check values
+ const Dtype* data = this->blob_bottom_vec_[0]->cpu_data();
+ const Dtype* prob = this->blob_top_vec_[1]->cpu_data();
+ const Dtype* labels = this->blob_bottom_vec_[1]->cpu_data();
+ const Dtype* H = this->blob_bottom_vec_[2]->cpu_data();
+ // first. test the prob top
+ CHECK_EQ(this->blob_bottom_vec_[0]->num_axes(),
+ this->blob_top_vec_[1]->num_axes())
+ << "prob top shape not match bottom data";
+ for (int ai = 0 ; ai < this->blob_bottom_vec_[0]->num_axes(); ai++) {
+ CHECK_EQ(this->blob_bottom_vec_[0]->shape(ai),
+ this->blob_top_vec_[1]->shape(ai))
+ << "prob top shape not match bottom data";
+ }
+ vector<Dtype> est_prob(this->num_labels_, 0);
+ for ( int i = 0 ; i < this->outer_; i++ ) {
+ for ( int j = 0; j < this->inner_; j++ ) {
+ Dtype den = 0;
+ for ( int l = 0; l < this->num_labels_; l++ ) {
+ est_prob[l] = std::exp(
+ data[i*this->num_labels_*this->inner_ + l*this->inner_ + j]);
+ den += est_prob[l];
+ }
+ for ( int l = 0; l < this->num_labels_; l++ ) {
+ EXPECT_NEAR(prob[i*this->num_labels_*this->inner_ + l*this->inner_ + j],
+ est_prob[l]/den, 1e-6);
+ }
+ }
+ }
+ Dtype loss = 0; // loss from prob top
+ for ( int i = 0 ; i < this->outer_; i++ ) {
+ for ( int j = 0; j < this->inner_; j++ ) {
+ int gt = static_cast<int>(labels[i*this->inner_+j]);
+ for ( int l = 0; l < this->num_labels_; l++ ) {
+ loss -= H[gt*this->num_labels_ + l] *
+ log(std::max(
+ prob[i*this->num_labels_*this->inner_ + l*this->inner_ + j],
+ Dtype(kLOG_THRESHOLD)));
+ }
+ }
+ }
+ EXPECT_NEAR(this->blob_top_loss_->cpu_data()[0],
+ loss/(this->outer_*this->inner_), 1e-6);
+}
TYPED_TEST(InfogainLossLayerTest, TestGradient) {
typedef typename TypeParam::Dtype Dtype;
LayerParameter layer_param;
+ layer_param.mutable_infogain_loss_param()->set_axis(2);
InfogainLossLayer<Dtype> layer(layer_param);
- GradientChecker<Dtype> checker(1e-4, 2e-2, 1701, 1, 0.01);
+ this->blob_top_vec_.clear(); // ignore prob top.
+ this->blob_top_vec_.push_back(this->blob_top_loss_);
+ GradientChecker<Dtype> checker(1e-4, 2e-2, 1701); // no "kink"
checker.CheckGradientExhaustive(&layer, this->blob_bottom_vec_,
this->blob_top_vec_, 0);
}
diff --git a/src/caffe/test/test_neuron_layer.cpp b/src/caffe/test/test_neuron_layer.cpp
index 342f825..180871a 100644
--- a/src/caffe/test/test_neuron_layer.cpp
+++ b/src/caffe/test/test_neuron_layer.cpp
@@ -791,16 +791,19 @@ TYPED_TEST(NeuronLayerTest, TestPReLUInPlace) {
ip2.Backward(blob_middle_vec_2, propagate_down, blob_bottom_vec_2);
// Check numbers
for (int s = 0; s < blob_bottom_2->count(); ++s) {
- EXPECT_EQ(this->blob_bottom_->cpu_diff()[s], blob_bottom_2->cpu_diff()[s]);
+ EXPECT_FLOAT_EQ(this->blob_bottom_->cpu_diff()[s],
+ blob_bottom_2->cpu_diff()[s]);
}
for (int s = 0; s < ip.blobs()[0]->count(); ++s) {
- EXPECT_EQ(ip.blobs()[0]->cpu_diff()[s], ip2.blobs()[0]->cpu_diff()[s]);
+ EXPECT_FLOAT_EQ(ip.blobs()[0]->cpu_diff()[s],
+ ip2.blobs()[0]->cpu_diff()[s]);
}
for (int s = 0; s < ip.blobs()[1]->count(); ++s) {
- EXPECT_EQ(ip.blobs()[1]->cpu_diff()[s], ip2.blobs()[1]->cpu_diff()[s]);
+ EXPECT_FLOAT_EQ(ip.blobs()[1]->cpu_diff()[s],
+ ip2.blobs()[1]->cpu_diff()[s]);
}
for (int s = 0; s < prelu.blobs()[0]->count(); ++s) {
- EXPECT_EQ(prelu.blobs()[0]->cpu_diff()[s],
+ EXPECT_FLOAT_EQ(prelu.blobs()[0]->cpu_diff()[s],
prelu2.blobs()[0]->cpu_diff()[s]);
}
}
diff --git a/src/caffe/util/math_functions.cpp b/src/caffe/util/math_functions.cpp
index 71c0227..59625bc 100644
--- a/src/caffe/util/math_functions.cpp
+++ b/src/caffe/util/math_functions.cpp
@@ -197,6 +197,16 @@ void caffe_sqr<double>(const int n, const double* a, double* y) {
}
template <>
+void caffe_sqrt<float>(const int n, const float* a, float* y) {
+ vsSqrt(n, a, y);
+}
+
+template <>
+void caffe_sqrt<double>(const int n, const double* a, double* y) {
+ vdSqrt(n, a, y);
+}
+
+template <>
void caffe_exp<float>(const int n, const float* a, float* y) {
vsExp(n, a, y);
}
diff --git a/src/caffe/util/math_functions.cu b/src/caffe/util/math_functions.cu
index 6d00102..314e6ba 100644
--- a/src/caffe/util/math_functions.cu
+++ b/src/caffe/util/math_functions.cu
@@ -387,6 +387,27 @@ void caffe_gpu_powx<double>(const int N, const double* a,
N, a, alpha, y);
}
+template <typename Dtype>
+__global__ void sqrt_kernel(const int n, const Dtype* a, Dtype* y) {
+ CUDA_KERNEL_LOOP(index, n) {
+ y[index] = sqrt(a[index]);
+ }
+}
+
+template <>
+void caffe_gpu_sqrt<float>(const int N, const float* a, float* y) {
+ // NOLINT_NEXT_LINE(whitespace/operators)
+ sqrt_kernel<float><<<CAFFE_GET_BLOCKS(N), CAFFE_CUDA_NUM_THREADS>>>(
+ N, a, y);
+}
+
+template <>
+void caffe_gpu_sqrt<double>(const int N, const double* a, double* y) {
+ // NOLINT_NEXT_LINE(whitespace/operators)
+ sqrt_kernel<double><<<CAFFE_GET_BLOCKS(N), CAFFE_CUDA_NUM_THREADS>>>(
+ N, a, y);
+}
+
DEFINE_AND_INSTANTIATE_GPU_UNARY_FUNC(sign, y[index] = (Dtype(0) < x[index])
- (x[index] < Dtype(0)));
DEFINE_AND_INSTANTIATE_GPU_UNARY_FUNC(sgnbit, y[index] = signbit(x[index]));
diff --git a/tools/CMakeLists.txt b/tools/CMakeLists.txt
index 02fbd5c..3789450 100644
--- a/tools/CMakeLists.txt
+++ b/tools/CMakeLists.txt
@@ -25,5 +25,6 @@ foreach(source ${srcs})
endif()
# Install
- install(TARGETS ${name} DESTINATION bin)
+ install(TARGETS ${name} DESTINATION ${CMAKE_INSTALL_BINDIR})
+
endforeach(source)
diff --git a/tools/compute_image_mean.cpp b/tools/compute_image_mean.cpp
index 2035d51..417f5e4 100644
--- a/tools/compute_image_mean.cpp
+++ b/tools/compute_image_mean.cpp
@@ -22,9 +22,11 @@ DEFINE_string(backend, "lmdb",
"The backend {leveldb, lmdb} containing the images");
int main(int argc, char** argv) {
+#ifdef USE_OPENCV
::google::InitGoogleLogging(argv[0]);
+ // Print output to stderr (while still logging)
+ FLAGS_alsologtostderr = 1;
-#ifdef USE_OPENCV
#ifndef GFLAGS_GFLAGS_H_
namespace gflags = google;
#endif
@@ -65,7 +67,7 @@ int main(int argc, char** argv) {
for (int i = 0; i < size_in_datum; ++i) {
sum_blob.add_data(0.);
}
- LOG(INFO) << "Starting Iteration";
+ LOG(INFO) << "Starting iteration";
while (cursor->valid()) {
Datum datum;
datum.ParseFromString(cursor->value());
@@ -114,7 +116,7 @@ int main(int argc, char** argv) {
for (int i = 0; i < dim; ++i) {
mean_values[c] += sum_blob.data(dim * c + i);
}
- LOG(INFO) << "mean_value channel [" << c << "]:" << mean_values[c] / dim;
+ LOG(INFO) << "mean_value channel [" << c << "]: " << mean_values[c] / dim;
}
#else
LOG(FATAL) << "This tool requires OpenCV; compile with USE_OPENCV.";
diff --git a/tools/extra/parse_log.sh b/tools/extra/parse_log.sh
index 9892c89..122eb9e 100755
--- a/tools/extra/parse_log.sh
+++ b/tools/extra/parse_log.sh
@@ -39,7 +39,7 @@ rm aux.txt aux0.txt aux1.txt aux2.txt aux3.txt aux4.txt
grep '] Solving ' $1 > aux.txt
grep ', loss = ' $1 >> aux.txt
grep 'Iteration ' aux.txt | sed 's/.*Iteration \([[:digit:]]*\).*/\1/g' > aux0.txt
-grep ', loss = ' $1 | awk '{print $9}' > aux1.txt
+grep ', loss = ' $1 | awk -F = '{print $2}' > aux1.txt
grep ', lr = ' $1 | awk '{print $9}' > aux2.txt
# Extracting elapsed seconds
diff --git a/tools/extra/resize_and_crop_images.py b/tools/extra/resize_and_crop_images.py
index c844f59..fd2c313 100755
--- a/tools/extra/resize_and_crop_images.py
+++ b/tools/extra/resize_and_crop_images.py
@@ -101,7 +101,7 @@ class ResizeCropImagesMapper(mapreducer.BasicMapper):
yield value, FLAGS.output_folder
mapreducer.REGISTER_DEFAULT_MAPPER(ResizeCropImagesMapper)
-
+mapreducer.REGISTER_DEFAULT_REDUCER(mapreducer.NoPassReducer)
mapreducer.REGISTER_DEFAULT_READER(mapreducer.FileReader)
mapreducer.REGISTER_DEFAULT_WRITER(mapreducer.FileWriter)