| 1605 | } |
| 1606 | |
| 1607 | void ExtractFCParameters(const caffe::LayerParameter& src, XGraph& graph) |
| 1608 | { |
| 1609 | // Map the Caffe layer type to anonymoX layer type |
| 1610 | caffe::InnerProductParameter src_parameter = src.inner_product_param(); |
| 1611 | mapStrStr::const_iterator it_type = CaffeLayerMap.find(src.type()); |
| 1612 | string xlayerType = it_type->second; |
| 1613 | |
| 1614 | // Parse the input/output connections |
| 1615 | checkNumberOfTopAndBottom(src, 1, 1); |
| 1616 | |
| 1617 | // Create new XLayer |
| 1618 | XLayer* dst = new XLayer(src.name(), xlayerType, src.top(0)); |
| 1619 | |
| 1620 | // Get NUM_OF_OUTPUT [MANDATORY] |
| 1621 | if(src_parameter.has_num_output()) |
| 1622 | { |
| 1623 | dst->fc_params->M = src_parameter.num_output(); |
| 1624 | } |
| 1625 | else |
| 1626 | { |
| 1627 | cout << "[EP018] num_output is not mentioned for layer : " << src.name() << endl; |
| 1628 | exit(-1); |
| 1629 | } |
| 1630 | |
| 1631 | // Get HAS_BIAS [DEFAULT = 1] |
| 1632 | dst->fc_params->has_bias = src_parameter.has_bias_term() ? src_parameter.bias_term() : 1; |
| 1633 | |
| 1634 | // TODO : There are other parameters like 'transpose', 'axis' etc. Currently not supported |
| 1635 | |
| 1636 | // Extract Precision Parameters |
| 1637 | bool success = ExtractPrecisionParameters(src, *dst); |
| 1638 | if(!success) |
| 1639 | graph.precMissLayers.push_back(src.name()); |
| 1640 | |
| 1641 | // Finally add the XLayer to graph |
| 1642 | graph.layers[src.name()] = dst; |
| 1643 | |
| 1644 | // ----------------------------- Setup Blobs and Connections ----------------------- // |
| 1645 | |
| 1646 | // Check bottom first. Make sure it is already registered in the Graph.blobs |
| 1647 | map<string, XBlob*>::iterator it = graph.checkIfBlobExists(src.bottom(0), true, false); |
| 1648 | |
| 1649 | // Execution here reached means, bottom blob exists in graph. So update its fields |
| 1650 | XBlob* tmpBottom = it->second; |
| 1651 | dst->bottom.push_back(nameIndex(tmpBottom)); // Add bottom to XLayer.bottom |
| 1652 | dst->bottomShape.push_back(tmpBottom->shape); // Replicate bottom shape in Layer also |
| 1653 | |
| 1654 | tmpBottom->consumers.push_back(dst->name); // Add convolution layer to bottom consumers |
| 1655 | tmpBottom->consumerDim.push_back(tmpBottom->shape); // and consumer uses the full bottom data. |
| 1656 | dst->fc_params->N = flattenTensorDim(tmpBottom->shape).at(3); // XXX : It is a bad location to do this |
| 1657 | |
| 1658 | // Check top. Make sure it is not registered in the Graph.blobs |
| 1659 | it = graph.checkIfBlobExists(src.top(0), true, true); |
| 1660 | |
| 1661 | // Execution reached here means, top blob doesn't exist, so create. |
| 1662 | XBlob* tmpTop = new XBlob(src.top(0)); |
| 1663 | |
| 1664 | dst->top.push_back(nameIndex(tmpTop)); // Add top blob to current layer top list |
no test coverage detected