geoHeil opened a new issue, #27004:
URL: https://github.com/apache/datafusion/issues/27004

   ### Describe the bug
   
   `datafusion-proto-common`'s `from_proto` conversions panic at four sites 
when a peer sends input that a well-formed encoder never produces. Nearby code 
returns an error in the same situations.
   
   1. **Decimal scalar value of the wrong length.** `Decimal32Value`, 
`Decimal64Value`, `Decimal128Value` and `Decimal256Value` pass their `value` 
bytes to `vec_to_array`, which panics when the length is not the width:
   
      
https://github.com/apache/datafusion/blob/636590bf4f4b4f792d3f2fdacedc5fee0ba54950/datafusion/proto-common/src/from_proto/mod.rs#L552-L568
      
https://github.com/apache/datafusion/blob/636590bf4f4b4f792d3f2fdacedc5fee0ba54950/datafusion/proto-common/src/from_proto/mod.rs#L1421-L1425
   
   2. **Nested scalar whose batch disagrees with its kind.** The nested 
`ScalarValue` arm decodes an IPC batch, then calls `record_batch.column(0)`, 
which panics on a zero-field schema. It then calls `as_list` / 
`as_fixed_size_list` / `as_list_view` / `as_struct` / `as_map`, which panic 
when the column is not the type the value kind names:
   
      
https://github.com/apache/datafusion/blob/636590bf4f4b4f792d3f2fdacedc5fee0ba54950/datafusion/proto-common/src/from_proto/mod.rs#L523-L544
   
   3. **Union with more than 128 fields and no `type_ids`.** 
`UnionFields::from_fields` panics with `"UnionFields cannot contain more than 
128 fields"`. The `else` branch just below calls `UnionFields::try_new` and 
maps its error. `UnionFields::try_from_fields` is the non-panicking equivalent:
   
      
https://github.com/apache/datafusion/blob/636590bf4f4b4f792d3f2fdacedc5fee0ba54950/datafusion/proto-common/src/from_proto/mod.rs#L319-L325
   
   4. **CSV options with an empty `delimiter` or `quote`.** These are indexed 
with `[0]`:
   
      
https://github.com/apache/datafusion/blob/636590bf4f4b4f792d3f2fdacedc5fee0ba54950/datafusion/proto-common/src/from_proto/mod.rs#L1129-L1130
   
   The same code is in 55.1.0, at `src/from_proto/mod.rs` lines 549-565 and 
1256, 521-541, 323, and 1009-1010.
   
   ### To Reproduce
   
   Decode a physical plan with 
`datafusion_proto::bytes::physical_plan_from_bytes` (or a `ScalarValue` / 
`Schema` with `TryFrom`), where the input contains one of:
   
   1. a `Decimal32Value` literal whose `value` is 3 bytes long;
   2. a `ListValue` literal whose IPC batch holds a single `Int32` column;
   3. a schema with a `Union` field of 129 children and an empty `type_ids`;
   4. `CsvOptions` with an empty `delimiter`.
   
   **What we observed, and what we did not.** We decode plan stages from peers, 
so we keep a patched copy of 55.1.0 in which each site returns an error. In our 
CI, inputs 1-3 reach their sites in that copy and get the error placed there. A 
test pins each error message, and a mutation of that message makes the test 
fail. We have not run the unpatched crate on these inputs. The panics above are 
the documented behaviour of the callees (`vec_to_array`'s own `panic!`, 
`as_list`'s "panicking if not possible", `from_fields`'s `expect`). Input 4 has 
no test on our side.
   
   ### Expected behavior
   
   Each site returns `Err` naming the bad field: `as_*_opt` accessors for site 
2, `UnionFields::try_from_fields` for site 3, and `.first().ok_or_else(..)` for 
site 4. The caller can then refuse the plan and keep running.
   
   ### Additional context
   
   This matters wherever a process decodes plans it did not encode itself, such 
as a distributed worker that receives plan stages from peers. Under `panic = 
"abort"`, one malformed message stops the whole process. #24726 fixed the same 
class of problem for `Constraint` and `TableParquetOptions`. #26998 and #26999 
are related cases in `datafusion-proto` and `datafusion-physical-plan`.
   
   The patch is small and each site has a decode test. I can open a PR if that 
is welcome.
   


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to