Change license header, remove stale pkg files.
[shibboleth/cpp-opensaml.git] / saml / binding / impl / SAMLArtifact.cpp
1 /**
2  * Licensed to the University Corporation for Advanced Internet
3  * Development, Inc. (UCAID) under one or more contributor license
4  * agreements. See the NOTICE file distributed with this work for
5  * additional information regarding copyright ownership.
6  *
7  * UCAID licenses this file to you under the Apache License,
8  * Version 2.0 (the "License"); you may not use this file except
9  * in compliance with the License. You may obtain a copy of the
10  * License at
11  *
12  * http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing,
15  * software distributed under the License is distributed on an
16  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
17  * either express or implied. See the License for the specific
18  * language governing permissions and limitations under the License.
19  */
20
21 /**
22  * SAMLArtifact.cpp
23  * 
24  * Base class for SAML 1.x and 2.0 artifacts.
25  */
26
27 #include "internal.h"
28 #include "binding/SAMLArtifact.h"
29
30 #include <xercesc/util/Base64.hpp>
31 #include <xsec/framework/XSECDefs.hpp>
32 #include <xmltooling/unicode.h>
33
34 using namespace opensaml;
35 using namespace xmltooling;
36 using namespace std;
37
38 namespace opensaml {
39     namespace saml1p {
40         SAML_DLLLOCAL PluginManager<SAMLArtifact,string,const char*>::Factory SAMLArtifactType0001Factory; 
41         SAML_DLLLOCAL PluginManager<SAMLArtifact,string,const char*>::Factory SAMLArtifactType0002Factory; 
42     };
43
44     namespace saml2p {
45         SAML_DLLLOCAL PluginManager<SAMLArtifact,string,const char*>::Factory SAML2ArtifactType0004Factory; 
46     };
47 };
48
49 void SAML_API opensaml::registerSAMLArtifacts()
50 {
51     SAMLConfig& conf=SAMLConfig::getConfig();
52
53     string typecode;
54     typecode+=(char)0x0;
55     typecode+=(char)0x1;
56     conf.SAMLArtifactManager.registerFactory(typecode, saml1p::SAMLArtifactType0001Factory);
57     typecode[1]=(char)0x2;
58     conf.SAMLArtifactManager.registerFactory(typecode, saml1p::SAMLArtifactType0002Factory);
59     typecode[1]=(char)0x4;
60     conf.SAMLArtifactManager.registerFactory(typecode, saml2p::SAML2ArtifactType0004Factory);
61 }
62
63 const unsigned int SAMLArtifact::TYPECODE_LENGTH = 2;
64
65 SAMLArtifact::SAMLArtifact()
66 {
67 }
68
69 SAMLArtifact::~SAMLArtifact()
70 {
71 }
72
73 SAMLArtifact::SAMLArtifact(const SAMLArtifact& src) : m_raw(src.m_raw)
74 {
75 }
76
77 // Basic constructor just decodes the string and saves it off.
78 // Subclasses will handle pulling it apart.
79
80 SAMLArtifact::SAMLArtifact(const char* s)
81 {
82     xsecsize_t len=0;
83     XMLByte* decoded=Base64::decode(reinterpret_cast<const XMLByte*>(s),&len);
84     if (!decoded)
85         throw ArtifactException("Unable to decode base64 artifact.");
86     XMLByte* ptr=decoded;
87     while (len--)
88         m_raw+= *ptr++;
89 #ifdef OPENSAML_XERCESC_HAS_XMLBYTE_RELEASE
90     XMLString::release(&decoded);
91 #else
92     XMLString::release((char**)&decoded);
93 #endif
94 }
95
96 string SAMLArtifact::getBytes() const
97 {
98     return m_raw;
99 }
100
101 string SAMLArtifact::getTypeCode() const
102 {
103     return m_raw.substr(0,TYPECODE_LENGTH);
104 }
105
106 string SAMLArtifact::getRemainingArtifact() const
107 {
108     return m_raw.substr(TYPECODE_LENGTH);
109 }
110
111 string SAMLArtifact::encode() const
112 {
113     xsecsize_t len=0;
114     XMLByte* out=Base64::encode(reinterpret_cast<const XMLByte*>(m_raw.data()),m_raw.size(),&len);
115     if (out) {
116         string ret(reinterpret_cast<char*>(out),len);
117 #ifdef OPENSAML_XERCESC_HAS_XMLBYTE_RELEASE
118         XMLString::release(&out);
119 #else
120         XMLString::release((char**)&out);
121 #endif
122         return ret;
123     }
124     return string();
125 }
126
127 SAMLArtifact* SAMLArtifact::parse(const char* s)
128 {
129     // Decode and extract the type code first.
130     xsecsize_t len=0;
131     XMLByte* decoded=Base64::decode(reinterpret_cast<const XMLByte*>(s),&len);
132     if (!decoded)
133         throw ArtifactException("Artifact parser unable to decode base64-encoded artifact.");
134     
135     string type;
136     type+= decoded[0];
137     type+= decoded[1];
138 #ifdef OPENSAML_XERCESC_HAS_XMLBYTE_RELEASE
139     XMLString::release(&decoded);
140 #else
141     XMLString::release((char**)&decoded);
142 #endif
143     
144     return SAMLConfig::getConfig().SAMLArtifactManager.newPlugin(type,s);
145 }
146
147 SAMLArtifact* SAMLArtifact::parse(const XMLCh* s)
148 {
149     auto_ptr_char temp(s);
150     return parse(temp.get());
151 }
152
153 string SAMLArtifact::toHex(const string& s)
154 {
155     static char DIGITS[] = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'};
156     string::size_type len = s.length();
157     string ret;
158     
159     // two characters form the hex value.
160     for (string::size_type i=0; i < len; i++) {
161         ret+=(DIGITS[((unsigned char)(0xF0 & s[i])) >> 4 ]);
162         ret+=(DIGITS[0x0F & s[i]]);
163     }
164     return ret;
165 }