re2 1.24.1 → 1.25.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (370) hide show
  1. package/LICENSE +15 -20
  2. package/README.md +62 -4
  3. package/binding.gyp +1 -2
  4. package/lib/addon.cc +7 -3
  5. package/lib/exec.cc +4 -4
  6. package/lib/match.cc +4 -4
  7. package/lib/pattern.cc +148 -1
  8. package/lib/replace.cc +5 -4
  9. package/lib/search.cc +1 -1
  10. package/lib/set.cc +75 -0
  11. package/lib/test.cc +1 -1
  12. package/lib/unicode_properties.h +15840 -0
  13. package/lib/wrapped_re2.h +11 -4
  14. package/lib/wrapped_re2_set.h +3 -1
  15. package/llms-full.txt +37 -7
  16. package/llms.txt +4 -1
  17. package/package.json +11 -10
  18. package/re2.d.ts +2 -0
  19. package/vendor/abseil-cpp/CMake/AbseilDll.cmake +87 -74
  20. package/vendor/abseil-cpp/CMakeLists.txt +3 -3
  21. package/vendor/abseil-cpp/FAQ.md +130 -79
  22. package/vendor/abseil-cpp/MODULE.bazel +6 -7
  23. package/vendor/abseil-cpp/absl/BUILD.bazel +6 -0
  24. package/vendor/abseil-cpp/absl/algorithm/BUILD.bazel +4 -0
  25. package/vendor/abseil-cpp/absl/algorithm/CMakeLists.txt +4 -0
  26. package/vendor/abseil-cpp/absl/algorithm/algorithm.h +34 -2
  27. package/vendor/abseil-cpp/absl/algorithm/container.h +164 -17
  28. package/vendor/abseil-cpp/absl/algorithm/container_test.cc +390 -13
  29. package/vendor/abseil-cpp/absl/base/BUILD.bazel +53 -6
  30. package/vendor/abseil-cpp/absl/base/CMakeLists.txt +28 -4
  31. package/vendor/abseil-cpp/absl/base/attributes.h +61 -42
  32. package/vendor/abseil-cpp/absl/base/call_once.h +1 -0
  33. package/vendor/abseil-cpp/absl/base/casts.h +8 -1
  34. package/vendor/abseil-cpp/absl/base/casts_test.cc +3 -6
  35. package/vendor/abseil-cpp/absl/base/config.h +54 -10
  36. package/vendor/abseil-cpp/absl/base/exception_safety_testing_test.cc +9 -9
  37. package/vendor/abseil-cpp/absl/base/fast_type_id.h +30 -2
  38. package/vendor/abseil-cpp/absl/base/fast_type_id_test.cc +3 -0
  39. package/vendor/abseil-cpp/absl/base/internal/exception_safety_testing.h +15 -12
  40. package/vendor/abseil-cpp/absl/base/internal/hardening.h +136 -0
  41. package/vendor/abseil-cpp/absl/base/internal/hardening_test.cc +168 -0
  42. package/vendor/abseil-cpp/absl/base/internal/iterator_traits.h +2 -2
  43. package/vendor/abseil-cpp/absl/base/internal/low_level_alloc.cc +6 -0
  44. package/vendor/abseil-cpp/absl/base/internal/low_level_scheduling.h +77 -15
  45. package/vendor/abseil-cpp/absl/base/internal/sysinfo.cc +1 -2
  46. package/vendor/abseil-cpp/absl/base/internal/thread_identity.h +52 -0
  47. package/vendor/abseil-cpp/absl/base/internal/unscaledcycleclock.h +5 -0
  48. package/vendor/abseil-cpp/absl/base/macros.h +36 -20
  49. package/vendor/abseil-cpp/absl/base/nullability.h +4 -3
  50. package/vendor/abseil-cpp/absl/base/optimization.h +3 -2
  51. package/vendor/abseil-cpp/absl/base/optimization_test.cc +4 -3
  52. package/vendor/abseil-cpp/absl/base/options.h +55 -1
  53. package/vendor/abseil-cpp/absl/base/policy_checks.h +5 -5
  54. package/vendor/abseil-cpp/absl/base/{internal/throw_delegate.cc → throw_delegate.cc} +9 -7
  55. package/vendor/abseil-cpp/absl/base/{internal/throw_delegate.h → throw_delegate.h} +4 -14
  56. package/vendor/abseil-cpp/absl/base/throw_delegate_test.cc +19 -28
  57. package/vendor/abseil-cpp/absl/cleanup/BUILD.bazel +2 -0
  58. package/vendor/abseil-cpp/absl/cleanup/CMakeLists.txt +2 -0
  59. package/vendor/abseil-cpp/absl/cleanup/cleanup.h +3 -2
  60. package/vendor/abseil-cpp/absl/cleanup/internal/cleanup.h +3 -2
  61. package/vendor/abseil-cpp/absl/container/BUILD.bazel +19 -7
  62. package/vendor/abseil-cpp/absl/container/CMakeLists.txt +6 -5
  63. package/vendor/abseil-cpp/absl/container/btree_benchmark.cc +3 -5
  64. package/vendor/abseil-cpp/absl/container/btree_set.h +5 -5
  65. package/vendor/abseil-cpp/absl/container/btree_test.cc +11 -14
  66. package/vendor/abseil-cpp/absl/container/chunked_queue.h +8 -6
  67. package/vendor/abseil-cpp/absl/container/chunked_queue_test.cc +5 -5
  68. package/vendor/abseil-cpp/absl/container/fixed_array.h +14 -13
  69. package/vendor/abseil-cpp/absl/container/fixed_array_test.cc +3 -3
  70. package/vendor/abseil-cpp/absl/container/flat_hash_map.h +18 -6
  71. package/vendor/abseil-cpp/absl/container/flat_hash_map_test.cc +34 -1
  72. package/vendor/abseil-cpp/absl/container/flat_hash_set.h +21 -7
  73. package/vendor/abseil-cpp/absl/container/flat_hash_set_test.cc +39 -7
  74. package/vendor/abseil-cpp/absl/container/inlined_vector.h +29 -29
  75. package/vendor/abseil-cpp/absl/container/inlined_vector_test.cc +2 -2
  76. package/vendor/abseil-cpp/absl/container/internal/btree.h +32 -24
  77. package/vendor/abseil-cpp/absl/container/internal/btree_container.h +16 -17
  78. package/vendor/abseil-cpp/absl/container/internal/common.h +6 -5
  79. package/vendor/abseil-cpp/absl/container/internal/common_policy_traits.h +1 -1
  80. package/vendor/abseil-cpp/absl/container/internal/compressed_tuple.h +16 -16
  81. package/vendor/abseil-cpp/absl/container/internal/compressed_tuple_test.cc +13 -13
  82. package/vendor/abseil-cpp/absl/container/internal/container_memory.h +41 -31
  83. package/vendor/abseil-cpp/absl/container/internal/hash_function_defaults.h +2 -2
  84. package/vendor/abseil-cpp/absl/container/internal/hash_generator_testing.h +4 -4
  85. package/vendor/abseil-cpp/absl/container/internal/hash_policy_traits.h +3 -3
  86. package/vendor/abseil-cpp/absl/container/internal/hashtable_control_bytes.h +27 -19
  87. package/vendor/abseil-cpp/absl/container/internal/hashtablez_sampler.cc +2 -2
  88. package/vendor/abseil-cpp/absl/container/internal/hashtablez_sampler.h +0 -17
  89. package/vendor/abseil-cpp/absl/container/internal/hashtablez_sampler_test.cc +12 -30
  90. package/vendor/abseil-cpp/absl/container/internal/inlined_vector.h +28 -28
  91. package/vendor/abseil-cpp/absl/container/internal/layout.h +13 -13
  92. package/vendor/abseil-cpp/absl/container/internal/layout_test.cc +3 -2
  93. package/vendor/abseil-cpp/absl/container/internal/raw_hash_map.h +60 -62
  94. package/vendor/abseil-cpp/absl/container/internal/raw_hash_set.cc +59 -39
  95. package/vendor/abseil-cpp/absl/container/internal/raw_hash_set.h +619 -326
  96. package/vendor/abseil-cpp/absl/container/internal/raw_hash_set_benchmark.cc +25 -2
  97. package/vendor/abseil-cpp/absl/container/internal/raw_hash_set_probe_benchmark.cc +4 -4
  98. package/vendor/abseil-cpp/absl/container/internal/raw_hash_set_test.cc +575 -159
  99. package/vendor/abseil-cpp/absl/container/linked_hash_map.h +2 -2
  100. package/vendor/abseil-cpp/absl/container/node_hash_map.h +27 -15
  101. package/vendor/abseil-cpp/absl/container/node_hash_map_test.cc +34 -0
  102. package/vendor/abseil-cpp/absl/container/node_hash_set.h +25 -11
  103. package/vendor/abseil-cpp/absl/container/node_hash_set_test.cc +39 -7
  104. package/vendor/abseil-cpp/absl/container/sample_element_size_test.cc +7 -4
  105. package/vendor/abseil-cpp/absl/crc/BUILD.bazel +0 -1
  106. package/vendor/abseil-cpp/absl/crc/CMakeLists.txt +2 -3
  107. package/vendor/abseil-cpp/absl/crc/crc32c_benchmark.cc +2 -1
  108. package/vendor/abseil-cpp/absl/crc/internal/cpu_detect.cc +6 -6
  109. package/vendor/abseil-cpp/absl/crc/internal/crc.cc +4 -6
  110. package/vendor/abseil-cpp/absl/crc/internal/crc32_x86_arm_combined_simd.h +41 -0
  111. package/vendor/abseil-cpp/absl/crc/internal/crc_internal.h +0 -16
  112. package/vendor/abseil-cpp/absl/crc/internal/crc_x86_arm_combined.cc +143 -81
  113. package/vendor/abseil-cpp/absl/debugging/BUILD.bazel +9 -31
  114. package/vendor/abseil-cpp/absl/debugging/CMakeLists.txt +3 -33
  115. package/vendor/abseil-cpp/absl/debugging/internal/demangle_rust.h +8 -0
  116. package/vendor/abseil-cpp/absl/debugging/internal/demangle_test.cc +2 -1
  117. package/vendor/abseil-cpp/absl/debugging/internal/examine_stack.cc +12 -2
  118. package/vendor/abseil-cpp/absl/debugging/internal/examine_stack.h +2 -3
  119. package/vendor/abseil-cpp/absl/debugging/internal/stacktrace_aarch64-inl.inc +11 -0
  120. package/vendor/abseil-cpp/absl/debugging/internal/stacktrace_emscripten-inl.inc +13 -4
  121. package/vendor/abseil-cpp/absl/debugging/internal/stacktrace_generic-inl.inc +14 -7
  122. package/vendor/abseil-cpp/absl/debugging/internal/stacktrace_riscv-inl.inc +4 -0
  123. package/vendor/abseil-cpp/absl/debugging/internal/symbolize.h +46 -36
  124. package/vendor/abseil-cpp/absl/debugging/stacktrace.cc +18 -58
  125. package/vendor/abseil-cpp/absl/debugging/stacktrace.h +5 -48
  126. package/vendor/abseil-cpp/absl/debugging/stacktrace_test.cc +10 -124
  127. package/vendor/abseil-cpp/absl/debugging/symbolize.cc +20 -2
  128. package/vendor/abseil-cpp/absl/debugging/symbolize_elf.inc +58 -106
  129. package/vendor/abseil-cpp/absl/debugging/symbolize_test.cc +37 -36
  130. package/vendor/abseil-cpp/absl/debugging/symbolize_unimplemented.inc +4 -4
  131. package/vendor/abseil-cpp/absl/flags/BUILD.bazel +6 -3
  132. package/vendor/abseil-cpp/absl/flags/CMakeLists.txt +1 -1
  133. package/vendor/abseil-cpp/absl/flags/commandlineflag.h +8 -6
  134. package/vendor/abseil-cpp/absl/flags/commandlineflag_test.cc +1 -1
  135. package/vendor/abseil-cpp/absl/flags/flag_benchmark.cc +5 -5
  136. package/vendor/abseil-cpp/absl/flags/flag_test.cc +30 -30
  137. package/vendor/abseil-cpp/absl/flags/internal/flag.cc +4 -4
  138. package/vendor/abseil-cpp/absl/flags/internal/flag.h +6 -6
  139. package/vendor/abseil-cpp/absl/flags/marshalling.h +2 -28
  140. package/vendor/abseil-cpp/absl/flags/marshalling_test.cc +12 -11
  141. package/vendor/abseil-cpp/absl/flags/reflection_test.cc +1 -1
  142. package/vendor/abseil-cpp/absl/functional/BUILD.bazel +26 -1
  143. package/vendor/abseil-cpp/absl/functional/CMakeLists.txt +29 -1
  144. package/vendor/abseil-cpp/absl/functional/any_invocable.h +13 -14
  145. package/vendor/abseil-cpp/absl/functional/any_invocable_test.cc +46 -47
  146. package/vendor/abseil-cpp/absl/functional/bind_back.h +79 -0
  147. package/vendor/abseil-cpp/absl/functional/bind_back_test.cc +237 -0
  148. package/vendor/abseil-cpp/absl/functional/bind_front.h +7 -1
  149. package/vendor/abseil-cpp/absl/functional/bind_front_test.cc +4 -4
  150. package/vendor/abseil-cpp/absl/functional/function_ref_test.cc +2 -2
  151. package/vendor/abseil-cpp/absl/functional/internal/any_invocable.h +28 -28
  152. package/vendor/abseil-cpp/absl/functional/internal/back_binder.h +95 -0
  153. package/vendor/abseil-cpp/absl/functional/internal/front_binder.h +4 -4
  154. package/vendor/abseil-cpp/absl/functional/internal/function_ref.h +2 -2
  155. package/vendor/abseil-cpp/absl/functional/overload_test.cc +13 -13
  156. package/vendor/abseil-cpp/absl/hash/BUILD.bazel +1 -2
  157. package/vendor/abseil-cpp/absl/hash/CMakeLists.txt +1 -2
  158. package/vendor/abseil-cpp/absl/hash/hash.h +1 -1
  159. package/vendor/abseil-cpp/absl/hash/hash_test.cc +14 -20
  160. package/vendor/abseil-cpp/absl/hash/hash_testing.h +11 -9
  161. package/vendor/abseil-cpp/absl/hash/internal/city.cc +39 -51
  162. package/vendor/abseil-cpp/absl/hash/internal/hash.cc +165 -47
  163. package/vendor/abseil-cpp/absl/hash/internal/hash.h +82 -26
  164. package/vendor/abseil-cpp/absl/hash/internal/low_level_hash_test.cc +36 -1
  165. package/vendor/abseil-cpp/absl/hash/internal/spy_hash_state.h +8 -5
  166. package/vendor/abseil-cpp/absl/log/BUILD.bazel +5 -2
  167. package/vendor/abseil-cpp/absl/log/CMakeLists.txt +5 -3
  168. package/vendor/abseil-cpp/absl/log/absl_vlog_is_on.h +0 -2
  169. package/vendor/abseil-cpp/absl/log/internal/BUILD.bazel +15 -1
  170. package/vendor/abseil-cpp/absl/log/internal/log_message.cc +5 -4
  171. package/vendor/abseil-cpp/absl/log/internal/log_message.h +14 -0
  172. package/vendor/abseil-cpp/absl/log/internal/nullstream.h +1 -1
  173. package/vendor/abseil-cpp/absl/log/internal/proto.cc +13 -0
  174. package/vendor/abseil-cpp/absl/log/internal/structured_proto.cc +5 -5
  175. package/vendor/abseil-cpp/absl/log/internal/structured_proto.h +6 -5
  176. package/vendor/abseil-cpp/absl/log/internal/structured_proto_test.cc +3 -3
  177. package/vendor/abseil-cpp/absl/log/internal/vlog_config.cc +2 -2
  178. package/vendor/abseil-cpp/absl/log/internal/vlog_config_benchmark.cc +3 -3
  179. package/vendor/abseil-cpp/absl/log/log_format_test.cc +19 -2
  180. package/vendor/abseil-cpp/absl/log/log_modifier_methods_test.cc +18 -0
  181. package/vendor/abseil-cpp/absl/log/log_streamer.h +29 -2
  182. package/vendor/abseil-cpp/absl/log/log_streamer_test.cc +18 -0
  183. package/vendor/abseil-cpp/absl/log/scoped_mock_log_test.cc +1 -1
  184. package/vendor/abseil-cpp/absl/log/vlog_is_on.h +0 -2
  185. package/vendor/abseil-cpp/absl/log/vlog_is_on_test.cc +6 -5
  186. package/vendor/abseil-cpp/absl/memory/memory.h +55 -5
  187. package/vendor/abseil-cpp/absl/memory/memory_test.cc +55 -1
  188. package/vendor/abseil-cpp/absl/meta/BUILD.bazel +2 -0
  189. package/vendor/abseil-cpp/absl/meta/internal/requires.h +1 -1
  190. package/vendor/abseil-cpp/absl/meta/type_traits.h +119 -55
  191. package/vendor/abseil-cpp/absl/meta/type_traits_test.cc +7 -7
  192. package/vendor/abseil-cpp/absl/numeric/int128_test.cc +6 -6
  193. package/vendor/abseil-cpp/absl/profiling/BUILD.bazel +3 -1
  194. package/vendor/abseil-cpp/absl/profiling/hashtable.cc +0 -4
  195. package/vendor/abseil-cpp/absl/profiling/internal/profile_builder.cc +32 -33
  196. package/vendor/abseil-cpp/absl/profiling/internal/profile_builder.h +25 -2
  197. package/vendor/abseil-cpp/absl/profiling/internal/sample_recorder_test.cc +8 -5
  198. package/vendor/abseil-cpp/absl/random/BUILD.bazel +13 -1
  199. package/vendor/abseil-cpp/absl/random/CMakeLists.txt +23 -2
  200. package/vendor/abseil-cpp/absl/random/benchmarks.cc +1 -1
  201. package/vendor/abseil-cpp/absl/random/beta_distribution.h +2 -2
  202. package/vendor/abseil-cpp/absl/random/bit_gen_ref.h +26 -53
  203. package/vendor/abseil-cpp/absl/random/bit_gen_ref_test.cc +43 -0
  204. package/vendor/abseil-cpp/absl/random/discrete_distribution.h +1 -1
  205. package/vendor/abseil-cpp/absl/random/distributions.h +17 -17
  206. package/vendor/abseil-cpp/absl/random/distributions_test.cc +4 -4
  207. package/vendor/abseil-cpp/absl/random/exponential_distribution.h +1 -1
  208. package/vendor/abseil-cpp/absl/random/internal/BUILD.bazel +4 -2
  209. package/vendor/abseil-cpp/absl/random/internal/distribution_caller.h +8 -21
  210. package/vendor/abseil-cpp/absl/random/internal/fast_uniform_bits.h +1 -1
  211. package/vendor/abseil-cpp/absl/random/internal/generate_real.h +1 -1
  212. package/vendor/abseil-cpp/absl/random/internal/iostream_state_saver.h +2 -2
  213. package/vendor/abseil-cpp/absl/random/internal/iostream_state_saver_test.cc +3 -2
  214. package/vendor/abseil-cpp/absl/random/internal/mock_helpers.h +14 -40
  215. package/vendor/abseil-cpp/absl/random/internal/nonsecure_base.h +2 -2
  216. package/vendor/abseil-cpp/absl/random/internal/nonsecure_base_test.cc +2 -2
  217. package/vendor/abseil-cpp/absl/random/internal/pcg_engine.h +6 -6
  218. package/vendor/abseil-cpp/absl/random/internal/pcg_engine_test.cc +3 -2
  219. package/vendor/abseil-cpp/absl/random/internal/randen_detect.cc +6 -6
  220. package/vendor/abseil-cpp/absl/random/internal/randen_engine.h +2 -2
  221. package/vendor/abseil-cpp/absl/random/internal/randen_engine_test.cc +3 -2
  222. package/vendor/abseil-cpp/absl/random/internal/randen_test.cc +3 -2
  223. package/vendor/abseil-cpp/absl/random/internal/salted_seed_seq.h +6 -5
  224. package/vendor/abseil-cpp/absl/random/internal/seed_material.cc +4 -4
  225. package/vendor/abseil-cpp/absl/random/internal/seed_material.h +2 -1
  226. package/vendor/abseil-cpp/absl/random/internal/traits.h +21 -0
  227. package/vendor/abseil-cpp/absl/random/internal/traits_test.cc +5 -0
  228. package/vendor/abseil-cpp/absl/random/internal/uniform_helper.h +23 -23
  229. package/vendor/abseil-cpp/absl/random/internal/uniform_helper_test.cc +2 -1
  230. package/vendor/abseil-cpp/absl/random/mocking_access.h +74 -0
  231. package/vendor/abseil-cpp/absl/random/mocking_bit_gen.h +9 -19
  232. package/vendor/abseil-cpp/absl/random/uniform_real_distribution.h +1 -1
  233. package/vendor/abseil-cpp/absl/status/BUILD.bazel +81 -0
  234. package/vendor/abseil-cpp/absl/status/CMakeLists.txt +91 -0
  235. package/vendor/abseil-cpp/absl/status/internal/status_internal.cc +63 -18
  236. package/vendor/abseil-cpp/absl/status/internal/status_internal.h +26 -2
  237. package/vendor/abseil-cpp/absl/status/internal/status_matchers.h +22 -8
  238. package/vendor/abseil-cpp/absl/status/internal/statusor_internal.h +43 -43
  239. package/vendor/abseil-cpp/absl/status/status.cc +62 -70
  240. package/vendor/abseil-cpp/absl/status/status.h +249 -23
  241. package/vendor/abseil-cpp/absl/status/status_benchmark.cc +12 -0
  242. package/vendor/abseil-cpp/absl/status/status_builder.cc +196 -0
  243. package/vendor/abseil-cpp/absl/status/status_builder.h +978 -0
  244. package/vendor/abseil-cpp/absl/status/status_builder_test.cc +380 -0
  245. package/vendor/abseil-cpp/absl/status/status_macros.h +484 -0
  246. package/vendor/abseil-cpp/absl/status/status_macros_test.cc +634 -0
  247. package/vendor/abseil-cpp/absl/status/status_matchers.h +2 -1
  248. package/vendor/abseil-cpp/absl/status/status_matchers_test.cc +3 -4
  249. package/vendor/abseil-cpp/absl/status/status_payload_printer.h +3 -2
  250. package/vendor/abseil-cpp/absl/status/status_test.cc +443 -13
  251. package/vendor/abseil-cpp/absl/status/statusor.h +69 -36
  252. package/vendor/abseil-cpp/absl/status/statusor_test.cc +132 -35
  253. package/vendor/abseil-cpp/absl/strings/BUILD.bazel +42 -7
  254. package/vendor/abseil-cpp/absl/strings/CMakeLists.txt +33 -4
  255. package/vendor/abseil-cpp/absl/strings/ascii.h +1 -2
  256. package/vendor/abseil-cpp/absl/strings/atod_manual_test.cc +5 -5
  257. package/vendor/abseil-cpp/absl/strings/cord.cc +26 -7
  258. package/vendor/abseil-cpp/absl/strings/cord.h +23 -13
  259. package/vendor/abseil-cpp/absl/strings/cord_buffer.h +4 -2
  260. package/vendor/abseil-cpp/absl/strings/cord_test.cc +85 -9
  261. package/vendor/abseil-cpp/absl/strings/escaping.cc +176 -30
  262. package/vendor/abseil-cpp/absl/strings/escaping.h +12 -2
  263. package/vendor/abseil-cpp/absl/strings/escaping_benchmark.cc +1 -3
  264. package/vendor/abseil-cpp/absl/strings/escaping_test.cc +18 -18
  265. package/vendor/abseil-cpp/absl/strings/has_absl_stringify_test.cc +2 -2
  266. package/vendor/abseil-cpp/absl/strings/has_ostream_operator_test.cc +2 -2
  267. package/vendor/abseil-cpp/absl/strings/internal/append_and_overwrite.h +10 -10
  268. package/vendor/abseil-cpp/absl/strings/internal/cordz_sample_token_test.cc +1 -1
  269. package/vendor/abseil-cpp/absl/strings/internal/damerau_levenshtein_distance.cc +6 -0
  270. package/vendor/abseil-cpp/absl/strings/internal/damerau_levenshtein_distance.h +1 -0
  271. package/vendor/abseil-cpp/absl/strings/internal/escaping.cc +0 -141
  272. package/vendor/abseil-cpp/absl/strings/internal/escaping.h +2 -26
  273. package/vendor/abseil-cpp/absl/strings/internal/generic_printer_internal.h +23 -2
  274. package/vendor/abseil-cpp/absl/strings/internal/generic_printer_test.cc +6 -2
  275. package/vendor/abseil-cpp/absl/strings/internal/resize_uninitialized.h +31 -24
  276. package/vendor/abseil-cpp/absl/strings/internal/resize_uninitialized_test.cc +16 -41
  277. package/vendor/abseil-cpp/absl/strings/internal/stl_type_traits.h +39 -39
  278. package/vendor/abseil-cpp/absl/strings/internal/str_format/arg.h +14 -22
  279. package/vendor/abseil-cpp/absl/strings/internal/str_format/bind.h +2 -2
  280. package/vendor/abseil-cpp/absl/strings/internal/str_format/convert_test.cc +12 -20
  281. package/vendor/abseil-cpp/absl/strings/internal/str_format/float_conversion.cc +510 -307
  282. package/vendor/abseil-cpp/absl/strings/internal/str_join_internal.h +0 -1
  283. package/vendor/abseil-cpp/absl/strings/internal/str_split_internal.h +9 -10
  284. package/vendor/abseil-cpp/absl/strings/internal/string_constant_test.cc +6 -5
  285. package/vendor/abseil-cpp/absl/strings/internal/stringify_sink.h +12 -0
  286. package/vendor/abseil-cpp/absl/strings/internal/stringify_stream.h +119 -0
  287. package/vendor/abseil-cpp/absl/strings/internal/stringify_stream_test.cc +111 -0
  288. package/vendor/abseil-cpp/absl/strings/numbers.cc +406 -0
  289. package/vendor/abseil-cpp/absl/strings/numbers.h +4 -0
  290. package/vendor/abseil-cpp/absl/strings/numbers_test.cc +33 -0
  291. package/vendor/abseil-cpp/absl/strings/resize_and_overwrite.h +10 -6
  292. package/vendor/abseil-cpp/absl/strings/str_cat.h +36 -1
  293. package/vendor/abseil-cpp/absl/strings/str_cat_benchmark.cc +1 -2
  294. package/vendor/abseil-cpp/absl/strings/str_cat_test.cc +28 -0
  295. package/vendor/abseil-cpp/absl/strings/str_join_test.cc +4 -4
  296. package/vendor/abseil-cpp/absl/strings/str_split.h +11 -6
  297. package/vendor/abseil-cpp/absl/strings/str_split_test.cc +13 -0
  298. package/vendor/abseil-cpp/absl/strings/substitute.h +2 -2
  299. package/vendor/abseil-cpp/absl/synchronization/BUILD.bazel +3 -0
  300. package/vendor/abseil-cpp/absl/synchronization/internal/create_thread_identity.cc +21 -0
  301. package/vendor/abseil-cpp/absl/synchronization/internal/per_thread_sem.h +5 -0
  302. package/vendor/abseil-cpp/absl/synchronization/mutex.cc +13 -0
  303. package/vendor/abseil-cpp/absl/synchronization/mutex.h +32 -2
  304. package/vendor/abseil-cpp/absl/synchronization/mutex_test.cc +17 -3
  305. package/vendor/abseil-cpp/absl/time/BUILD.bazel +80 -0
  306. package/vendor/abseil-cpp/absl/time/CMakeLists.txt +73 -0
  307. package/vendor/abseil-cpp/absl/time/clock.h +3 -0
  308. package/vendor/abseil-cpp/absl/time/clock_interface.cc +71 -0
  309. package/vendor/abseil-cpp/absl/time/clock_interface.h +93 -0
  310. package/vendor/abseil-cpp/absl/time/clock_interface_test.cc +128 -0
  311. package/vendor/abseil-cpp/absl/time/format.cc +3 -10
  312. package/vendor/abseil-cpp/absl/time/format_test.cc +12 -0
  313. package/vendor/abseil-cpp/absl/time/internal/cctz/src/time_zone_format.cc +90 -89
  314. package/vendor/abseil-cpp/absl/time/internal/cctz/src/time_zone_format_test.cc +80 -5
  315. package/vendor/abseil-cpp/absl/time/internal/cctz/src/time_zone_name_win.cc +1 -2
  316. package/vendor/abseil-cpp/absl/time/internal/cctz/src/tzfile.h +10 -15
  317. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/version +1 -1
  318. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/zoneinfo/America/Vancouver +0 -0
  319. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/zoneinfo/Asia/Ho_Chi_Minh +0 -0
  320. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/zoneinfo/Asia/Phnom_Penh +0 -0
  321. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/zoneinfo/Asia/Saigon +0 -0
  322. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/zoneinfo/Asia/Tbilisi +0 -0
  323. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/zoneinfo/Asia/Vientiane +0 -0
  324. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/zoneinfo/Canada/Pacific +0 -0
  325. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/zoneinfo/Europe/Chisinau +0 -0
  326. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/zoneinfo/Europe/Tiraspol +0 -0
  327. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/zoneinfo/zone1970.tab +1 -1
  328. package/vendor/abseil-cpp/absl/time/internal/cctz/testdata/zoneinfo/zonenow.tab +3 -3
  329. package/vendor/abseil-cpp/absl/time/simulated_clock.cc +225 -0
  330. package/vendor/abseil-cpp/absl/time/simulated_clock.h +109 -0
  331. package/vendor/abseil-cpp/absl/time/simulated_clock_test.cc +614 -0
  332. package/vendor/abseil-cpp/absl/types/BUILD.bazel +116 -0
  333. package/vendor/abseil-cpp/absl/types/CMakeLists.txt +100 -0
  334. package/vendor/abseil-cpp/absl/types/any.h +26 -4
  335. package/vendor/abseil-cpp/absl/types/any_span.h +1067 -0
  336. package/vendor/abseil-cpp/absl/types/any_span_benchmark.cc +258 -0
  337. package/vendor/abseil-cpp/absl/types/any_span_test.cc +1210 -0
  338. package/vendor/abseil-cpp/absl/types/compare.h +4 -4
  339. package/vendor/abseil-cpp/absl/types/internal/any_span.h +477 -0
  340. package/vendor/abseil-cpp/absl/types/internal/span.h +5 -6
  341. package/vendor/abseil-cpp/absl/types/optional.h +30 -3
  342. package/vendor/abseil-cpp/absl/types/optional_ref.h +295 -0
  343. package/vendor/abseil-cpp/absl/types/optional_ref_test.cc +370 -0
  344. package/vendor/abseil-cpp/absl/types/source_location.cc +18 -0
  345. package/vendor/abseil-cpp/absl/types/source_location.h +172 -0
  346. package/vendor/abseil-cpp/absl/types/source_location_test.cc +139 -0
  347. package/vendor/abseil-cpp/absl/types/span.h +19 -23
  348. package/vendor/abseil-cpp/absl/types/variant.h +75 -18
  349. package/vendor/abseil-cpp/absl/types/variant_test.cc +23 -23
  350. package/vendor/abseil-cpp/absl/utility/BUILD.bazel +1 -0
  351. package/vendor/abseil-cpp/absl/utility/CMakeLists.txt +1 -0
  352. package/vendor/abseil-cpp/absl/utility/utility.h +99 -16
  353. package/vendor/abseil-cpp/ci/absl_alternate_options.h +2 -0
  354. package/vendor/abseil-cpp/ci/linux_arm_clang-latest_libcxx_bazel.sh +10 -4
  355. package/vendor/abseil-cpp/ci/linux_clang-latest_libcxx_asan_bazel.sh +13 -6
  356. package/vendor/abseil-cpp/ci/linux_clang-latest_libcxx_bazel.sh +10 -4
  357. package/vendor/abseil-cpp/ci/linux_clang-latest_libcxx_tsan_bazel.sh +12 -5
  358. package/vendor/abseil-cpp/ci/linux_clang-latest_libstdcxx_bazel.sh +9 -2
  359. package/vendor/abseil-cpp/ci/linux_docker_containers.sh +4 -4
  360. package/vendor/abseil-cpp/ci/linux_gcc-floor_libstdcxx_bazel.sh +10 -3
  361. package/vendor/abseil-cpp/ci/linux_gcc-latest_libstdcxx_bazel.sh +8 -2
  362. package/vendor/abseil-cpp/ci/macos_xcode_bazel.sh +4 -3
  363. package/vendor/abseil-cpp/ci/macos_xcode_cmake.sh +2 -2
  364. package/vendor/abseil-cpp/ci/windows_clangcl_bazel.bat +1 -1
  365. package/vendor/abseil-cpp/ci/windows_msvc_bazel.bat +1 -1
  366. package/AGENTS.md +0 -131
  367. package/ARCHITECTURE.md +0 -152
  368. package/vendor/abseil-cpp/absl/debugging/internal/borrowed_fixup_buffer.cc +0 -118
  369. package/vendor/abseil-cpp/absl/debugging/internal/borrowed_fixup_buffer.h +0 -71
  370. package/vendor/abseil-cpp/absl/debugging/internal/borrowed_fixup_buffer_test.cc +0 -97
