X-Git-Url: https://git.openssl.org/?p=openssl.git;a=blobdiff_plain;f=crypto%2Fasn1%2Ftasn_utl.c;h=f79d7d6b447cf2ed5d3eb19ebbbfedcd0c8495f3;hp=f03f9e9ed04b5684daaa71463fc2b07b641569f6;hb=a3ea6bf0ef703b38a656245931979c7e53c410b7;hpb=b2b361f6afb55c501bedef664c1fdc0d71a91d4b diff --git a/crypto/asn1/tasn_utl.c b/crypto/asn1/tasn_utl.c index f03f9e9ed0..f79d7d6b44 100644 --- a/crypto/asn1/tasn_utl.c +++ b/crypto/asn1/tasn_utl.c @@ -46,13 +46,14 @@ int asn1_set_choice_selector(ASN1_VALUE **pval, int value, } /* - * Do reference counting. The value 'op' decides what to do. if it is +1 - * then the count is incremented. If op is 0 count is set to 1. If op is -1 - * count is decremented and the return value is the current reference count - * or 0 if no reference count exists. - * FIXME: return and manage any error from inside this method + * Do atomic reference counting. The value 'op' decides what to do. + * If it is +1 then the count is incremented. + * If |op| is 0, lock is initialised and count is set to 1. + * If |op| is -1, count is decremented and the return value is the current + * reference count or 0 if no reference count is active. + * It returns -1 on initialisation error. + * Used by ASN1_SEQUENCE construct of X509, X509_REQ, X509_CRL objects */ - int asn1_do_lock(ASN1_VALUE **pval, int op, const ASN1_ITEM *it) { const ASN1_AUX *aux; @@ -70,18 +71,21 @@ int asn1_do_lock(ASN1_VALUE **pval, int op, const ASN1_ITEM *it) *lck = 1; *lock = CRYPTO_THREAD_lock_new(); if (*lock == NULL) { - /* FIXME: should report an error (-1) at this point */ - return 0; + ASN1err(ASN1_F_ASN1_DO_LOCK, ERR_R_MALLOC_FAILURE); + return -1; } return 1; } - CRYPTO_atomic_add(lck, op, &ret, *lock); + if (CRYPTO_atomic_add(lck, op, &ret, *lock) < 0) + return -1; /* failed */ #ifdef REF_PRINT fprintf(stderr, "%p:%4d:%s\n", it, *lck, it->sname); #endif REF_ASSERT_ISNT(ret < 0); - if (ret == 0) + if (ret == 0) { CRYPTO_THREAD_lock_free(*lock); + *lock = NULL; + } return ret; } @@ -189,7 +193,7 @@ const ASN1_TEMPLATE *asn1_do_adb(ASN1_VALUE **pval, const ASN1_TEMPLATE *tt, sfld = offset2ptr(*pval, adb->offset); /* Check if NULL */ - if (!sfld) { + if (*sfld == NULL) { if (!adb->null_tt) goto err; return adb->null_tt;