Skip to content

Commit 60d995d

Browse files
committed
Fix 0b and 0x indentifiers
1 parent c567a3f commit 60d995d

File tree

2 files changed

+18
-7
lines changed

2 files changed

+18
-7
lines changed

tests/mysql/WP_MySQL_Lexer_Tests.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -143,12 +143,14 @@ public function data_identifier_or_number(): array {
143143
// binary
144144
array( '0b01', array( WP_MySQL_Lexer::BIN_NUMBER, WP_MySQL_Lexer::EOF ) ),
145145
array( '0b01xyz', array( WP_MySQL_Lexer::IDENTIFIER, WP_MySQL_Lexer::EOF ) ), // identifier
146+
array( '0b', array( WP_MySQL_Lexer::IDENTIFIER, WP_MySQL_Lexer::EOF ) ), // identifier
146147
array( "b'01'", array( WP_MySQL_Lexer::BIN_NUMBER, WP_MySQL_Lexer::EOF ) ),
147148
array( "b'01xyz'", array( WP_MySQL_Lexer::BIN_NUMBER, WP_MySQL_Lexer::IDENTIFIER, WP_MySQL_Lexer::INVALID_INPUT, WP_MySQL_Lexer::EOF ) ),
148149

149150
// hex
150151
array( '0xab01', array( WP_MySQL_Lexer::HEX_NUMBER, WP_MySQL_Lexer::EOF ) ),
151152
array( '0xab01xyz', array( WP_MySQL_Lexer::IDENTIFIER, WP_MySQL_Lexer::EOF ) ), // identifier
153+
array( '0x', array( WP_MySQL_Lexer::IDENTIFIER, WP_MySQL_Lexer::EOF ) ), // identifier
152154
array( "x'ab01'", array( WP_MySQL_Lexer::HEX_NUMBER, WP_MySQL_Lexer::EOF ) ),
153155
array( "x'ab01xyz'", array( WP_MySQL_Lexer::HEX_NUMBER, WP_MySQL_Lexer::IDENTIFIER, WP_MySQL_Lexer::INVALID_INPUT, WP_MySQL_Lexer::EOF ) ),
154156

wp-includes/mysql/class-wp-mysql-lexer.php

Lines changed: 16 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,7 @@ class WP_MySQL_Lexer {
4141
*/
4242
const WHITESPACE_MASK = " \t\n\r\f";
4343
const DIGIT_MASK = '0123456789';
44+
const HEX_DIGIT_MASK = '0123456789abcdefABCDEF';
4445

4546
/**
4647
* Tokens from the MySQL Workbench "predefined.tokens" list.
@@ -2480,8 +2481,6 @@ private function read_next_token(): int {
24802481
} elseif ( null !== $byte && strspn( $byte, self::WHITESPACE_MASK ) > 0 ) {
24812482
$this->bytes_already_read += strspn( $this->sql, self::WHITESPACE_MASK, $this->bytes_already_read );
24822483
$type = self::WHITESPACE;
2483-
} elseif ( '0' === $byte && ( 'x' === $next_byte || 'b' === $next_byte ) ) {
2484-
$type = $this->read_number();
24852484
} elseif ( ( 'x' === $byte || 'X' === $byte || 'b' === $byte || 'B' === $byte ) && "'" === $next_byte ) {
24862485
$type = $this->read_number();
24872486
} elseif ( ( 'n' === $byte || 'N' === $byte ) && "'" === $next_byte ) {
@@ -2597,25 +2596,35 @@ private function read_identifier(): int {
25972596
private function read_number(): int {
25982597
// @TODO: Support numeric-only identifier parts after "." (e.g., 1ea10.1).
25992598

2600-
$byte = $this->sql[ $this->bytes_already_read ] ?? null;
2601-
$next_byte = $this->sql[ $this->bytes_already_read + 1 ] ?? null;
2599+
$byte = $this->sql[ $this->bytes_already_read ] ?? null;
2600+
$next_byte = $this->sql[ $this->bytes_already_read + 1 ] ?? null;
2601+
$third_byte = $this->sql[ $this->bytes_already_read + 2 ] ?? null;
26022602

26032603
if (
26042604
// HEX number in the form of 0xN.
2605-
( '0' === $byte && 'x' === $next_byte )
2605+
(
2606+
'0' === $byte
2607+
&& 'x' === $next_byte
2608+
&& null !== $third_byte
2609+
&& strspn( $third_byte, self::HEX_DIGIT_MASK ) > 0
2610+
)
26062611
// HEX number in the form of x'N' or X'N'.
26072612
|| ( ( 'x' === $byte || 'X' === $byte ) && "'" === $next_byte )
26082613
) {
26092614
$is_quoted = "'" === $next_byte;
26102615
$this->bytes_already_read += 2; // Consume "0x" or "x'".
2611-
$this->bytes_already_read += strspn( $this->sql, '0123456789abcdefABCDEF', $this->bytes_already_read );
2616+
$this->bytes_already_read += strspn( $this->sql, self::HEX_DIGIT_MASK, $this->bytes_already_read );
26122617
if ( $is_quoted ) {
26132618
$this->bytes_already_read += 1; // Consume the "'".
26142619
}
26152620
$type = self::HEX_NUMBER;
26162621
} elseif (
26172622
// BIN number in the form of 0bN.
2618-
( '0' === $byte && 'b' === $next_byte )
2623+
(
2624+
'0' === $byte
2625+
&& 'b' === $next_byte
2626+
&& ( '0' === $third_byte || '1' === $third_byte )
2627+
)
26192628
// BIN number in the form of b'N' or B'N'.
26202629
|| ( ( 'b' === $byte || 'B' === $byte ) && "'" === $next_byte )
26212630
) {

0 commit comments

Comments
 (0)