@@ -0,0 +1,128 @@
1
+ // Copyright 2026 The Abseil Authors.
2
+ //
3
+ // Licensed under the Apache License, Version 2.0 (the "License");
4
+ // you may not use this file except in compliance with the License.
5
+ // You may obtain a copy of the License at
6
+ //
7
+ // https://www.apache.org/licenses/LICENSE-2.0
8
+ //
9
+ // Unless required by applicable law or agreed to in writing, software
10
+ // distributed under the License is distributed on an "AS IS" BASIS,
11
+ // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ // See the License for the specific language governing permissions and
13
+ // limitations under the License.
14
+
15
+ #include "absl/time/clock_interface.h"
16
+
17
+ #include <cstdint>
18
+ #include <functional>
19
+ #include <thread> // NOLINT(build/c++11)
20
+ #include <vector>
21
+
22
+ #include "gmock/gmock.h"
23
+ #include "gtest/gtest.h"
24
+ #include "absl/functional/bind_front.h"
25
+ #include "absl/synchronization/mutex.h"
26
+ #include "absl/synchronization/notification.h"
27
+ #include "absl/time/clock.h"
28
+ #include "absl/time/time.h"
29
+
30
+ namespace {
31
+
32
+ constexpr absl::Duration kLongPause = absl::Milliseconds(150);
33
+
34
+ #ifdef _MSC_VER
35
+ // As of 2026-01-29, multithreaded tests on MSVC are too flaky.
36
+ const char* kSkipFlakyReason =
37
+ "Skipping this timing test because it is too flaky";
38
+ #else
39
+ const char* kSkipFlakyReason = nullptr;
40
+ #endif
41
+
42
+
43
+ void AwaitWithDeadlineAndNotify(absl::Clock* clock, absl::Mutex* mu,
44
+ absl::Condition* cond, absl::Time wakeup_time,
45
+ absl::Notification* note, bool* return_val) {
46
+ mu->lock_shared();
47
+ *return_val = clock->AwaitWithDeadline(mu, *cond, wakeup_time);
48
+ mu->unlock_shared();
49
+ note->Notify();
50
+ }
51
+
52
+ TEST(RealClockTest, AwaitWithVeryLargeDeadline) {
53
+ if (kSkipFlakyReason != nullptr) {
54
+ GTEST_SKIP() << kSkipFlakyReason;
55
+ }
56
+
57
+ absl::Clock& clock = absl::Clock::GetRealClock();
58
+ absl::Mutex mu;
59
+ bool f = false;
60
+ absl::Condition cond(&f);
61
+ absl::Notification note;
62
+ bool return_val;
63
+
64
+ std::thread thread(AwaitWithDeadlineAndNotify, &clock, &mu, &cond,
65
+ absl::InfiniteFuture(), &note, &return_val);
66
+
67
+ EXPECT_FALSE(note.HasBeenNotified());
68
+
69
+ mu.lock();
70
+ f = true;
71
+ mu.unlock();
72
+
73
+ absl::SleepFor(kLongPause);
74
+ EXPECT_TRUE(note.HasBeenNotified());
75
+ EXPECT_TRUE(return_val);
76
+ note.WaitForNotification(); // In case the expectation fails.
77
+ thread.join();
78
+ }
79
+
80
+ TEST(RealClockTest, AwaitWithPastDeadline) {
81
+ if (kSkipFlakyReason != nullptr) {
82
+ GTEST_SKIP() << kSkipFlakyReason;
83
+ }
84
+
85
+ absl::Clock& clock = absl::Clock::GetRealClock();
86
+ absl::Mutex mu;
87
+ bool f = false;
88
+ absl::Condition cond(&f);
89
+ absl::Notification note;
90
+ bool return_val;
91
+
92
+ std::thread thread(AwaitWithDeadlineAndNotify, &clock, &mu, &cond,
93
+ clock.TimeNow() - absl::Seconds(10), &note, &return_val);
94
+ absl::Time start = absl::Now();
95
+ note.WaitForNotification(); // AwaitWithDeadline() should ping note.
96
+ EXPECT_GE(kLongPause, absl::Now() - start);
97
+ EXPECT_FALSE(return_val);
98
+ thread.join();
99
+ }
100
+
101
+ TEST(RealClockTest, AwaitWithSmallDeadline) {
102
+ if (kSkipFlakyReason != nullptr) {
103
+ GTEST_SKIP() << kSkipFlakyReason;
104
+ }
105
+
106
+ absl::Clock& clock = absl::Clock::GetRealClock();
107
+ absl::Mutex mu;
108
+ bool f = false;
109
+ absl::Condition cond(&f);
110
+
111
+ for (int i = 0; i < 5; ++i) {
112
+ absl::Duration wait_time = absl::Milliseconds(i);
113
+ absl::Duration elapsed_time;
114
+ {
115
+ absl::MutexLock lock(mu);
116
+ absl::Time start = clock.TimeNow();
117
+ absl::Time wakeup_time = start + wait_time;
118
+ EXPECT_FALSE(clock.AwaitWithDeadline(&mu, cond, wakeup_time));
119
+ elapsed_time = clock.TimeNow() - start;
120
+ }
121
+ if (elapsed_time >= absl::ZeroDuration()) { // ignore jumps backwards
122
+ // 60 microseconds of slop to allow for non-monotonic clocks.
123
+ EXPECT_GE(elapsed_time, wait_time - absl::Microseconds(60));
124
+ }
125
+ }
126
+ }
127
+
128
+ } // namespace
@@ -17,7 +17,7 @@
17
17
  #include <cctype>
