1 /*-------------------------------------------------------------------------
2 * drawElements Quality Program Test Executor
3 * ------------------------------------------
5 * Copyright 2014 The Android Open Source Project
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
11 * http://www.apache.org/licenses/LICENSE-2.0
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
22 *//*--------------------------------------------------------------------*/
24 #include "xeXMLWriter.hpp"
33 const Writer::EndElementType Writer::EndElement = Writer::EndElementType();
35 inline const char* getEscapeEntity (char ch)
39 case '<': return "<";
40 case '>': return ">";
41 case '&': return "&";
42 case '\'': return "'";
43 case '"': return """;
45 // Non-printable characters.
46 case 0: return "<NUL>";
47 case 1: return "<SOH>";
48 case 2: return "<STX>";
49 case 3: return "<ETX>";
50 case 4: return "<EOT>";
51 case 5: return "<ENQ>";
52 case 6: return "<ACK>";
53 case 7: return "<BEL>";
54 case 8: return "<BS>";
55 case 11: return "<VT>";
56 case 12: return "<FF>";
57 case 14: return "<SO>";
58 case 15: return "<SI>";
59 case 16: return "<DLE>";
60 case 17: return "<DC1>";
61 case 18: return "<DC2>";
62 case 19: return "<DC3>";
63 case 20: return "<DC4>";
64 case 21: return "<NAK>";
65 case 22: return "<SYN>";
66 case 23: return "<ETB>";
67 case 24: return "<CAN>";
68 case 25: return "<EM>";
69 case 26: return "<SUB>";
70 case 27: return "<ESC>";
71 case 28: return "<FS>";
72 case 29: return "<GS>";
73 case 30: return "<RS>";
74 case 31: return "<US>";
76 default: return DE_NULL;
80 std::streamsize EscapeStreambuf::xsputn (const char* s, std::streamsize count)
82 std::streamsize numWritten = 0;
84 for (std::streamsize inPos = 0; inPos < count; inPos++)
86 const char* entity = getEscapeEntity(s[inPos]);
90 // Flush data prior to entity.
91 if (inPos > numWritten)
93 m_dst.write(s + numWritten, inPos-numWritten);
99 m_dst.write(entity, (std::streamsize)strlen(entity));
101 numWritten = inPos+1;
105 if (numWritten < count)
107 m_dst.write(s + numWritten, count-numWritten);
115 int EscapeStreambuf::overflow (int ch)
121 DE_ASSERT((ch & 0xff) == ch);
122 const char chVal = (char)(deUint8)(ch & 0xff);
123 return xsputn(&chVal, 1) == 1 ? ch : -1;
127 Writer::Writer (std::ostream& dst)
130 , m_dataStr (&m_dataBuf)
131 , m_state (STATE_DATA)
135 Writer::~Writer (void)
139 Writer& Writer::operator<< (const BeginElement& begin)
141 if (m_state == STATE_ELEMENT)
144 if (m_state == STATE_ELEMENT || m_state == STATE_ELEMENT_END)
147 for (int i = 0; i < (int)m_elementStack.size(); i++)
151 m_rawDst << "<" << begin.element;
153 m_elementStack.push_back(begin.element);
154 m_state = STATE_ELEMENT;
159 Writer& Writer::operator<< (const Attribute& attribute)
161 DE_ASSERT(m_state == STATE_ELEMENT);
163 // \todo [2012-09-05 pyry] Escape?
164 m_rawDst << " " << attribute.name << "=\"" << attribute.value << "\"";
169 Writer& Writer::operator<< (const EndElementType&)
171 if (m_state == STATE_ELEMENT)
175 if (m_state == STATE_ELEMENT_END)
178 for (int i = 0; i < (int)m_elementStack.size()-1; i++)
182 m_rawDst << "</" << m_elementStack.back() << ">";
185 m_elementStack.pop_back();
186 m_state = STATE_ELEMENT_END;