A millisecond setting with a unit suffix silently wraps on overflow

Aperta Adatta ai principianti
#8,381 0 commenti 0 reazioni 0 assegnatari Vedi su GitHub

I maintainer di solito rispondono entro 2 giorni

Nessuno ha ancora preso questa issue.

Valutazione

Difficoltà
2/5
Tempo stimato
1-3 ore
Idoneità per principianti
76/100
Tipo di issue
Bug
Chiarezza
Specificata chiaramente
Stato di attività
Attiva
Stack tecnologico
java
Ambito
backend

Direzione di ricerca

Inizia da core/src/main/java/io/questdb/std/Numbers.java, in parseMillis(CharSequence), dove le moltiplicazioni per unità intorno alle righe 1911, 1917 e 1938 non sono verificate. parseLongSize mostra già il controllo di overflow da copiare, e parseMicros e parseNanos richiedono la stessa revisione. Poi esegui NumbersTest con gli input elencati, che dovrebbero lanciare NumericException con "duration overflow", e verifica che i valori più grandi che rientrano continuino a essere analizzati esattamente. PropServerConfiguration.getMillis (circa righe 3522-3534) dovrebbe poi far fallire la configurazione con il nome della chiave nel messaggio.

Scritto dal modello di indicizzazione a partire dal testo della issue.

Descrizione

  • Classification: PRE-EXISTING (not introduced by PR #8159; Numbers.java is unchanged by the PR,
    the unit code dates from a4b9a7e4088, 2024-11-05). Not [security], not [crash].
  • Location: core/src/main/java/io/questdb/std/Numbers.java:1911 (val *= Dates.MINUTE_MILLIS),
    :1917 (val *= Dates.SECOND_MILLIS), :1938 (val *= Dates.HOUR_MILLIS) in
    Numbers.parseMillis(CharSequence). PropServerConfiguration.getMillis (:3522-3534) returns the
    result as is.

Problem

parseMillis checks the digit accumulation for overflow (r > val -> "duration overflow"), but
multiplies the accumulated value by its unit (m, s, h) without a check. A value whose
milliseconds do not fit a long wraps around instead of failing. Numbers.parseLongSize does check
its unit multiplication (r > val after val * 1024L), so the two parsers disagree.

Probe at HEAD 9e3e2af653 (probes/M1R3SettingProbeTest.java, Numbers.parseMillis):

input result
9223372036854775807s -1000
10000000000000000s -8446744073709551616
9223372036854775807h -3600000
153722867280913m -9223372036854771616
18446744073709552s 384
9223372036854775808 (no unit) NumericException, as expected

Impact

A server.conf or QDB_... value meant as "practically never" (for example a huge timeout with an
s or h suffix) starts the server with a negative or a small positive value instead of failing at
startup. Every millisecond setting read through getMillis is affected, for example
cairo.mat.view.refresh.busy.retry.timeout (no range check: a negative value retries at once), and
the planned cairo.view.compile.busy.retry.timeout (its "must not be negative" check catches the
negative outcomes, but 18446744073709552s would start with a 384 ms delay). Only an administrator
can set these values, and only absurd ones wrap.

Expected

parseMillis (and the same pattern in parseMicros / parseNanos, to be checked) fails with
"duration overflow" when the unit multiplication overflows, as parseLongSize does, so the server
refuses to start with ServerConfigurationException naming the key.

Suggested test

NumbersTest: parseMillis of each input above throws NumericException with "duration overflow";
the largest values that fit (9223372036854775807, 9223372036854775s, 2562047788015h) parse to
their exact products (plain Java long arithmetic is the oracle). PropServerConfigurationTest:
cairo.mat.view.refresh.busy.retry.timeout=18446744073709552s fails the configuration with the key
in the message.

Found while working on PR #8159 (branch puzpuzpuz_view_matview_fixes); the PR base cd8749a10a has the same behavior.

Lingua principale
Java
Stelle
17.5k
Fork
1.7k
Merge medio
5g 11h
PR unite (30g)
64

Preparare l'ambiente

Come iniziare

  1. Leggi tutta la issue e poi la guida ai contributi del progetto.
  2. Commenta sulla issue per dire che te ne occupi tu — evita che due persone facciano lo stesso lavoro.
  3. Fai un fork del repository e lavora su un branch.
  4. Apri una pull request che faccia riferimento al numero della issue.

Altre issue di questdb/questdb

Tutte le issue di questdb/questdb

Issue simili

Altre issue su Java

Ricevi le nuove issue nella tua casella

Un breve riepilogo di issue GitHub adatte ai principianti.