|
1 /** |
|
2 * XML Security Library (http://www.aleksey.com/xmlsec). |
|
3 * |
|
4 * Memory buffer transform |
|
5 * |
|
6 * This is free software; see Copyright file in the source |
|
7 * distribution for preciese wording. |
|
8 * |
|
9 * Copyright (C) 2002-2003 Aleksey Sanin <aleksey@aleksey.com> |
|
10 * Portion Copyright © 2009 Nokia Corporation and/or its subsidiary(-ies). All rights reserved. |
|
11 */ |
|
12 #include "xmlsec_globals.h" |
|
13 |
|
14 #include <stdlib.h> |
|
15 #include <string.h> |
|
16 |
|
17 #include <libxml2_tree.h> |
|
18 |
|
19 #include "xmlsec_xmlsec.h" |
|
20 #include "xmlsec_buffer.h" |
|
21 #include "xmlsec_keys.h" |
|
22 #include "xmlsec_transforms.h" |
|
23 #include "xmlsec_keys.h" |
|
24 #include "xmlsec_base64.h" |
|
25 #include "xmlsec_membuf.h" |
|
26 #include "xmlsec_errors.h" |
|
27 |
|
28 /***************************************************************************** |
|
29 * |
|
30 * Memory Buffer Transform |
|
31 * |
|
32 * xmlSecBuffer is located after xmlSecTransform |
|
33 * |
|
34 ****************************************************************************/ |
|
35 #define xmlSecTransformMemBufSize \ |
|
36 (sizeof(xmlSecTransform) + sizeof(xmlSecBuffer)) |
|
37 #define xmlSecTransformMemBufGetBuf(transform) \ |
|
38 ((xmlSecTransformCheckSize((transform), xmlSecTransformMemBufSize)) ? \ |
|
39 (xmlSecBufferPtr)(((xmlSecByte*)(transform)) + sizeof(xmlSecTransform)) : \ |
|
40 (xmlSecBufferPtr)NULL) |
|
41 |
|
42 static int xmlSecTransformMemBufInitialize (xmlSecTransformPtr transform); |
|
43 static void xmlSecTransformMemBufFinalize (xmlSecTransformPtr transform); |
|
44 static int xmlSecTransformMemBufExecute (xmlSecTransformPtr transform, |
|
45 int last, |
|
46 xmlSecTransformCtxPtr transformCtx); |
|
47 static xmlSecTransformKlass xmlSecTransformMemBufKlass = { |
|
48 /* klass/object sizes */ |
|
49 sizeof(xmlSecTransformKlass), /* xmlSecSize klassSize */ |
|
50 xmlSecTransformMemBufSize, /* xmlSecSize objSize */ |
|
51 |
|
52 xmlSecNameMemBuf, /* const xmlChar* name; */ |
|
53 NULL, /* const xmlChar* href; */ |
|
54 0, /* xmlSecAlgorithmUsage usage; */ |
|
55 |
|
56 xmlSecTransformMemBufInitialize, /* xmlSecTransformInitializeMethod initialize; */ |
|
57 xmlSecTransformMemBufFinalize, /* xmlSecTransformFianlizeMethod finalize; */ |
|
58 NULL, /* xmlSecTransformNodeReadMethod readNode; */ |
|
59 NULL, /* xmlSecTransformNodeWriteMethod writeNode; */ |
|
60 NULL, /* xmlSecTransformSetKeyReqMethod setKeyReq; */ |
|
61 NULL, /* xmlSecTransformSetKeyMethod setKey; */ |
|
62 NULL, /* xmlSecTransformValidateMethod validate; */ |
|
63 xmlSecTransformDefaultGetDataType, /* xmlSecTransformGetDataTypeMethod getDataType; */ |
|
64 xmlSecTransformDefaultPushBin, /* xmlSecTransformPushBinMethod pushBin; */ |
|
65 xmlSecTransformDefaultPopBin, /* xmlSecTransformPopBinMethod popBin; */ |
|
66 NULL, /* xmlSecTransformPushXmlMethod pushXml; */ |
|
67 NULL, /* xmlSecTransformPopXmlMethod popXml; */ |
|
68 xmlSecTransformMemBufExecute, /* xmlSecTransformExecuteMethod execute; */ |
|
69 |
|
70 NULL, /* void* reserved0; */ |
|
71 NULL, /* void* reserved1; */ |
|
72 }; |
|
73 |
|
74 /** |
|
75 * xmlSecTransformMemBufGetKlass: |
|
76 * |
|
77 * The memory buffer transorm (used to store the data that go through it). |
|
78 * |
|
79 * Returns memory buffer transform klass. |
|
80 */ |
|
81 EXPORT_C |
|
82 xmlSecTransformId |
|
83 xmlSecTransformMemBufGetKlass(void) { |
|
84 return(&xmlSecTransformMemBufKlass); |
|
85 } |
|
86 |
|
87 /** |
|
88 * xmlSecTransformMemBufGetBuffer: |
|
89 * @transform: the pointer to memory buffer transform. |
|
90 * |
|
91 * Gets the pointer to memory buffer transform buffer. |
|
92 * |
|
93 * Returns pointer to the transform's #xmlSecBuffer. |
|
94 */ |
|
95 EXPORT_C |
|
96 xmlSecBufferPtr |
|
97 xmlSecTransformMemBufGetBuffer(xmlSecTransformPtr transform) { |
|
98 xmlSecBufferPtr buffer; |
|
99 |
|
100 xmlSecAssert2(xmlSecTransformCheckId(transform, xmlSecTransformMemBufId), NULL); |
|
101 |
|
102 buffer = xmlSecTransformMemBufGetBuf(transform); |
|
103 xmlSecAssert2(buffer != NULL, NULL); |
|
104 |
|
105 return(buffer); |
|
106 } |
|
107 |
|
108 static int |
|
109 xmlSecTransformMemBufInitialize(xmlSecTransformPtr transform) { |
|
110 xmlSecBufferPtr buffer; |
|
111 int ret; |
|
112 |
|
113 xmlSecAssert2(xmlSecTransformCheckId(transform, xmlSecTransformMemBufId), -1); |
|
114 |
|
115 buffer = xmlSecTransformMemBufGetBuf(transform); |
|
116 xmlSecAssert2(buffer != NULL, -1); |
|
117 |
|
118 ret = xmlSecBufferInitialize(buffer, 0); |
|
119 if(ret < 0) { |
|
120 xmlSecError(XMLSEC_ERRORS_HERE, |
|
121 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)), |
|
122 "xmlSecBufferInitialize", |
|
123 XMLSEC_ERRORS_R_XMLSEC_FAILED, |
|
124 XMLSEC_ERRORS_NO_MESSAGE); |
|
125 return(-1); |
|
126 } |
|
127 return(0); |
|
128 } |
|
129 |
|
130 static void |
|
131 xmlSecTransformMemBufFinalize(xmlSecTransformPtr transform) { |
|
132 xmlSecBufferPtr buffer; |
|
133 |
|
134 xmlSecAssert(xmlSecTransformCheckId(transform, xmlSecTransformMemBufId)); |
|
135 |
|
136 buffer = xmlSecTransformMemBufGetBuf(transform); |
|
137 xmlSecAssert(buffer != NULL); |
|
138 |
|
139 xmlSecBufferFinalize(xmlSecTransformMemBufGetBuf(transform)); |
|
140 } |
|
141 |
|
142 static int |
|
143 xmlSecTransformMemBufExecute(xmlSecTransformPtr transform, int last, xmlSecTransformCtxPtr transformCtx) { |
|
144 xmlSecBufferPtr buffer; |
|
145 xmlSecBufferPtr in, out; |
|
146 xmlSecSize inSize; |
|
147 int ret; |
|
148 |
|
149 xmlSecAssert2(xmlSecTransformCheckId(transform, xmlSecTransformMemBufId), -1); |
|
150 xmlSecAssert2(transformCtx != NULL, -1); |
|
151 |
|
152 buffer = xmlSecTransformMemBufGetBuf(transform); |
|
153 xmlSecAssert2(buffer != NULL, -1); |
|
154 |
|
155 in = &(transform->inBuf); |
|
156 out = &(transform->outBuf); |
|
157 inSize = xmlSecBufferGetSize(in); |
|
158 |
|
159 if(transform->status == xmlSecTransformStatusNone) { |
|
160 transform->status = xmlSecTransformStatusWorking; |
|
161 } |
|
162 |
|
163 if(transform->status == xmlSecTransformStatusWorking) { |
|
164 /* just copy everything from in to our buffer and out */ |
|
165 ret = xmlSecBufferAppend(buffer, xmlSecBufferGetData(in), inSize); |
|
166 if(ret < 0) { |
|
167 xmlSecError(XMLSEC_ERRORS_HERE, |
|
168 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)), |
|
169 "xmlSecBufferAppend", |
|
170 XMLSEC_ERRORS_R_XMLSEC_FAILED, |
|
171 "size=%d", inSize); |
|
172 return(-1); |
|
173 } |
|
174 |
|
175 ret = xmlSecBufferAppend(out, xmlSecBufferGetData(in), inSize); |
|
176 if(ret < 0) { |
|
177 xmlSecError(XMLSEC_ERRORS_HERE, |
|
178 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)), |
|
179 "xmlSecBufferAppend", |
|
180 XMLSEC_ERRORS_R_XMLSEC_FAILED, |
|
181 "size=%d", inSize); |
|
182 return(-1); |
|
183 } |
|
184 |
|
185 ret = xmlSecBufferRemoveHead(in, inSize); |
|
186 if(ret < 0) { |
|
187 xmlSecError(XMLSEC_ERRORS_HERE, |
|
188 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)), |
|
189 "xmlSecBufferRemoveHead", |
|
190 XMLSEC_ERRORS_R_XMLSEC_FAILED, |
|
191 "size=%d", inSize); |
|
192 return(-1); |
|
193 } |
|
194 |
|
195 if(last != 0) { |
|
196 transform->status = xmlSecTransformStatusFinished; |
|
197 } |
|
198 } else if(transform->status == xmlSecTransformStatusFinished) { |
|
199 /* the only way we can get here is if there is no input */ |
|
200 xmlSecAssert2(inSize == 0, -1); |
|
201 } else { |
|
202 xmlSecError(XMLSEC_ERRORS_HERE, |
|
203 xmlSecErrorsSafeString(xmlSecTransformGetName(transform)), |
|
204 NULL, |
|
205 XMLSEC_ERRORS_R_INVALID_STATUS, |
|
206 "status=%d", transform->status); |
|
207 return(-1); |
|
208 } |
|
209 return(0); |
|
210 } |
|
211 |
|
212 |
|
213 |