src/lib/GenericASN1ContentHandler.h
branchv_0
changeset 38 44ee477875ec
parent 35 bf2c546f49d1
child 39 6ef41443211e
equal deleted inserted replaced
37:0845ca3636b6 38:44ee477875ec
    14  * You should have received a copy of the GNU General Public License
    14  * You should have received a copy of the GNU General Public License
    15  * along with this program. If not, see <http://www.gnu.org/licenses/>.
    15  * along with this program. If not, see <http://www.gnu.org/licenses/>.
    16  */
    16  */
    17 #pragma once
    17 #pragma once
    18 
    18 
       
    19 #include <string>
    19 #include <sstream>
    20 #include <sstream>
    20 #include <iomanip>
    21 #include <iomanip>
    21 
    22 
    22 #include "ASN1ContentHandler.h"
    23 #include "ASN1ContentHandler.h"
    23 #include "XMLContentHandler.h"
    24 #include "XMLContentHandler.h"
    33  * Does not need to know anything about the model/schema – works with generic events (nodes).
    34  * Does not need to know anything about the model/schema – works with generic events (nodes).
    34  */
    35  */
    35 class GenericASN1ContentHandler : public ASN1ContentHandler {
    36 class GenericASN1ContentHandler : public ASN1ContentHandler {
    36 private:
    37 private:
    37 	XMLContentHandlerProxy handlers;
    38 	XMLContentHandlerProxy handlers;
       
    39 
       
    40 	std::vector<std::string> getCommonAttributes(const Header& header, std::vector<std::string> attributes = {}) {
       
    41 		std::string tag = std::to_string(header.tag);
       
    42 		std::string tagClass = std::to_string((uint64_t) header.tagClass);
       
    43 		std::string pc = std::to_string((uint8_t) header.pc);
       
    44 
       
    45 		if (header.tagClass == TagClass::Universal) tagClass = "universal";
       
    46 		else if (header.tagClass == TagClass::ContextSpecific) tagClass = "context";
       
    47 		else if (header.tagClass == TagClass::Application) tagClass = "application";
       
    48 		else if (header.tagClass == TagClass::Private) tagClass = "private";
       
    49 
       
    50 		// if (header.pc == PC::Constructed) pc = "constructed";
       
    51 		// else if (header.pc == PC::Primitive) pc = "primitive";
       
    52 
       
    53 		attributes.push_back("tag");
       
    54 		attributes.push_back(tag);
       
    55 		// attributes.push_back("pc");
       
    56 		// attributes.push_back(pc);
       
    57 		attributes.push_back("class");
       
    58 		attributes.push_back(tagClass);
       
    59 
       
    60 		return attributes;
       
    61 	}
       
    62 
    38 public:
    63 public:
    39 
    64 
    40 	void addHandler(std::shared_ptr<XMLContentHandler> handler) {
    65 	void addHandler(std::shared_ptr<XMLContentHandler> handler) {
    41 		handlers.addHandler(handler);
    66 		handlers.addHandler(handler);
    42 	}
    67 	}
    51 	void writeStreamEnd() override {
    76 	void writeStreamEnd() override {
    52 		handlers.writeEndElement();
    77 		handlers.writeEndElement();
    53 	}
    78 	}
    54 
    79 
    55 	void writeCollectionStart(const Header& header) override {
    80 	void writeCollectionStart(const Header& header) override {
    56 		if (header.tag == UniversalType::Sequence) handlers.writeStartElement("sequence");
    81 		if (header.tag == UniversalType::Sequence) handlers.writeStartElement("sequence", getCommonAttributes(header));
    57 		else if (header.tag == UniversalType::Set) handlers.writeStartElement("set");
    82 		else if (header.tag == UniversalType::Set) handlers.writeStartElement("set", getCommonAttributes(header));
    58 		else if (header.tag == UniversalType::OctetString || header.tag == UniversalType::BitString) handlers.writeStartElement("encapsulated",{"type", std::to_string(header.tag)}); // TODO: type name, better attributes
    83 		else if (header.tag == UniversalType::OctetString || header.tag == UniversalType::BitString) handlers.writeStartElement("encapsulated", getCommonAttributes(header));
    59 		else handlers.writeStartElement("constructed");
    84 		else handlers.writeStartElement("constructed", getCommonAttributes(header));
    60 	}
    85 	}
    61 
    86 
    62 	void writeCollectionEnd() override {
    87 	void writeCollectionEnd() override {
    63 		handlers.writeEndElement();
    88 		handlers.writeEndElement();
    64 	}
    89 	}
    65 
    90 
    66 	void writeBoolean(const Header& header, bool value) override {
    91 	void writeBoolean(const Header& header, bool value) override {
    67 		handlers.writeStartElement("boolean");
    92 		handlers.writeStartElement("boolean", getCommonAttributes(header));
    68 		handlers.writeCharacters(value ? "true" : "false");
    93 		handlers.writeCharacters(value ? "true" : "false");
    69 		handlers.writeEndElement();
    94 		handlers.writeEndElement();
    70 	}
    95 	}
    71 
    96 
    72 	void writeNull(const Header& header) override {
    97 	void writeNull(const Header& header) override {
    73 		handlers.writeStartElement("null");
    98 		handlers.writeStartElement("null", getCommonAttributes(header));
    74 		handlers.writeEndElement();
    99 		handlers.writeEndElement();
    75 	}
   100 	}
    76 
   101 
    77 	void writeInteger(const Header& header, Integer value) override {
   102 	void writeInteger(const Header& header, Integer value) override {
    78 		handlers.writeStartElement("integer",{"hex", value.toHex()});
   103 		handlers.writeStartElement("integer", getCommonAttributes(header,{"hex", value.toHex()}));
    79 		handlers.writeCharacters(value.toString());
   104 		handlers.writeCharacters(value.toString());
    80 		handlers.writeEndElement();
   105 		handlers.writeEndElement();
    81 	}
   106 	}
    82 
   107 
    83 	void writeTextString(const Header& header, std::string value) override {
   108 	void writeTextString(const Header& header, std::string value) override {
    84 		handlers.writeStartElement("text-string",{"type", std::to_string(header.tag)}); // TODO: type name, better attributes
   109 		handlers.writeStartElement("text-string", getCommonAttributes(header));
    85 		handlers.writeCharacters(value);
   110 		handlers.writeCharacters(value);
    86 		handlers.writeEndElement();
   111 		handlers.writeEndElement();
    87 	}
   112 	}
    88 
   113 
    89 	void writeOctetString(const Header& header, std::string value) override {
   114 	void writeOctetString(const Header& header, std::string value) override {
    90 		std::stringstream hex;
   115 		std::stringstream hex;
    91 		hex << std::hex << std::setfill('0');
   116 		hex << std::hex << std::setfill('0');
    92 		for (uint8_t b : value) hex << std::setw(2) << (int) b;
   117 		for (uint8_t b : value) hex << std::setw(2) << (int) b;
    93 		handlers.writeStartElement("octet-string",{"length", std::to_string(value.size())});
   118 		handlers.writeStartElement("octet-string", getCommonAttributes(header,{"length", std::to_string(value.size())}));
    94 		handlers.writeCharacters(hex.str());
   119 		handlers.writeCharacters(hex.str());
    95 		handlers.writeEndElement();
   120 		handlers.writeEndElement();
    96 	}
   121 	}
    97 
   122 
    98 	void writeBitString(const Header& header, std::vector<bool> value) override {
   123 	void writeBitString(const Header& header, std::vector<bool> value) override {
    99 		std::stringstream bits;
   124 		std::stringstream bits;
   100 		for (bool b : value) bits << (int) b;
   125 		for (bool b : value) bits << (int) b;
   101 		// for (bool b : value) bits << (b ? ':' : '.'); // TODO: configurable true/false symbols?
   126 		// for (bool b : value) bits << (b ? ':' : '.'); // TODO: configurable true/false symbols?
   102 		handlers.writeStartElement("bit-string",{"length", std::to_string(value.size())});
   127 		handlers.writeStartElement("bit-string", getCommonAttributes(header,{"length", std::to_string(value.size())}));
   103 		handlers.writeCharacters(bits.str());
   128 		handlers.writeCharacters(bits.str());
   104 		handlers.writeEndElement();
   129 		handlers.writeEndElement();
   105 	}
   130 	}
   106 
   131 
   107 	void writeOID(const Header& header, ObjectIdentifier value) override {
   132 	void writeOID(const Header& header, ObjectIdentifier value) override {
   108 		// TODO: optionally expand into separate elements with additional metadata
   133 		// TODO: optionally expand into separate elements with additional metadata
   109 		handlers.writeStartElement("oid");
   134 		handlers.writeStartElement("oid", getCommonAttributes(header)); // TODO: {"length", std::to_string(value.size())}
   110 		handlers.writeCharacters(value.toString());
   135 		handlers.writeCharacters(value.toString());
   111 		handlers.writeEndElement();
   136 		handlers.writeEndElement();
   112 	}
   137 	}
   113 
   138 
   114 	void writeDateTime(const Header& header, DateTime value) override {
   139 	void writeDateTime(const Header& header, DateTime value) override {
   115 		handlers.writeStartElement("date-time");
   140 		handlers.writeStartElement("date-time", getCommonAttributes(header));
   116 		handlers.writeCharacters(value.toString());
   141 		handlers.writeCharacters(value.toString());
   117 		handlers.writeEndElement();
   142 		handlers.writeEndElement();
   118 	}
   143 	}
   119 
   144 
   120 	void writeSpecific(const Header& header, std::string value) override {
   145 	void writeSpecific(const Header& header, std::string value) override {
   123 		for (uint8_t b : value) hex << std::setw(2) << (int) b;
   148 		for (uint8_t b : value) hex << std::setw(2) << (int) b;
   124 
   149 
   125 		std::stringstream ascii;
   150 		std::stringstream ascii;
   126 		for (uint8_t b : value) ascii << (b >= 32 && b < 127 ? (char) b : '.'); // TODO: configurable unsupported symbol?
   151 		for (uint8_t b : value) ascii << (b >= 32 && b < 127 ? (char) b : '.'); // TODO: configurable unsupported symbol?
   127 
   152 
   128 		handlers.writeStartElement("specific",{"length", std::to_string(value.size()), "hex", hex.str()});
   153 		handlers.writeStartElement("specific", getCommonAttributes(header,{"length", std::to_string(value.size()), "hex", hex.str()}));
   129 		handlers.writeCharacters(ascii.str());
   154 		handlers.writeCharacters(ascii.str());
   130 		handlers.writeEndElement();
   155 		handlers.writeEndElement();
   131 	}
   156 	}
   132 
   157 
   133 
   158