18
18
  #include <cstdint>
19
19
  #include <utility>
20
-
20
+ #include "absl/strings/ascii.h"
21
21
  #include "absl/strings/match.h"
22
22
  #include "absl/strings/string_view.h"
23
23
  #include "absl/time/internal/cctz/include/cctz/time_zone.h"
@@ -99,13 +99,6 @@ bool ParseTime(absl::string_view format, absl::string_view input,
99
99
  // the fields with respect to the given TimeZone.
100
100
  bool ParseTime(absl::string_view format, absl::string_view input,
101
101
  absl::TimeZone tz, absl::Time* time, std::string* err) {
102
- auto strip_leading_space = [](absl::string_view* sv) {
103
- while (!sv->empty()) {
104
- if (!std::isspace(sv->front())) return;
105
- sv->remove_prefix(1);
106
- }
107
- };
108
-
109
102
  // Portable toolchains means we don't get nice constexpr here.
110
103
  struct Literal {
111
104
  const char* name;
@@ -116,12 +109,12 @@ bool ParseTime(absl::string_view format, absl::string_view input,
116
109
  {kInfiniteFutureStr, strlen(kInfiniteFutureStr), InfiniteFuture()},
117
110
  {kInfinitePastStr, strlen(kInfinitePastStr), InfinitePast()},
118
111
  };
119
- strip_leading_space(&input);
112
+ input = StripLeadingAsciiWhitespace(input);
120
113
  for (const auto& lit : literals) {
121
114
  if (absl::StartsWith(input, absl::string_view(lit.name, lit.size))) {
122
115
  absl::string_view tail = input;
123
116
  tail.remove_prefix(lit.size);
124
- strip_leading_space(&tail);
117
+ tail = StripLeadingAsciiWhitespace(tail);
125
118
  if (tail.empty()) {
126
119
  *time = lit.value;
127
120
  return true;
@@ -245,6 +245,18 @@ TEST(ParseTime, ErrorCases) {
245
245
  EXPECT_THAT(err, HasSubstr("Illegal trailing data"));
246
246
  EXPECT_FALSE(absl::ParseTime("%Ez", "-00:-0", &t, &err)) << err;
247
247
  EXPECT_THAT(err, HasSubstr("Illegal trailing data"));
248
+
249
+ // Check that we do not accept strings with embedded NULs.
250
+ EXPECT_FALSE(
251
+ absl::ParseTime("%Y", std::string("2026\0payload", 12), &t, &err));
252
+ EXPECT_THAT(err, HasSubstr("Illegal trailing data"));
253
+
254
+ // High-bit character test for sign-extension bugs.
255
+ for (int i = 128; i < 256; ++i) {
256
+ char c = static_cast<char>(i);
257
+ std::string input = std::string(1, c) + "2015-01-02";
258
+ EXPECT_FALSE(absl::ParseTime("%Y-%m-%d", input, &t, &err));
259
+ }
248
260
  }
249
261
 
250
262
  TEST(ParseTime, ExtendedSeconds) {
@@ -41,7 +41,6 @@
41
41
  #include <ctime>
42
42
  #include <limits>
43
43
  #include <string>
44
- #include <vector>
45
44
  #if !HAS_STRPTIME
46
45
  #include <iomanip>
47
46
  #include <sstream>
@@ -215,19 +214,15 @@ char* FormatOffset(char* ep, int offset, const char* mode) {
215
214
 
216
215
  // Formats a std::tm using strftime(3).
217
216
  void FormatTM(std::string* out, const std::string& fmt, const std::tm& tm) {
218
- // strftime(3) returns the number of characters placed in the output
219
- // array (which may be 0 characters). It also returns 0 to indicate
220
- // an error, like the array wasn't large enough. To accommodate this,
221
- // the following code grows the buffer size from 2x the format string
222
- // length up to 32x.
223
- for (std::size_t i = 2; i != 32; i *= 2) {
224
- std::size_t buf_size = fmt.size() * i;
225
- std::vector<char> buf(buf_size);
226
- if (std::size_t len = strftime(&buf[0], buf_size, fmt.c_str(), &tm)) {
227
- out->append(&buf[0], len);
228
- return;
229
- }
230
- }
217
+ // We assume that 16 times the length of the format string will
218
+ // be sufficient to store the result. The extreme case appears
219
+ // to be "%c" (2 chars), which, in the POSIX locale, produces
220
+ // "Thu Jan 1 00:00:00 1970" (24 chars).
221
+ auto out_size = out->size();
222
+ auto buf_size = (16 * fmt.size()) + 1;
223
+ out->resize(out_size + buf_size);
224
+ auto len = strftime(&(*out)[out_size], buf_size, fmt.c_str(), &tm);
225
+ out->resize(out_size + len);
231
226
  }
232
227
 
233
228
  // Used for %E#S/%E#f specifiers and for data values in parse().
@@ -335,12 +330,12 @@ const std::int_fast64_t kExp10[kDigits10_64 + 1] = {
335
330
  std::string format(const std::string& format, const time_point<seconds>& tp,
336
331
  const detail::femtoseconds& fs, const time_zone& tz) {
337
332
  std::string result;
338
- result.reserve(format.size()); // A reasonable guess for the result size.
333
+ result.reserve(2 * format.size()); // A guess for the result size.
339
334
  const time_zone::absolute_lookup al = tz.lookup(tp);
340
335
  const std::tm tm = ToTM(al);
341
336
 
342
337
  // Scratch buffer for internal conversions.
343
- char buf[6 + (kDigits10_64 + 2)]; // enough for longest conversion %F
338
+ char buf[6 + (kDigits10_64 + 2)]; // enough for longest conversion (%F)
344
339
  char* const ep = buf + sizeof(buf);
345
340
  char* bp; // works back from ep
346
341
 
@@ -349,23 +344,29 @@ std::string format(const std::string& format, const time_point<seconds>& tp,
349
344
  // [pending ... cur) : formatting pending, but no special cases
350
345
  // [cur ... format.end()) : unexamined
351
346
  // Initially, everything is in the unexamined part.
352
- const char* pending = format.c_str(); // NUL terminated
347
+ const char* pending = format.data();
353
348
  const char* cur = pending;
354
- const char* end = pending + format.length();
349
+ const char* const end = pending + format.size();
355
350
 
356
351
  while (cur != end) { // while something is unexamined
357
352
  // Moves cur to the next percent sign.
358
353
  const char* start = cur;
359
- while (cur != end && *cur != '%') ++cur;
354
+ while (cur != end && *cur != '%') {
355
+ if (*cur == '\0' && pending != start) {
356
+ FormatTM(&result, std::string(pending, cur), tm);
357
+ pending = start = cur;
358
+ }
359
+ ++cur;
360
+ }
360
361
 
361
362
  // If the new pending text is all ordinary, copy it out.
362
363
  if (cur != start && pending == start) {
363
- result.append(pending, static_cast<std::size_t>(cur - pending));
364
+ result.append(pending, cur);
364
365
  pending = start = cur;
365
366
  }
366
367
 
367
368
  // Span the sequential percent signs.
368
- const char* percent = cur;
369
+ const char* const percent = cur;
369
370
  while (cur != end && *cur == '%') ++cur;
370
371
 
371
372
  // If the new pending text is all percents, copy out one
@@ -384,26 +385,32 @@ std::string format(const std::string& format, const time_point<seconds>& tp,
384
385
  if (cur == end || (cur - percent) % 2 == 0) continue;
385
386
 
386
387
  // Simple specifiers that we handle ourselves.
387
- if (strchr("YmdeFUuWwHMSTzZs%", *cur)) {
388
- if (cur - 1 != pending) {
389
- FormatTM(&result, std::string(pending, cur - 1), tm);
390
- }
388
+ if (*cur == '\0' || strchr("YmdeFUuWwHMSTzZs%", *cur)) {
389
+ FormatTM(&result, std::string(pending, cur - 1), tm);
391
390
  switch (*cur) {
391
+ case '\0':
392
+ // Because we allow NULs in the format string, we must give
393
+ // some meaning to the "%\0" specifier. We choose the common
394
+ // (but undefined) strftime() behavior of echoing unknown
395
+ // specifiers.
396
+ result.push_back('%');
397
+ result.push_back('\0');
398
+ break;
392
399
  case 'Y':
393
400
  // This avoids the tm.tm_year overflow problem for %Y, however
394
401
  // tm.tm_year will still be used by other specifiers like %D.
395
402
  bp = Format64(ep, 0, al.cs.year());
396
- result.append(bp, static_cast<std::size_t>(ep - bp));
403
+ result.append(bp, ep);
397
404
  break;
398
405
  case 'm':
399
406
  bp = Format02d(ep, al.cs.month());
400
- result.append(bp, static_cast<std::size_t>(ep - bp));
407
+ result.append(bp, ep);
401
408
  break;
402
409
  case 'd':
403
410
  case 'e':
404
411
  bp = Format02d(ep, al.cs.day());
405
412
  if (*cur == 'e' && *bp == '0') *bp = ' '; // for Windows
406
- result.append(bp, static_cast<std::size_t>(ep - bp));
413
+ result.append(bp, ep);
407
414
  break;
408
415
  case 'F':
409
416
  bp = Format02d(ep, al.cs.day());
@@ -411,35 +418,35 @@ std::string format(const std::string& format, const time_point<seconds>& tp,
411
418
  bp = Format02d(bp, al.cs.month());
412
419
  *--bp = '-';
413
420
  bp = Format64(bp, 0, al.cs.year());
414
- result.append(bp, static_cast<std::size_t>(ep - bp));
421
+ result.append(bp, ep);
415
422
  break;
416
423
  case 'U':
417
424
  bp = Format02d(ep, ToWeek(civil_day(al.cs), weekday::sunday));
418
- result.append(bp, static_cast<std::size_t>(ep - bp));
425
+ result.append(bp, ep);
419
426
  break;
420
427
  case 'u':
421
428
  bp = Format64(ep, 0, tm.tm_wday ? tm.tm_wday : 7);
422
- result.append(bp, static_cast<std::size_t>(ep - bp));
429
+ result.append(bp, ep);
423
430
  break;
424
431
  case 'W':
425
432
  bp = Format02d(ep, ToWeek(civil_day(al.cs), weekday::monday));
426
- result.append(bp, static_cast<std::size_t>(ep - bp));
433
+ result.append(bp, ep);
427
434
  break;
428
435
  case 'w':
429
436
  bp = Format64(ep, 0, tm.tm_wday);
430
- result.append(bp, static_cast<std::size_t>(ep - bp));
437
+ result.append(bp, ep);
431
438
  break;
432
439
  case 'H':
433
440
  bp = Format02d(ep, al.cs.hour());
434
- result.append(bp, static_cast<std::size_t>(ep - bp));
441
+ result.append(bp, ep);
435
442
  break;
436
443
  case 'M':
437
444
  bp = Format02d(ep, al.cs.minute());
438
- result.append(bp, static_cast<std::size_t>(ep - bp));
445
+ result.append(bp, ep);
439
446
  break;
440
447
  case 'S':
441
448
  bp = Format02d(ep, al.cs.second());
442
- result.append(bp, static_cast<std::size_t>(ep - bp));
449
+ result.append(bp, ep);
443
450
  break;
444
451
  case 'T':
445
452
  bp = Format02d(ep, al.cs.second());
@@ -447,18 +454,18 @@ std::string format(const std::string& format, const time_point<seconds>& tp,
447
454
  bp = Format02d(bp, al.cs.minute());
448
455
  *--bp = ':';
449
456
  bp = Format02d(bp, al.cs.hour());
450
- result.append(bp, static_cast<std::size_t>(ep - bp));
457
+ result.append(bp, ep);
451
458
  break;
452
459
  case 'z':
453
460
  bp = FormatOffset(ep, al.offset, "");
454
- result.append(bp, static_cast<std::size_t>(ep - bp));
461
+ result.append(bp, ep);
455
462
  break;
456
463
  case 'Z':
457
464
  result.append(al.abbr);
458
465
  break;
459
466
  case 's':
460
467
  bp = Format64(ep, 0, ToUnixSeconds(tp));
461
- result.append(bp, static_cast<std::size_t>(ep - bp));
468
+ result.append(bp, ep);
462
469
  break;
463
470
  case '%':
464
471
  result.push_back('%');
@@ -472,33 +479,27 @@ std::string format(const std::string& format, const time_point<seconds>& tp,
472
479
  if (*cur == ':' && cur + 1 != end) {
473
480
  if (*(cur + 1) == 'z') {
474
481
  // Formats %:z.
475
- if (cur - 1 != pending) {
476
- FormatTM(&result, std::string(pending, cur - 1), tm);
477
- }
482
+ FormatTM(&result, std::string(pending, cur - 1), tm);
478
483
  bp = FormatOffset(ep, al.offset, ":");
479
- result.append(bp, static_cast<std::size_t>(ep - bp));
484
+ result.append(bp, ep);
480
485
  pending = cur += 2;
481
486
  continue;
482
487
  }
483
488
  if (*(cur + 1) == ':' && cur + 2 != end) {
484
489
  if (*(cur + 2) == 'z') {
485
490
  // Formats %::z.
486
- if (cur - 1 != pending) {
487
- FormatTM(&result, std::string(pending, cur - 1), tm);
488
- }
491
+ FormatTM(&result, std::string(pending, cur - 1), tm);
489
492
  bp = FormatOffset(ep, al.offset, ":*");
490
- result.append(bp, static_cast<std::size_t>(ep - bp));
493
+ result.append(bp, ep);
491
494
  pending = cur += 3;
492
495
  continue;
493
496
  }
494
497
  if (*(cur + 2) == ':' && cur + 3 != end) {
495
498
  if (*(cur + 3) == 'z') {
496
499
  // Formats %:::z.
497
- if (cur - 1 != pending) {
498
- FormatTM(&result, std::string(pending, cur - 1), tm);
499
- }
500
+ FormatTM(&result, std::string(pending, cur - 1), tm);
500
501
  bp = FormatOffset(ep, al.offset, ":*:");
501
- result.append(bp, static_cast<std::size_t>(ep - bp));
502
+ result.append(bp, ep);
502
503
  pending = cur += 4;
503
504
  continue;
504
505
  }
@@ -512,33 +513,25 @@ std::string format(const std::string& format, const time_point<seconds>& tp,
512
513
  // Format our extensions.
513
514
  if (*cur == 'T') {
514
515
  // Formats %ET.
515
- if (cur - 2 != pending) {
516
- FormatTM(&result, std::string(pending, cur - 2), tm);
517
- }
516
+ FormatTM(&result, std::string(pending, cur - 2), tm);
518
517
  result.append("T");
519
518
  pending = ++cur;
520
519
  } else if (*cur == 'z') {
521
520
  // Formats %Ez.
522
- if (cur - 2 != pending) {
523
- FormatTM(&result, std::string(pending, cur - 2), tm);
524
- }
521
+ FormatTM(&result, std::string(pending, cur - 2), tm);
525
522
  bp = FormatOffset(ep, al.offset, ":");
526
- result.append(bp, static_cast<std::size_t>(ep - bp));
523
+ result.append(bp, ep);
527
524
  pending = ++cur;
528
525
  } else if (*cur == '*' && cur + 1 != end && *(cur + 1) == 'z') {
529
526
  // Formats %E*z.
530
- if (cur - 2 != pending) {
531
- FormatTM(&result, std::string(pending, cur - 2), tm);
532
- }
527
+ FormatTM(&result, std::string(pending, cur - 2), tm);
533
528
  bp = FormatOffset(ep, al.offset, ":*");
534
- result.append(bp, static_cast<std::size_t>(ep - bp));
529
+ result.append(bp, ep);
535
530
  pending = cur += 2;
536
531
  } else if (*cur == '*' && cur + 1 != end &&
537
532
  (*(cur + 1) == 'S' || *(cur + 1) == 'f')) {
538
533
  // Formats %E*S or %E*F.
539
- if (cur - 2 != pending) {
540
- FormatTM(&result, std::string(pending, cur - 2), tm);
541
- }
534
+ FormatTM(&result, std::string(pending, cur - 2), tm);
542
535
  char* cp = ep;
543
536
  bp = Format64(cp, 15, fs.count());
544
537
  while (cp != bp && cp[-1] == '0') --cp;
@@ -551,15 +544,13 @@ std::string format(const std::string& format, const time_point<seconds>& tp,
551
544
  if (cp == bp) *--bp = '0';
552
545
  break;
553
546
  }
554
- result.append(bp, static_cast<std::size_t>(cp - bp));
547
+ result.append(bp, cp);
555
548
  pending = cur += 2;
556
549
  } else if (*cur == '4' && cur + 1 != end && *(cur + 1) == 'Y') {
557
550
  // Formats %E4Y.
558
- if (cur - 2 != pending) {
559
- FormatTM(&result, std::string(pending, cur - 2), tm);
560
- }
551
+ FormatTM(&result, std::string(pending, cur - 2), tm);
561
552
  bp = Format64(ep, 4, al.cs.year());
562
- result.append(bp, static_cast<std::size_t>(ep - bp));
553
+ result.append(bp, ep);
563
554
  pending = cur += 2;
564
555
  } else if (std::isdigit(*cur)) {
565
556
  // Possibly found %E#S or %E#f.
@@ -567,9 +558,7 @@ std::string format(const std::string& format, const time_point<seconds>& tp,
567
558
  if (const char* np = ParseInt(cur, 0, 0, 1024, &n)) {
568
559
  if (*np == 'S' || *np == 'f') {
569
560
  // Formats %E#S or %E#f.
570
- if (cur - 2 != pending) {
571
- FormatTM(&result, std::string(pending, cur - 2), tm);
572
- }
561
+ FormatTM(&result, std::string(pending, cur - 2), tm);
573
562
  bp = ep;
574
563
  if (n > 0) {
575
564
  if (n > kDigits10_64) n = kDigits10_64;
@@ -579,7 +568,7 @@ std::string format(const std::string& format, const time_point<seconds>& tp,
579
568
  if (*np == 'S') *--bp = '.';
580
569
  }
581
570
  if (*np == 'S') bp = Format02d(bp, al.cs.second());
582
- result.append(bp, static_cast<std::size_t>(ep - bp));
571
+ result.append(bp, ep);
583
572
  pending = cur = ++np;
584
573
  }
585
574
  }
@@ -587,9 +576,7 @@ std::string format(const std::string& format, const time_point<seconds>& tp,
587
576
  }
588
577
 
589
578
  // Formats any remaining data.
590
- if (end != pending) {
591
- FormatTM(&result, std::string(pending, end), tm);
592
- }
579
+ FormatTM(&result, std::string(pending, end), tm);
593
580
 
594
581
  return result;
595
582
  }
@@ -710,8 +697,12 @@ bool FromWeek(int week_num, weekday week_start, year_t* year, std::tm* tm) {
710
697
  bool parse(const std::string& format, const std::string& input,
711
698
  const time_zone& tz, time_point<seconds>* sec,
712
699
  detail::femtoseconds* fs, std::string* err) {
713
- // The unparsed input.
700
+ // The unparsed input. Even though we allow NULs in input, and
701
+ // match them against corresponding NULs in format, we depend on
702
+ // *edata being a NUL so that we can call strptime(). This also
703
+ // makes our handling of input easier.
714
704
  const char* data = input.c_str(); // NUL terminated
705
+ const char* const edata = data + input.size();
715
706
 
716
707
  // Skips leading whitespace.
717
708
  while (std::isspace(*data)) ++data;
@@ -737,7 +728,11 @@ bool parse(const std::string& format, const std::string& input,
737
728
  int offset = 0; // No offset from passed tz.
738
729
  std::string zone = "UTC";
739
730
 
731
+ // Even though we allow NULs in format, and match them against
732
+ // corresponding NULs in input, we simplify its handling by also
733
+ // ensuring that *efmt is a NUL.
740
734
  const char* fmt = format.c_str(); // NUL terminated
735
+ const char* const efmt = fmt + format.size();
741
736
  bool twelve_hour = false;
742
737
  bool afternoon = false;
743
738
  int week_num = -1;
@@ -747,7 +742,7 @@ bool parse(const std::string& format, const std::string& input,
747
742
  std::int_fast64_t percent_s = 0;
748
743
 
749
744
  // Steps through format, one specifier at a time.
750
- while (data != nullptr && *fmt != '\0') {
745
+ while (data != nullptr && fmt != efmt) {
751
746
  if (std::isspace(*fmt)) {
752
747
  while (std::isspace(*data)) ++data;
753
748
  while (std::isspace(*++fmt)) continue;
@@ -755,7 +750,7 @@ bool parse(const std::string& format, const std::string& input,
755
750
  }
756
751
 
757
752
  if (*fmt != '%') {
758
- if (*data == *fmt) {
753
+ if (data != edata && *data == *fmt) {
759
754
  ++data;
760
755
  ++fmt;
761
756
  } else {
@@ -764,14 +759,21 @@ bool parse(const std::string& format, const std::string& input,
764
759
  continue;
765
760
  }
766
761
 
767
- const char* percent = fmt;
768
- if (*++fmt == '\0') {
762
+ const char* const percent = fmt;
763
+ if (++fmt == efmt) {
769
764
  data = nullptr;
770
765
  continue;
771
766
  }
772
767
  switch (*fmt++) {
768
+ case '\0':
769
+ // Because we allow NULs in the format string, we must give
770
+ // some meaning to the "%\0" specifier. We choose the common
771
+ // (but undefined) strptime() behavior of failing on unknown
772
+ // specifiers.
773
+ data = nullptr;
774
+ continue;
773
775
  case 'Y':
774
- // Symmetrically with FormatTime(), directly handing %Y avoids the
776
+ // Symmetrically with format(), directly handing %Y avoids the
775
777
  // tm.tm_year overflow problem. However, tm.tm_year will still be
776
778
  // used by other specifiers like %D.
777
779
  data = ParseInt(data, 0, kyearmin, kyearmax, &year);
@@ -946,8 +948,8 @@ bool parse(const std::string& format, const std::string& input,
946
948
  }
947
949
 
948
950
  // Parses the current specifier.
949
- const char* orig_data = data;
950
- std::string spec(percent, static_cast<std::size_t>(fmt - percent));
951
+ const char* const orig_data = data;
952
+ std::string spec(percent, fmt);
951
953
  data = ParseTM(data, spec.c_str(), &tm);
952
954
 
953
955
  // If we successfully parsed %p we need to remember whether the result
@@ -956,10 +958,9 @@ bool parse(const std::string& format, const std::string& input,
956
958
  // to a PM hour.
957
959
  if (spec == "%p" && data != nullptr) {
958
960
  std::string test_input = "1";
959
- test_input.append(orig_data, static_cast<std::size_t>(data - orig_data));
960
- const char* test_data = test_input.c_str();
961
+ test_input.append(orig_data, data);
961
962
  std::tm tmp{};
962
- ParseTM(test_data, "%I%p", &tmp);
963
+ ParseTM(test_input.c_str(), "%I%p", &tmp);
963
964
  afternoon = (tmp.tm_hour == 13);
964
965
  }
965
966
  }
@@ -978,7 +979,7 @@ bool parse(const std::string& format, const std::string& input,
978
979
  while (std::isspace(*data)) ++data;
979
980
 
980
981
  // parse() must consume the entire input string.
981
- if (*data != '\0') {
982
+ if (data != edata) {
982
983
  if (err != nullptr) *err = "Illegal trailing data in input string";
983
984
  return false;
984
985
  }