While running clang-tidy on my project that uses concurrentqueue it reports a possible null pointer dereference when using enqueue. Not sure if this is fully possible, but wanted to report it. The output is below.
/home/user/project/src/parsers/Serializer.cpp:38:9: note: Calling 'ConcurrentQueue::enqueue' EventWorker::event_queue.enqueue(json_value); ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:913:3: note: Taking false branch if (INITIAL_IMPLICIT_PRODUCER_HASH_SIZE == 0) return false; ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:914:10: note: Calling 'ConcurrentQueue::inner_enqueue' return inner_enqueue<CanAlloc>(item); ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:1288:19: note: Calling 'ConcurrentQueue::get_or_add_implicit_producer' auto producer = get_or_add_implicit_producer(); ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3312:19: note: Calling 'atomic::load' auto mainHash = implicitProducerHash.load(std::memory_order_acquire); ^ /opt/rh/devtoolset-7/root/usr/bin/../lib/gcc/x86_64-redhat-linux/7/../../../../include/c++/7/atomic:452:16: note: Calling '__atomic_base::load' { return _M_b.load(__m); } ^ /opt/rh/devtoolset-7/root/usr/bin/../lib/gcc/x86_64-redhat-linux/7/../../../../include/c++/7/bits/atomic_base.h:709:21: note: Calling 'operator&' memory_order __b = __m & __memory_order_mask; ^ /opt/rh/devtoolset-7/root/usr/bin/../lib/gcc/x86_64-redhat-linux/7/../../../../include/c++/7/bits/atomic_base.h:709:21: note: Returning from 'operator&' /opt/rh/devtoolset-7/root/usr/bin/../lib/gcc/x86_64-redhat-linux/7/../../../../include/c++/7/atomic:452:16: note: Returning from '__atomic_base::load' { return _M_b.load(__m); } ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3312:19: note: Returning from 'atomic::load' auto mainHash = implicitProducerHash.load(std::memory_order_acquire); ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3312:3: note: 'mainHash' initialized here auto mainHash = implicitProducerHash.load(std::memory_order_acquire); ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3313:30: note: Assuming the condition is false for (auto hash = mainHash; hash != nullptr; hash = hash->prev) { ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3313:30: note: Assuming pointer value is null /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3313:3: note: Loop condition is false. Execution continues on line 3357 for (auto hash = mainHash; hash != nullptr; hash = hash->prev) { ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3358:3: note: Loop condition is true. Entering loop body while (true) { ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3359:21: note: Access to field 'capacity' results in a dereference of a null pointer (loaded from variable 'mainHash') if (newCount >= (mainHash->capacity >> 1) && !implicitProducerHashResizeInProgress.test_and_set(std::memory_order_acquire)) {
While running clang-tidy on my project that uses concurrentqueue it reports a possible null pointer dereference when using enqueue. Not sure if this is fully possible, but wanted to report it. The output is below.
/home/user/project/src/parsers/Serializer.cpp:38:9: note: Calling 'ConcurrentQueue::enqueue' EventWorker::event_queue.enqueue(json_value); ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:913:3: note: Taking false branch if (INITIAL_IMPLICIT_PRODUCER_HASH_SIZE == 0) return false; ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:914:10: note: Calling 'ConcurrentQueue::inner_enqueue' return inner_enqueue<CanAlloc>(item); ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:1288:19: note: Calling 'ConcurrentQueue::get_or_add_implicit_producer' auto producer = get_or_add_implicit_producer(); ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3312:19: note: Calling 'atomic::load' auto mainHash = implicitProducerHash.load(std::memory_order_acquire); ^ /opt/rh/devtoolset-7/root/usr/bin/../lib/gcc/x86_64-redhat-linux/7/../../../../include/c++/7/atomic:452:16: note: Calling '__atomic_base::load' { return _M_b.load(__m); } ^ /opt/rh/devtoolset-7/root/usr/bin/../lib/gcc/x86_64-redhat-linux/7/../../../../include/c++/7/bits/atomic_base.h:709:21: note: Calling 'operator&' memory_order __b = __m & __memory_order_mask; ^ /opt/rh/devtoolset-7/root/usr/bin/../lib/gcc/x86_64-redhat-linux/7/../../../../include/c++/7/bits/atomic_base.h:709:21: note: Returning from 'operator&' /opt/rh/devtoolset-7/root/usr/bin/../lib/gcc/x86_64-redhat-linux/7/../../../../include/c++/7/atomic:452:16: note: Returning from '__atomic_base::load' { return _M_b.load(__m); } ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3312:19: note: Returning from 'atomic::load' auto mainHash = implicitProducerHash.load(std::memory_order_acquire); ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3312:3: note: 'mainHash' initialized here auto mainHash = implicitProducerHash.load(std::memory_order_acquire); ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3313:30: note: Assuming the condition is false for (auto hash = mainHash; hash != nullptr; hash = hash->prev) { ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3313:30: note: Assuming pointer value is null /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3313:3: note: Loop condition is false. Execution continues on line 3357 for (auto hash = mainHash; hash != nullptr; hash = hash->prev) { ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3358:3: note: Loop condition is true. Entering loop body while (true) { ^ /home/user/project/build/concurrentqueue/include/concurrentqueue.h:3359:21: note: Access to field 'capacity' results in a dereference of a null pointer (loaded from variable 'mainHash') if (newCount >= (mainHash->capacity >> 1) && !implicitProducerHashResizeInProgress.test_and_set(std::memory_order_acquire)) {