goto loser;
/* start the child decoder */
- childp7dcx->dcx = SEC_ASN1DecoderStart(poolp, childp7dcx->content.pointer, template, NULL);
+ childp7dcx->dcx = SEC_ASN1DecoderStart(poolp, childp7dcx->content.pointer, template, NULL, 0);
if (childp7dcx->dcx == NULL)
goto loser;
nss_cms_after_end(SecCmsDecoderRef p7dcx)
{
OSStatus rv;
- PLArenaPool *poolp;
-
- poolp = p7dcx->cmsg->poolp;
switch (p7dcx->type) {
case SEC_OID_PKCS7_SIGNED_DATA:
storage = cinfo->content.data;
offset = storage->Length;
+
+ /* check for potential overflow */
+ if (len >= (size_t)(INT_MAX - storage->Length)) {
+ p7dcx->error = SEC_ERROR_NO_MEMORY;
+ goto loser;
+ }
+
if (storage->Length == 0) {
dest = (unsigned char *)PORT_ArenaAlloc(p7dcx->cmsg->poolp, len);
} else {
goto loser;
}
- p7dcx->dcx = SEC_ASN1DecoderStart(cmsg->poolp, cmsg, SecCmsMessageTemplate, NULL);
+ p7dcx->dcx = SEC_ASN1DecoderStart(cmsg->poolp, cmsg, SecCmsMessageTemplate, NULL, 0);
if (p7dcx->dcx == NULL) {
PORT_Free (p7dcx);
SecCmsMessageDestroy(cmsg);
OSStatus
SecCmsDecoderUpdate(SecCmsDecoderRef p7dcx, const void *buf, CFIndex len)
{
+ if (!p7dcx) {
+ return errSecParam;
+ }
+
if (p7dcx->dcx != NULL && p7dcx->error == 0) { /* if error is set already, don't bother */
if (SEC_ASN1DecoderUpdate (p7dcx->dcx, buf, len) != SECSuccess) {
p7dcx->error = PORT_GetError();
void
SecCmsDecoderDestroy(SecCmsDecoderRef p7dcx)
{
- /* XXXX what about inner decoders? running digests? decryption? */
- /* XXXX there's a leak here! */
+ /* SecCmsMessageDestroy frees inner decoders and digests. */
SecCmsMessageDestroy(p7dcx->cmsg);
+ p7dcx->cmsg = NULL;
if (p7dcx->dcx)
(void)SEC_ASN1DecoderFinish(p7dcx->dcx);
+ /* Clear out references */
+ p7dcx->cmsg = NULL;
+ p7dcx->dcx = NULL;
+ p7dcx->childp7dcx = NULL;
PORT_Free(p7dcx);
}
if (p7dcx->dcx == NULL || SEC_ASN1DecoderFinish(p7dcx->dcx) != SECSuccess ||
nss_cms_after_end(p7dcx) != SECSuccess)
{
- SecCmsMessageDestroy(cmsg);
+ if (p7dcx->cmsg) {
+ SecCmsMessageDestroy(cmsg);
+ }
result = PORT_GetError();
goto loser;
}
result = errSecSuccess;
loser:
+ /* Clear out references */
+ p7dcx->cmsg = NULL;
+ p7dcx->dcx = NULL;
+ p7dcx->childp7dcx = NULL;
PORT_Free(p7dcx);
return result;
}