@@ -2602,7 +2602,9 @@ protected function processAdditional()
26022602
26032603 $ this ->createAttributesNestingMap ();
26042604
2605- $ numTokens = count ($ this ->tokens );
2605+ $ numTokens = count ($ this ->tokens );
2606+ $ lastSeenTypeToken = $ numTokens ;
2607+
26062608 for ($ i = ($ numTokens - 1 ); $ i >= 0 ; $ i --) {
26072609 // Check for any unset scope conditions due to alternate IF/ENDIF syntax.
26082610 if (isset ($ this ->tokens [$ i ]['scope_opener ' ]) === true
@@ -3036,9 +3038,14 @@ protected function processAdditional()
30363038 continue ;
30373039 } else if ($ this ->tokens [$ i ]['code ' ] === T_BITWISE_OR
30383040 || $ this ->tokens [$ i ]['code ' ] === T_BITWISE_AND
3039- || $ this ->tokens [$ i ]['code ' ] === T_OPEN_PARENTHESIS
30403041 || $ this ->tokens [$ i ]['code ' ] === T_CLOSE_PARENTHESIS
30413042 ) {
3043+ if ($ lastSeenTypeToken < $ i ) {
3044+ // We've already examined this code to check if it is a type declaration and concluded it wasn't.
3045+ // No need to do it again.
3046+ continue ;
3047+ }
3048+
30423049 /*
30433050 Convert "|" to T_TYPE_UNION or leave as T_BITWISE_OR.
30443051 Convert "&" to T_TYPE_INTERSECTION or leave as T_BITWISE_AND.
@@ -3133,9 +3140,14 @@ protected function processAdditional()
31333140
31343141 $ typeTokenCountBefore = 0 ;
31353142 $ typeOperators = [$ i ];
3143+ $ parenthesesCount = 0 ;
31363144 $ confirmed = false ;
31373145 $ maybeNullable = null ;
31383146
3147+ if ($ this ->tokens [$ i ]['code ' ] === T_OPEN_PARENTHESIS || $ this ->tokens [$ i ]['code ' ] === T_CLOSE_PARENTHESIS ) {
3148+ ++$ parenthesesCount ;
3149+ }
3150+
31393151 for ($ x = ($ i - 1 ); $ x >= 0 ; $ x --) {
31403152 if (isset (Tokens::$ emptyTokens [$ this ->tokens [$ x ]['code ' ]]) === true ) {
31413153 continue ;
@@ -3167,7 +3179,7 @@ protected function processAdditional()
31673179 $ confirmed = true ;
31683180 break ;
31693181 } else {
3170- // This may still be an arrow function which hasn't be handled yet.
3182+ // This may still be an arrow function which hasn't been handled yet.
31713183 for ($ y = ($ x - 1 ); $ y > 0 ; $ y --) {
31723184 if (isset (Tokens::$ emptyTokens [$ this ->tokens [$ y ]['code ' ]]) === false
31733185 && $ this ->tokens [$ y ]['code ' ] !== T_BITWISE_AND
@@ -3202,11 +3214,13 @@ protected function processAdditional()
32023214 continue ;
32033215 }
32043216
3205- if ($ this ->tokens [$ x ]['code ' ] === T_BITWISE_OR
3206- || $ this ->tokens [$ x ]['code ' ] === T_BITWISE_AND
3207- || $ this ->tokens [$ x ]['code ' ] === T_OPEN_PARENTHESIS
3208- || $ this ->tokens [$ x ]['code ' ] === T_CLOSE_PARENTHESIS
3209- ) {
3217+ if ($ this ->tokens [$ x ]['code ' ] === T_BITWISE_OR || $ this ->tokens [$ x ]['code ' ] === T_BITWISE_AND ) {
3218+ $ typeOperators [] = $ x ;
3219+ continue ;
3220+ }
3221+
3222+ if ($ this ->tokens [$ x ]['code ' ] === T_OPEN_PARENTHESIS || $ this ->tokens [$ x ]['code ' ] === T_CLOSE_PARENTHESIS ) {
3223+ ++$ parenthesesCount ;
32103224 $ typeOperators [] = $ x ;
32113225 continue ;
32123226 }
@@ -3244,6 +3258,9 @@ protected function processAdditional()
32443258 break ;
32453259 }//end for
32463260
3261+ // Remember the last token we examined as part of the (non-)"type declaration".
3262+ $ lastSeenTypeToken = $ x ;
3263+
32473264 if ($ confirmed === false
32483265 && $ suspectedType === 'property or parameter '
32493266 && isset ($ this ->tokens [$ i ]['nested_parenthesis ' ]) === true
@@ -3288,8 +3305,8 @@ protected function processAdditional()
32883305 unset($ parens , $ last );
32893306 }//end if
32903307
3291- if ($ confirmed === false ) {
3292- // Not a union or intersection type after all, move on.
3308+ if ($ confirmed === false || ( $ parenthesesCount % 2 ) !== 0 ) {
3309+ // Not a (valid) union, intersection or DNF type after all, move on.
32933310 continue ;
32943311 }
32953312
0 commit comments