Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Overflow in negate operator #11084

Merged
merged 6 commits into from
Jun 26, 2024
Merged

Overflow in negate operator #11084

merged 6 commits into from
Jun 26, 2024

Conversation

LorrensP-2158466
Copy link
Contributor

Which issue does this PR close?

Closes #11076. Tracking: #11078

Rationale for this change

What changes are included in this PR?

Doing checked negations on scalarValue

Are these changes tested?

With unit tests yes

Are there any user-facing changes?

no

Copy link
Contributor

@alamb alamb left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you @LorrensP-2158466 -- this looks good to me except for creating error messags on each row.

let val = IntervalDayTimeType::make_value(
neg_checked_with_ctx(
days,
format!("In negation of days {days} in IntervalDayTime"),
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think that calling these functions like this will result in actually creating these error strings for each row, even if there is no error -- I think it is important to avoid that overhead.

I suspect it would be faster to use map_err like

let days = v.neg_checked()
  .map_err(|e| {
    DataFusionError::from(e)
      .context(format!("In negation of milliseconds {ms} in IntervalDayTime")))
  })?

The reason being that in that formulation the format! is part of a closure that is only called when there is an actual error

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, I first tried that, but I didn't like repeating the same thing for every case. But this went over my head, I'll fix this back to map_err. Thanks for the tip!

(f64::MAX.into(), f64::MIN.into()),
];
// skip float 16 because they aren't supported
for (test, expected) in float_cases.into_iter().skip(2) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

maybe we just shouldn't list float 16 at all 🤔 I think it might be more confusing to see them listed then skipped than simply not listed (or listed in a separate test that simply fails)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah I did this when filing #11083. Maybe it's cleaner to add a test that should fail on Float16 and when Float16 is supported, that test fails and the person making those changes knows to change the test.

Copy link
Contributor

@alamb alamb left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👨‍🍳 👌 @LorrensP-2158466 -- very nice. Thank you for this improvement

@alamb alamb merged commit ec3c71d into apache:main Jun 26, 2024
23 checks passed
@LorrensP-2158466 LorrensP-2158466 deleted the overflow-in-negate-operator branch June 26, 2024 16:16
findepi pushed a commit to findepi/datafusion that referenced this pull request Jul 16, 2024
* Do checked negative op instead of unchecked

* add tests for checking if overflow error occurs

* add context to negating complexer ScalarValues

* put format! call to create error message in closure

* seperate test case for f16 that should panic with not implemented
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Overflow bug in negate arithmetic operator (found by SQLancer)
2 participants