@@ -2918,6 +2918,100 @@ class PropertyInfo extends VariableLike
2918
2918
public bool $isDocReadonly;
2919
2919
public bool $isVirtual;
2920
2920
2921
+ // Map possible variable names to the known string constant, see
2922
+ // ZEND_KNOWN_STRINGS
2923
+ private const PHP_80_KNOWN = [
2924
+ "file" => "ZEND_STR_FILE",
2925
+ "line" => "ZEND_STR_LINE",
2926
+ "function" => "ZEND_STR_FUNCTION",
2927
+ "class" => "ZEND_STR_CLASS",
2928
+ "object" => "ZEND_STR_OBJECT",
2929
+ "type" => "ZEND_STR_TYPE",
2930
+ // ZEND_STR_OBJECT_OPERATOR and ZEND_STR_PAAMAYIM_NEKUDOTAYIM are
2931
+ // not valid variable names
2932
+ "args" => "ZEND_STR_ARGS",
2933
+ "unknown" => "ZEND_STR_UNKNOWN",
2934
+ "eval" => "ZEND_STR_EVAL",
2935
+ "include" => "ZEND_STR_INCLUDE",
2936
+ "require" => "ZEND_STR_REQUIRE",
2937
+ "include_once" => "ZEND_STR_INCLUDE_ONCE",
2938
+ "require_once" => "ZEND_STR_REQUIRE_ONCE",
2939
+ "scalar" => "ZEND_STR_SCALAR",
2940
+ "error_reporting" => "ZEND_STR_ERROR_REPORTING",
2941
+ "static" => "ZEND_STR_STATIC",
2942
+ // ZEND_STR_THIS cannot be used since $this cannot be reassigned
2943
+ "value" => "ZEND_STR_VALUE",
2944
+ "key" => "ZEND_STR_KEY",
2945
+ "__invoke" => "ZEND_STR_MAGIC_INVOKE",
2946
+ "previous" => "ZEND_STR_PREVIOUS",
2947
+ "code" => "ZEND_STR_CODE",
2948
+ "message" => "ZEND_STR_MESSAGE",
2949
+ "severity" => "ZEND_STR_SEVERITY",
2950
+ "string" => "ZEND_STR_STRING",
2951
+ "trace" => "ZEND_STR_TRACE",
2952
+ "scheme" => "ZEND_STR_SCHEME",
2953
+ "host" => "ZEND_STR_HOST",
2954
+ "port" => "ZEND_STR_PORT",
2955
+ "user" => "ZEND_STR_USER",
2956
+ "pass" => "ZEND_STR_PASS",
2957
+ "path" => "ZEND_STR_PATH",
2958
+ "query" => "ZEND_STR_QUERY",
2959
+ "fragment" => "ZEND_STR_FRAGMENT",
2960
+ "NULL" => "ZEND_STR_NULL",
2961
+ "boolean" => "ZEND_STR_BOOLEAN",
2962
+ "integer" => "ZEND_STR_INTEGER",
2963
+ "double" => "ZEND_STR_DOUBLE",
2964
+ "array" => "ZEND_STR_ARRAY",
2965
+ "resource" => "ZEND_STR_RESOURCE",
2966
+ // ZEND_STR_CLOSED_RESOURCE has a space in it
2967
+ "name" => "ZEND_STR_NAME",
2968
+ // ZEND_STR_ARGV and ZEND_STR_ARGC are superglobals that wouldn't be
2969
+ // variable names
2970
+ "Array" => "ZEND_STR_ARRAY_CAPITALIZED",
2971
+ "bool" => "ZEND_STR_BOOL",
2972
+ "int" => "ZEND_STR_INT",
2973
+ "float" => "ZEND_STR_FLOAT",
2974
+ "callable" => "ZEND_STR_CALLABLE",
2975
+ "iterable" => "ZEND_STR_ITERABLE",
2976
+ "void" => "ZEND_STR_VOID",
2977
+ "false" => "ZEND_STR_FALSE",
2978
+ "null" => "ZEND_STR_NULL_LOWERCASE",
2979
+ "mixed" => "ZEND_STR_MIXED",
2980
+ ];
2981
+
2982
+ // NEW in 8.1
2983
+ private const PHP_81_KNOWN = [
2984
+ "Unknown" => "ZEND_STR_UNKNOWN_CAPITALIZED",
2985
+ "never" => "ZEND_STR_NEVER",
2986
+ "__sleep" => "ZEND_STR_SLEEP",
2987
+ "__wakeup" => "ZEND_STR_WAKEUP",
2988
+ "cases" => "ZEND_STR_CASES",
2989
+ "from" => "ZEND_STR_FROM",
2990
+ "tryFrom" => "ZEND_STR_TRYFROM",
2991
+ "tryfrom" => "ZEND_STR_TRYFROM_LOWERCASE",
2992
+ // Omit ZEND_STR_AUTOGLOBAL_(SERVER|ENV|REQUEST)
2993
+ ];
2994
+
2995
+ // NEW in 8.2
2996
+ private const PHP_82_KNOWN = [
2997
+ "true" => "ZEND_STR_TRUE",
2998
+ "Traversable" => "ZEND_STR_TRAVERSABLE",
2999
+ "count" => "ZEND_STR_COUNT",
3000
+ "SensitiveParameter" => "ZEND_STR_SENSITIVEPARAMETER",
3001
+ ];
3002
+
3003
+ // Only new string in 8.3 is ZEND_STR_CONST_EXPR_PLACEHOLDER which is
3004
+ // not a valid variable name ("[constant expression]")
3005
+
3006
+ // NEW in 8.4
3007
+ private const PHP_84_KNOWN = [
3008
+ "exit" => "ZEND_STR_EXIT",
3009
+ "Deprecated" => "ZEND_STR_DEPRECATED_CAPITALIZED",
3010
+ "since" => "ZEND_STR_SINCE",
3011
+ "get" => "ZEND_STR_GET",
3012
+ "set" => "ZEND_STR_SET",
3013
+ ];
3014
+
2921
3015
/**
2922
3016
* @var AttributeInfo[] $attributes
2923
3017
*/
@@ -3003,8 +3097,8 @@ public function getDeclaration(array $allConstInfos): string {
3003
3097
$code .= $defaultValue->initializeZval($zvalName);
3004
3098
}
3005
3099
3006
- $code .= "\tzend_string *property_{$propertyName}_name = zend_string_init(\"$propertyName\", sizeof(\" $propertyName\") - 1, 1);\n" ;
3007
- $nameCode = "property_{$propertyName}_name" ;
3100
+ [$stringInit, $nameCode, $stringRelease] = $this->getString( $propertyName) ;
3101
+ $code .= $stringInit ;
3008
3102
3009
3103
if ($this->exposedDocComment) {
3010
3104
$commentCode = "property_{$propertyName}_comment";
@@ -3035,11 +3129,61 @@ public function getDeclaration(array $allConstInfos): string {
3035
3129
);
3036
3130
$code .= implode("", $flagsCode);
3037
3131
3038
- $code .= "\tzend_string_release(property_{$propertyName}_name);\n" ;
3132
+ $code .= $stringRelease ;
3039
3133
3040
3134
return $code;
3041
3135
}
3042
3136
3137
+ /**
3138
+ * Get an array of three strings:
3139
+ * - declaration of zend_string, if needed, or empty otherwise
3140
+ * - usage of that zend_string, or usage with ZSTR_KNOWN()
3141
+ * - freeing the zend_string, if needed
3142
+ *
3143
+ * @param string $propName
3144
+ * @return string[]
3145
+ */
3146
+ private function getString(string $propName): array {
3147
+ // Generally strings will not be known
3148
+ $nameCode = "property_{$propName}_name";
3149
+ $result = [
3150
+ "\tzend_string *$nameCode = zend_string_init(\"$propName\", sizeof(\"$propName\") - 1, 1);\n",
3151
+ $nameCode,
3152
+ "\tzend_string_release($nameCode);\n"
3153
+ ];
3154
+ // If not set, use the current latest version
3155
+ $allVersions = ALL_PHP_VERSION_IDS;
3156
+ $minPhp = $phpVersionIdMinimumCompatibility ?? end($allVersions);
3157
+ if ($minPhp < PHP_80_VERSION_ID) {
3158
+ // No known strings in 7.0
3159
+ return $result;
3160
+ }
3161
+ $include = self::PHP_80_KNOWN;
3162
+ switch ($minPhp) {
3163
+ case PHP_84_VERSION_ID:
3164
+ $include = array_merge($include, self::PHP_84_KNOWN);
3165
+ // Intentional fall through
3166
+
3167
+ case PHP_83_VERSION_ID:
3168
+ case PHP_82_VERSION_ID:
3169
+ $include = array_merge($include, self::PHP_82_KNOWN);
3170
+ // Intentional fall through
3171
+
3172
+ case PHP_81_VERSION_ID:
3173
+ $include = array_merge($include, self::PHP_81_KNOWN);
3174
+ break;
3175
+ }
3176
+ if (array_key_exists($propName,$include)) {
3177
+ $knownStr = $include[$propName];
3178
+ return [
3179
+ '',
3180
+ "ZSTR_KNOWN($knownStr)",
3181
+ '',
3182
+ ];
3183
+ }
3184
+ return $result;
3185
+ }
3186
+
3043
3187
/**
3044
3188
* @return array<int, string[]>
3045
3189
*/
0 commit comments