1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 // MARKER(update_precomp.py): autogen include statement, do not remove 29 #include "precompiled_xmlsecurity.hxx" 30 31 #include "xsecparser.hxx" 32 #include <tools/debug.hxx> 33 #include "cppuhelper/exc_hlp.hxx" 34 35 #include <string.h> 36 37 namespace cssu = com::sun::star::uno; 38 namespace cssxs = com::sun::star::xml::sax; 39 40 #define RTL_ASCII_USTRINGPARAM( asciiStr ) asciiStr, strlen( asciiStr ), RTL_TEXTENCODING_ASCII_US 41 42 XSecParser::XSecParser( 43 XSecController* pXSecController, 44 const cssu::Reference< cssxs::XDocumentHandler >& xNextHandler ) 45 : m_pXSecController(pXSecController), 46 m_xNextHandler(xNextHandler), 47 m_bReferenceUnresolved(false) 48 { 49 } 50 51 rtl::OUString XSecParser::getIdAttr(const cssu::Reference< cssxs::XAttributeList >& xAttribs ) 52 { 53 rtl::OUString ouIdAttr = xAttribs->getValueByName( 54 rtl::OUString(RTL_ASCII_USTRINGPARAM("id"))); 55 56 if (ouIdAttr == NULL) 57 { 58 ouIdAttr = xAttribs->getValueByName( 59 rtl::OUString(RTL_ASCII_USTRINGPARAM("Id"))); 60 } 61 62 return ouIdAttr; 63 } 64 65 /* 66 * XDocumentHandler 67 */ 68 void SAL_CALL XSecParser::startDocument( ) 69 throw (cssxs::SAXException, cssu::RuntimeException) 70 { 71 m_bInX509IssuerName = false; 72 m_bInX509SerialNumber = false; 73 m_bInX509Certificate = false; 74 m_bInSignatureValue = false; 75 m_bInDigestValue = false; 76 m_bInDate = false; 77 //m_bInTime = false; 78 79 if (m_xNextHandler.is()) 80 { 81 m_xNextHandler->startDocument(); 82 } 83 } 84 85 void SAL_CALL XSecParser::endDocument( ) 86 throw (cssxs::SAXException, cssu::RuntimeException) 87 { 88 if (m_xNextHandler.is()) 89 { 90 m_xNextHandler->endDocument(); 91 } 92 } 93 94 void SAL_CALL XSecParser::startElement( 95 const rtl::OUString& aName, 96 const cssu::Reference< cssxs::XAttributeList >& xAttribs ) 97 throw (cssxs::SAXException, cssu::RuntimeException) 98 { 99 try 100 { 101 rtl::OUString ouIdAttr = getIdAttr(xAttribs); 102 if (ouIdAttr != NULL) 103 { 104 m_pXSecController->collectToVerify( ouIdAttr ); 105 } 106 107 if ( aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_SIGNATURE)) ) 108 { 109 m_pXSecController->addSignature(); 110 if (ouIdAttr != NULL) 111 { 112 m_pXSecController->setId( ouIdAttr ); 113 } 114 } 115 else if ( aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_REFERENCE)) ) 116 { 117 rtl::OUString ouUri = xAttribs->getValueByName(rtl::OUString(RTL_ASCII_USTRINGPARAM(ATTR_URI))); 118 DBG_ASSERT( ouUri != NULL, "URI == NULL" ); 119 120 if (0 == ouUri.compareTo(rtl::OUString(RTL_ASCII_USTRINGPARAM(CHAR_FRAGMENT)),1)) 121 { 122 /* 123 * remove the first character '#' from the attribute value 124 */ 125 m_pXSecController->addReference( ouUri.copy(1) ); 126 } 127 else 128 { 129 /* 130 * remember the uri 131 */ 132 m_currentReferenceURI = ouUri; 133 m_bReferenceUnresolved = true; 134 } 135 } 136 else if (aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_TRANSFORM))) 137 { 138 if ( m_bReferenceUnresolved ) 139 { 140 rtl::OUString ouAlgorithm = xAttribs->getValueByName(rtl::OUString(RTL_ASCII_USTRINGPARAM(ATTR_ALGORITHM))); 141 142 if (ouAlgorithm != NULL && ouAlgorithm == rtl::OUString(RTL_ASCII_USTRINGPARAM(ALGO_C14N))) 143 /* 144 * a xml stream 145 */ 146 { 147 m_pXSecController->addStreamReference( m_currentReferenceURI, sal_False); 148 m_bReferenceUnresolved = false; 149 } 150 } 151 } 152 else if (aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_X509ISSUERNAME))) 153 { 154 m_ouX509IssuerName = rtl::OUString::createFromAscii(""); 155 m_bInX509IssuerName = true; 156 } 157 else if (aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_X509SERIALNUMBER))) 158 { 159 m_ouX509SerialNumber = rtl::OUString::createFromAscii(""); 160 m_bInX509SerialNumber = true; 161 } 162 else if (aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_X509CERTIFICATE))) 163 { 164 m_ouX509Certificate = rtl::OUString::createFromAscii(""); 165 m_bInX509Certificate = true; 166 } 167 else if (aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_SIGNATUREVALUE))) 168 { 169 m_ouSignatureValue = rtl::OUString::createFromAscii(""); 170 m_bInSignatureValue = true; 171 } 172 else if (aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_DIGESTVALUE))) 173 { 174 m_ouDigestValue = rtl::OUString::createFromAscii(""); 175 m_bInDigestValue = true; 176 } 177 else if ( aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_SIGNATUREPROPERTY)) ) 178 { 179 if (ouIdAttr != NULL) 180 { 181 m_pXSecController->setPropertyId( ouIdAttr ); 182 } 183 } 184 else if (aName == rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(NSTAG_DC)) 185 +rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(":")) 186 +rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(TAG_DATE))) 187 { 188 m_ouDate = rtl::OUString::createFromAscii(""); 189 m_bInDate = true; 190 } 191 /* 192 else if (aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_TIME))) 193 { 194 m_ouTime = rtl::OUString::createFromAscii(""); 195 m_bInTime = true; 196 } 197 */ 198 199 if (m_xNextHandler.is()) 200 { 201 m_xNextHandler->startElement(aName, xAttribs); 202 } 203 } 204 catch (cssu::Exception& ) 205 {//getCaughtException MUST be the first line in the catch block 206 cssu::Any exc = cppu::getCaughtException(); 207 throw cssxs::SAXException( 208 rtl::OUString(RTL_CONSTASCII_USTRINGPARAM( 209 "xmlsecurity: Exception in XSecParser::startElement")), 210 0, exc); 211 } 212 catch (...) 213 { 214 throw cssxs::SAXException( 215 rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("xmlsecurity: unexpected exception in XSecParser::startElement")), 0, 216 cssu::Any()); 217 } 218 } 219 220 void SAL_CALL XSecParser::endElement( const rtl::OUString& aName ) 221 throw (cssxs::SAXException, cssu::RuntimeException) 222 { 223 try 224 { 225 if (aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_DIGESTVALUE))) 226 { 227 m_bInDigestValue = false; 228 } 229 else if ( aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_REFERENCE)) ) 230 { 231 if ( m_bReferenceUnresolved ) 232 /* 233 * it must be a octet stream 234 */ 235 { 236 m_pXSecController->addStreamReference( m_currentReferenceURI, sal_True); 237 m_bReferenceUnresolved = false; 238 } 239 240 m_pXSecController->setDigestValue( m_ouDigestValue ); 241 } 242 else if ( aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_SIGNEDINFO)) ) 243 { 244 m_pXSecController->setReferenceCount(); 245 } 246 else if ( aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_SIGNATUREVALUE)) ) 247 { 248 m_pXSecController->setSignatureValue( m_ouSignatureValue ); 249 m_bInSignatureValue = false; 250 } 251 else if (aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_X509ISSUERNAME))) 252 { 253 m_pXSecController->setX509IssuerName( m_ouX509IssuerName ); 254 m_bInX509IssuerName = false; 255 } 256 else if (aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_X509SERIALNUMBER))) 257 { 258 m_pXSecController->setX509SerialNumber( m_ouX509SerialNumber ); 259 m_bInX509SerialNumber = false; 260 } 261 else if (aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_X509CERTIFICATE))) 262 { 263 m_pXSecController->setX509Certificate( m_ouX509Certificate ); 264 m_bInX509Certificate = false; 265 } 266 else if (aName == rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(NSTAG_DC)) 267 +rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(":")) 268 +rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(TAG_DATE))) 269 { 270 m_pXSecController->setDate( m_ouDate ); 271 m_bInDate = false; 272 } 273 /* 274 else if ( aName == rtl::OUString(RTL_ASCII_USTRINGPARAM(TAG_TIME)) ) 275 { 276 m_pXSecController->setTime( m_ouTime ); 277 m_bInTime = false; 278 } 279 */ 280 281 if (m_xNextHandler.is()) 282 { 283 m_xNextHandler->endElement(aName); 284 } 285 } 286 catch (cssu::Exception& ) 287 {//getCaughtException MUST be the first line in the catch block 288 cssu::Any exc = cppu::getCaughtException(); 289 throw cssxs::SAXException( 290 rtl::OUString(RTL_CONSTASCII_USTRINGPARAM( 291 "xmlsecurity: Exception in XSecParser::endElement")), 292 0, exc); 293 } 294 catch (...) 295 { 296 throw cssxs::SAXException( 297 rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("xmlsecurity: unexpected exception in XSecParser::endElement")), 0, 298 cssu::Any()); 299 } 300 } 301 302 void SAL_CALL XSecParser::characters( const rtl::OUString& aChars ) 303 throw (cssxs::SAXException, cssu::RuntimeException) 304 { 305 if (m_bInX509IssuerName) 306 { 307 m_ouX509IssuerName += aChars; 308 } 309 else if (m_bInX509SerialNumber) 310 { 311 m_ouX509SerialNumber += aChars; 312 } 313 else if (m_bInX509Certificate) 314 { 315 m_ouX509Certificate += aChars; 316 } 317 else if (m_bInSignatureValue) 318 { 319 m_ouSignatureValue += aChars; 320 } 321 else if (m_bInDigestValue) 322 { 323 m_ouDigestValue += aChars; 324 } 325 else if (m_bInDate) 326 { 327 m_ouDate += aChars; 328 } 329 /* 330 else if (m_bInTime) 331 { 332 m_ouTime += aChars; 333 } 334 */ 335 336 if (m_xNextHandler.is()) 337 { 338 m_xNextHandler->characters(aChars); 339 } 340 } 341 342 void SAL_CALL XSecParser::ignorableWhitespace( const rtl::OUString& aWhitespaces ) 343 throw (cssxs::SAXException, cssu::RuntimeException) 344 { 345 if (m_xNextHandler.is()) 346 { 347 m_xNextHandler->ignorableWhitespace( aWhitespaces ); 348 } 349 } 350 351 void SAL_CALL XSecParser::processingInstruction( const rtl::OUString& aTarget, const rtl::OUString& aData ) 352 throw (cssxs::SAXException, cssu::RuntimeException) 353 { 354 if (m_xNextHandler.is()) 355 { 356 m_xNextHandler->processingInstruction(aTarget, aData); 357 } 358 } 359 360 void SAL_CALL XSecParser::setDocumentLocator( const cssu::Reference< cssxs::XLocator >& xLocator ) 361 throw (cssxs::SAXException, cssu::RuntimeException) 362 { 363 if (m_xNextHandler.is()) 364 { 365 m_xNextHandler->setDocumentLocator( xLocator ); 366 } 367 } 368 369 /* 370 * XInitialization 371 */ 372 void SAL_CALL XSecParser::initialize( 373 const cssu::Sequence< cssu::Any >& aArguments ) 374 throw(cssu::Exception, cssu::RuntimeException) 375 { 376 aArguments[0] >>= m_xNextHandler; 377 } 378