CVE-2022-41896 (C++, published 2022-11-18T22:15Z)
Description: value: TensorFlow is an open source platform for machine learning. If `ThreadUnsafeUnigramCandidateSampler` is given input `filterbank_channel_count` greater than the allowed max size, TensorFlow will crash. We have patched the issue in GitHub commit 39ec7eaf1428e90c37787e5b3fbd68ebd3c48860. The fix will be included in TensorFlow 2.11. We will also cherrypick this commit on TensorFlow 2.10.1, 2.9.3, and TensorFlow 2.8.4, as these are also affected and still in supported range.
Severity: nan (CVSS v3 base score: 7.5)
Weakness: CWE-1284 \u2014 Improper Validation of Specified Quantity in Input
The product receives input that is expected to specify a quantity (such as size or length), but it does not validate or incorrectly validates that the quantity has the required properties.
Repository: https://github.com/tensorflow/tensorflow
Files changed:
tensorflow/core/kernels/mfcc.cc
tensorflow/core/kernels/mfcc_mel_filterbank.cc
tensorflow/core/kernels/mfcc_mel_filterbank_test.cc
tensorflow/core/kernels/mfcc_op.cc
Commit message: Make MfccMelFilterbank fail initialization if num_channels is > max int value.

Also initialize MfccDct only if MfccMelFilterbank initialization was successful.

PiperOrigin-RevId: 477844246


Vulnerable code:
  initialized &=
      dct_.Initialize(filterbank_channel_count_, dct_coefficient_count_);
  center_frequencies_.resize(num_channels_ + 1);
// Create a speech fingerpring from spectrogram data.
    OP_REQUIRES(context, mfcc.Initialize(spectrogram_channels, sample_rate),
                errors::InvalidArgument(
                    "Mfcc initialization failed for channel count ",
                    spectrogram_channels, " and sample rate ", sample_rate));

Fixed code:
  if (initialized) {
    initialized =
        dct_.Initialize(filterbank_channel_count_, dct_coefficient_count_);
  }
#include <limits>

  std::size_t center_frequencies_size = std::size_t(num_channels_) + 1;
  if (center_frequencies_size >= std::numeric_limits<int>::max() ||
      center_frequencies_size > center_frequencies_.max_size()) {
    LOG(ERROR) << "Number of filterbank channels must be less than "
               << std::numeric_limits<int>::max()
               << " and less than or equal to "
               << center_frequencies_.max_size();
    return false;
  }
  center_frequencies_.resize(center_frequencies_size);

#include <limits>
TEST(MfccMelFilterbankTest, FailsWhenChannelsGreaterThanMaxIntValue) {
  // Test for bug where vector throws a length_error when it suspects the size
  // to be more than it's max_size. For now, we fail initialization when the
  // number of requested channels is >= the maximum value int can take (since
  // num_channels_ is an int).
  MfccMelFilterbank filterbank;

  const int kSampleCount = 513;
  std::size_t num_channels = std::numeric_limits<int>::max();
  bool initialized = filterbank.Initialize(
      kSampleCount, 2 /* sample rate */, num_channels /* channels */,
      1.0 /*  lower frequency limit */, 5.0 /* upper frequency limit */);

  EXPECT_FALSE(initialized);
}

TEST(MfccMelFilterbankTest, FailsWhenChannelsGreaterThanMaxSize) {
  // Test for bug where vector throws a length_error when it suspects the size
  // to be more than it's max_size. For now, we fail initialization when the
  // number of requested channels is > than std::vector<double>::max_size().
  MfccMelFilterbank filterbank;

  const int kSampleCount = 513;
  // Set num_channels to exceed the max_size a double vector can
  // theoretically take.
  std::size_t num_channels = std::vector<double>().max_size() + 1;
  bool initialized = filterbank.Initialize(
      kSampleCount, 2 /* sample rate */, num_channels /* channels */,
      1.0 /*  lower frequency limit */, 5.0 /* upper frequency limit */);

  EXPECT_FALSE(initialized);
}

// Create a speech fingerprint from spectrogram data.
    OP_REQUIRES(
        context, mfcc.Initialize(spectrogram_channels, sample_rate),
        errors::InvalidArgument("Mfcc initialization failed for channel count ",
                                spectrogram_channels, ", sample rate ",
                                sample_rate, " and filterbank_channel_count ",
                                filterbank_channel_count_));