| 191 | } // namespace |
| 192 | |
| 193 | Status FuzzReader(const uint8_t* data, int64_t size) { |
| 194 | Status st; |
| 195 | |
| 196 | auto buffer = std::make_shared<::arrow::Buffer>(data, size); |
| 197 | auto file = std::make_shared<::arrow::io::BufferReader>(buffer); |
| 198 | auto pool = ::arrow::internal::fuzzing_memory_pool(); |
| 199 | auto reader_properties = MakeFuzzReaderProperties(pool); |
| 200 | |
| 201 | std::default_random_engine rng(/*seed*/ 42); |
| 202 | |
| 203 | // Read Parquet file metadata only once, which will reduce iteration time slightly |
| 204 | std::shared_ptr<FileMetaData> pq_md; |
| 205 | BEGIN_PARQUET_CATCH_EXCEPTIONS { |
| 206 | int num_row_groups, num_columns; |
| 207 | auto pq_file_reader = ParquetFileReader::Open(file, reader_properties); |
| 208 | { |
| 209 | // Read some additional metadata (often lazy-decoded, such as statistics) |
| 210 | pq_md = pq_file_reader->metadata(); |
| 211 | num_row_groups = pq_md->num_row_groups(); |
| 212 | num_columns = pq_md->num_columns(); |
| 213 | for (int i = 0; i < num_row_groups; ++i) { |
| 214 | auto rg = pq_md->RowGroup(i); |
| 215 | rg->sorting_columns(); |
| 216 | for (int j = 0; j < num_columns; ++j) { |
| 217 | auto col = rg->ColumnChunk(j); |
| 218 | col->encoded_statistics(); |
| 219 | col->statistics(); |
| 220 | col->geo_statistics(); |
| 221 | col->size_statistics(); |
| 222 | col->key_value_metadata(); |
| 223 | col->encodings(); |
| 224 | col->encoding_stats(); |
| 225 | } |
| 226 | } |
| 227 | } |
| 228 | { |
| 229 | // Read and decode bloom filters |
| 230 | auto& bloom_reader = pq_file_reader->GetBloomFilterReader(); |
| 231 | std::uniform_int_distribution<uint64_t> hash_dist; |
| 232 | for (int i = 0; i < num_row_groups; ++i) { |
| 233 | auto bloom_rg = bloom_reader.RowGroup(i); |
| 234 | for (int j = 0; j < num_columns; ++j) { |
| 235 | st &= FuzzReadBloomFilter(bloom_rg.get(), j, hash_dist, rng); |
| 236 | } |
| 237 | } |
| 238 | } |
| 239 | { |
| 240 | // Read and decode page indexes |
| 241 | auto index_reader = pq_file_reader->GetPageIndexReader(); |
| 242 | for (int i = 0; i < num_row_groups; ++i) { |
| 243 | auto index_rg = index_reader->RowGroup(i); |
| 244 | if (index_rg) { |
| 245 | for (int j = 0; j < num_columns; ++j) { |
| 246 | st &= FuzzReadPageIndex(index_rg.get(), pq_md->schema(), j); |
| 247 | } |
| 248 | } |
| 249 | } |
| 250 | } |