Skip to content

Commit

Permalink
Migrate to Python 3, make V1 compatible.
Browse files Browse the repository at this point in the history
  • Loading branch information
keunhong committed Jan 19, 2017
1 parent fd54fb2 commit 4068ea3
Show file tree
Hide file tree
Showing 8 changed files with 2,399 additions and 496 deletions.
2 changes: 1 addition & 1 deletion convert.py
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ def convert(def_path, caffemodel_path, data_output_path, code_output_path, phase
np.save(data_out, data)
if code_output_path:
print_stderr('Saving source...')
with open(code_output_path, 'wb') as src_out:
with open(code_output_path, 'w') as src_out:
src_out.write(transformer.transform_source())
print_stderr('Done.')
except KaffeError as err:
Expand Down
1,404 changes: 1,404 additions & 0 deletions kaffe/caffe/caffe.proto

Large diffs are not rendered by default.

1,401 changes: 931 additions & 470 deletions kaffe/caffe/caffepb.py

Large diffs are not rendered by default.

17 changes: 4 additions & 13 deletions kaffe/caffe/resolver.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,19 +8,10 @@ def __init__(self):

def import_caffe(self):
self.caffe = None
try:
# Try to import PyCaffe first
import caffe
self.caffe = caffe
except ImportError:
# Fall back to the protobuf implementation
from . import caffepb
self.caffepb = caffepb
show_fallback_warning()
if self.caffe:
# Use the protobuf code from the imported distribution.
# This way, Caffe variants with custom layers will work.
self.caffepb = self.caffe.proto.caffe_pb2
# Fall back to the protobuf implementation
from . import caffepb
self.caffepb = caffepb
show_fallback_warning()
self.NetParameter = self.caffepb.NetParameter

def has_pycaffe(self):
Expand Down
2 changes: 1 addition & 1 deletion kaffe/core.py
Original file line number Diff line number Diff line change
Expand Up @@ -278,7 +278,7 @@ def filter_layers(self, layers):
return filtered_layers

def make_node(self, layer):
kind = NodeKind.map_raw_kind(layer.type)
kind = NodeKind.map_raw_kind(layer)
if kind is None:
raise KaffeError('Unknown layer type encountered: %s'%layer.type)
return Node(layer.name, kind, layer=layer)
Expand Down
17 changes: 9 additions & 8 deletions kaffe/graph.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
from google.protobuf import text_format

from .caffe import get_caffe_resolver
from .caffe import get_caffe_resolver, caffepb
from .errors import KaffeError, print_stderr
from .layers import LayerAdapter, LayerType, NodeKind, NodeDispatch
from .shapes import TensorShape
Expand Down Expand Up @@ -114,15 +114,16 @@ def __contains__(self, key):
return key in self.node_lut

def __str__(self):
hdr = '{:<20} {:<30} {:>20} {:>20}'.format('Type', 'Name', 'Param', 'Output')
hdr = '{:<20} {:<30} {:>20} {:>20}'.format(
'Type', 'Name', 'Param', 'Output')
s = [hdr, '-' * 94]
for node in self.topologically_sorted():
# If the node has learned parameters, display the first one's shape.
# In case of convolutions, this corresponds to the weights.
data_shape = node.data[0].shape if node.data else '--'
out_shape = node.output_shape or '--'
s.append('{:<20} {:<30} {:>20} {:>20}'.format(node.kind, node.name, data_shape,
tuple(out_shape)))
data_shape = str(node.data[0].shape) if node.data else '--'
out_shape = str(tuple(node.output_shape)) or '--'
s.append('{:<20} {:<30} {:>20} {:>20}'.format(
node.kind, node.name, data_shape, out_shape))
return '\n'.join(s)


Expand All @@ -142,7 +143,7 @@ def __init__(self, def_path, phase='test'):
def load(self):
'''Load the layer definitions from the prototxt.'''
self.params = get_caffe_resolver().NetParameter()
with open(self.def_path, 'rb') as def_file:
with open(self.def_path, 'r') as def_file:
text_format.Merge(def_file.read(), self.params)

def filter_layers(self, layers):
Expand Down Expand Up @@ -171,7 +172,7 @@ def filter_layers(self, layers):

def make_node(self, layer):
'''Create a graph node for the given layer.'''
kind = NodeKind.map_raw_kind(layer.type)
kind = NodeKind.map_raw_kind(layer)
if kind is None:
raise KaffeError('Unknown layer type encountered: %s' % layer.type)
# We want to use the layer's top names (the "output" names), rather than the
Expand Down
48 changes: 47 additions & 1 deletion kaffe/layers.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import re
import numbers
from collections import namedtuple
from .caffe import caffepb

from .shapes import *

Expand Down Expand Up @@ -51,14 +52,59 @@
'Threshold': shape_identity,
}

V1_TO_NEW = {
35: 'AbsVal',
1: 'Accuracy',
30: 'ArgMax',
2: 'BNLL',
3: 'Concat',
37: 'ContrastiveLoss',
4: 'Convolution',
5: 'Data',
39: 'Deconvolution',
6: 'Dropout',
32: 'DummyData',
7: 'EuclideanLoss',
25: 'Eltwise',
38: 'Exp',
8: 'Flatten',
9: 'HDF5Data',
10: 'HDF5Output',
28: 'HingeLoss',
11: 'Im2col',
12: 'ImageData',
13: 'InfogainLoss',
14: 'InnerProduct',
15: 'LRN',
29: 'MemoryData',
16: 'MultinomialLogisticLoss',
34: 'MVN',
17: 'Pooling',
26: 'Power',
18: 'ReLU',
19: 'Sigmoid',
27: 'SigmoidCrossEntropyLoss',
36: 'Silence',
20: 'Softmax',
21: 'SoftmaxLoss',
22: 'Split',
33: 'Slice',
23: 'TanH',
24: 'WindowData',
31: 'Threshold',
}

LAYER_TYPES = list(LAYER_DESCRIPTORS.keys())

LayerType = type('LayerType', (), {t: t for t in LAYER_TYPES})

class NodeKind(LayerType):

@staticmethod
def map_raw_kind(kind):
def map_raw_kind(layer):
kind = layer.type
if isinstance(layer, caffepb.V1LayerParameter):
kind = V1_TO_NEW[layer.type]
if kind in LAYER_TYPES:
return kind
return None
Expand Down
4 changes: 2 additions & 2 deletions kaffe/tensorflow/transformer.py
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ def __init__(self, op, *args, **kwargs):

def format(self, arg):
'''Returns a string representation for the given value.'''
return "'%s'" % arg if isinstance(arg, basestring) else str(arg)
return "'%s'" % arg if isinstance(arg, str) else str(arg)

def pair(self, key, value):
'''Returns key=formatted(value).'''
Expand All @@ -53,7 +53,7 @@ def pair(self, key, value):
def emit(self):
'''Emits the Python source for this node.'''
# Format positional arguments
args = map(self.format, self.args)
args = list(map(self.format, self.args))
# Format any keyword arguments
if self.kwargs:
args += [self.pair(k, v) for k, v in self.kwargs]
Expand Down

0 comments on commit 4068ea3

Please sign in to comment.