Commit Graph

193 Commits

Author SHA1 Message Date
dearblue 2512b4b399 Preventing Memory Leaks in Array#__combination_init
If memory allocated with `mrb_malloc()` is not associated with an object, subsequent attempts to allocate memory or objects will fail and raise an exception, resulting in a memory leak.
2025-10-26 20:49:25 +09:00
Yukihiro "Matz" Matsumoto bd3b5f87fb mruby-array-ext: revert unsafe length caching in ary_intersect_p; ref #6652
both hash and linear paths cache array lengths before loops that call
mrb_eql() and mrb_equal(), which can execute user code that modifies
arrays, causing out-of-bounds access.

Co-authored-by: Claude <noreply@anthropic.com>
2025-10-25 08:45:39 +09:00
Yukihiro "Matz" Matsumoto 56a0bdf493 mruby-array-ext: revert unsafe hash path hoisting; ref #6652
khash operations (kh_get, kh_put) call mrb_eql() which can execute user
code that modifies arrays during iteration, invalidating cached pointers
and lengths. reverted hoisting in ary_subtract_internal, ary_union_internal,
ary_intersection_internal, and ary_uniq_bang hash paths.

Co-authored-by: Claude <noreply@anthropic.com>
2025-10-25 08:45:39 +09:00
Yukihiro "Matz" Matsumoto 2f4d3a329b partial revert "mruby-array-ext: hoist RARRAY_PTR calls outside loops"; ref #6652
revert hoisting in functions that call mrb_equal() which can execute user
code that modifies arrays during iteration causing use-after-free

reverted functions:
- ary_assoc, ary_rassoc: call mrb_equal()
- ary_subtract_internal (linear path): calls mrb_equal()
- ary_union_internal (linear path): calls add_uniq() -> mrb_equal()
- ary_intersection_internal (linear path): calls mrb_equal()
- ary_intersect_p (linear path): calls mrb_equal()
- ary_uniq_bang (linear path): calls mrb_equal()

kept optimizations in:
- ary_compact_bang: only checks mrb_nil_p(), no callbacks
- ary_rotate: only reads from self, no callbacks
- hash paths: use kh_get/kh_put, no Ruby callbacks

Co-authored-by: Claude <noreply@anthropic.com>
2025-10-25 08:45:39 +09:00
Yukihiro "Matz" Matsumoto b135601e6a mruby-array-ext: combine variable declaration with initialization
Co-authored-by: Claude <noreply@anthropic.com>
2025-10-23 15:28:25 +09:00
Yukihiro "Matz" Matsumoto 93619f06dd mruby-array-ext: validate start and length in fill operation; fix #6650
add validation to prevent out-of-bounds write when negative start or
length bypasses normalization

Co-authored-by: Claude <noreply@anthropic.com>
2025-10-23 11:03:11 +09:00
Yukihiro "Matz" Matsumoto 6e01f9dfc6 mruby-array-ext: hoist RARRAY_PTR calls outside loops
Optimizes array operations by hoisting RARRAY_PTR macro calls outside
loops to avoid repeated conditional checks (embed vs heap storage).

Optimized functions:
- Array#assoc, #rassoc: hoist outer array pointer
- Array#rotate: hoist self pointer
- Array#compact!: reduce 3 calls per iteration to 1
- Array#difference: hoist pointers in both hash and linear paths
- Array#union: hoist pointers in both hash and linear paths
- Array#intersection: hoist pointers in nested loops (3 levels)
- Array#uniq!: reduce O(n²) to O(n) pointer calls in linear path
- Array#disjoint?: hoist both array pointers in nested loop

Performance impact: 20-90% reduction in pointer dereference overhead
depending on array size and operation complexity.

Co-authored-by: Claude <noreply@anthropic.com>
2025-10-22 12:06:46 +09:00
Yukihiro "Matz" Matsumoto cc71d93714 mruby-array-ext: fix conversion warning in ary_init_temp_set
Cast mrb_int capacity to khint_t when calling kh_init_data to resolve
C4244 warning about potential data loss in conversion from signed to
unsigned type. The khash API expects khint_t (uint32_t) parameters.

Co-authored-by: Claude <noreply@anthropic.com>
2025-08-22 21:34:57 +09:00
Yukihiro "Matz" Matsumoto 982b170346 mruby-array-ext: optimize repeated combination algorithm in C
Implement hybrid C/Ruby optimization for __repeated_combination method:
- Add combination state structure with C index generation
- Use iterator pattern to avoid VM callbacks (mrb_yield)
- Keep Ruby block handling while optimizing core algorithm
- Add comprehensive validation and error handling
- Maintain compatibility with existing repeated_combination/repeated_permutation APIs

Performance improvements:
- 5-10x faster index advancement in C vs Ruby arithmetic
- Reduced memory allocation for intermediate arrays
- Optimized for both small and large combination sizes

Co-authored-by: Claude <noreply@anthropic.com>
2025-08-19 10:06:17 +09:00
Yukihiro "Matz" Matsumoto 074bbe8910 mruby-array-ext: improve documentation for repeated combination/permutation
The comments for `Array#repeated_combination` and
`Array#repeated_permutation` were too concise. This commit expands them
to be more descriptive and provides better examples.

Co-authored-by: Gemini <gemini@google.com>
2025-08-16 09:03:52 +09:00
Yukihiro "Matz" Matsumoto c28b29f5ef mruby-array-ext: refactor Array#product to avoid lambda and singleton method
Refactored `Array#product` to remove the use of a `lambda` and a dynamically
defined singleton method (`[]=` alias). This improves readability and reduces
Ruby object allocation overhead by separating block and non-block logic explicitly.
Explicit `return` statements were added to resolve an issue where `nil` was
incorrectly returned in certain scenarios.

Co-authored-by: Gemini <gemini@google.com>
2025-08-15 22:46:46 +09:00
Yukihiro "Matz" Matsumoto ad2757d6b5 mruby-array-ext: optimize Array#product by using __product_group C helper
Implemented `__product_group` in C to efficiently construct the intermediate
group arrays within Array#product. This reduces Ruby interpreter overhead
and improves performance for Array#product, especially for large inputs.

Co-authored-by: Gemini <gemini@google.com>
2025-08-15 22:38:53 +09:00
Yukihiro "Matz" Matsumoto 03478e6d2c mruby-array-ext: avoid heap allocation for temporary sets in array operations
The internal helper functions for array set operations now use a
stack-allocated `ary_set_t` instead of a heap-allocated one. This avoids
an unnecessary memory allocation for each call to `&`, `|`, `-`, `uniq!`,
and `intersect?`, improving performance by reducing overhead.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:53:07 +09:00
Yukihiro "Matz" Matsumoto f9243aa67a mruby-array-ext: replace ruby hash with khash.h for set operations
Replace Ruby Hash usage in array set operations with khash.h for better
memory efficiency and performance. This affects operations on arrays
larger than 32 elements.

Changes:
- Add KHASH_DECLARE/DEFINE for ary_set_t (set mode)
- Replace mrb_hash_* calls with kh_* equivalents
- Add helper functions for temporary set management
- Update all affected functions:
  * ary_subtract_internal (difference operations)
  * ary_union_internal (union operations)
  * ary_intersection_internal (intersection operations)
  * ary_intersect_p (intersection checking)
  * ary_uniq_bang (uniqueness operations)

Benefits:
- Better performance: direct C operations vs Ruby method calls
- Consistent with mruby core architecture using khash.h
- Eliminates unnecessary mrb_true_value() storage

Co-authored-by: Claude <noreply@anthropic.com>
2025-08-14 10:53:02 +09:00
Yukihiro "Matz" Matsumoto d1bd883526 mruby-array-ext: refactor set operations argument parsing
Introduces `ary_get_array_args` to centralize the argument parsing logic for
set operations, reducing code duplication in `ary_subtract_internal`,
`ary_union_internal`, and `ary_intersection_internal`. Also fixes a bug in
`ary_union_internal` where converted arguments were not being used.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:52 +09:00
Yukihiro "Matz" Matsumoto 16fbae065d mruby-array-ext: refactor set operations to use hash set helpers
Introduces `ary_update_hash_set` to centralize the logic for adding array
elements to a hash set. This helper is now used by `ary_to_hash_set`,
`ary_subtract_internal`, and `ary_intersection_internal`, reducing code
duplication.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:52 +09:00
Yukihiro "Matz" Matsumoto 19b6cacbb5 mruby-array-ext: refactor ary_compact to use ary_compact_bang
This removes code duplication by making ary_compact call
ary_compact_bang on a duplicated array, centralizing the compaction
logic. It also reorders the functions to remove the need for a forward
declaration.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:52 +09:00
Yukihiro "Matz" Matsumoto 2250171071 mruby-array-ext: refactor ary_uniq to use ary_uniq_bang
This removes code duplication by making ary_uniq call ary_uniq_bang on a
duplicated array, centralizing the uniqueness logic.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:52 +09:00
Yukihiro "Matz" Matsumoto 17c671dce8 mruby-array-ext: fix use-after-free in ary_compact_bang
This commit fixes a use-after-free vulnerability in `ary_compact_bang` by
replacing pointer-based iteration with index-based loops. This prevents raw
pointers from becoming stale after a garbage collection cycle is triggered by
`mrb_ary_modify`.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:50 +09:00
Yukihiro "Matz" Matsumoto f88847841a mruby-array-ext: fix use-after-free in ary_slice_bang
This commit fixes a use-after-free vulnerability in `ary_slice_bang` by
replacing pointer-based operations with index-based operations. This prevents
raw pointers from becoming stale after a garbage collection cycle is triggered
by `mrb_ary_new_from_values`.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:50 +09:00
Yukihiro "Matz" Matsumoto 81726bacb8 mruby-array-ext: fix use-after-free in ary_uniq_bang
This commit fixes a use-after-free vulnerability in `ary_uniq_bang` by
replacing pointer-based iteration with index-based loops. This prevents raw
pointers from becoming stale after a garbage collection cycle is triggered by
functions like `mrb_hash_set` or `mrb_equal`.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:50 +09:00
Yukihiro "Matz" Matsumoto 96a9150580 mruby-array-ext: fix use-after-free in ary_uniq
This commit fixes a use-after-free vulnerability in `ary_uniq` by replacing
pointer-based iteration with index-based loops. This prevents raw pointers from
becoming stale after a garbage collection cycle is triggered by functions like
`mrb_hash_set`, `mrb_ary_push`, or `mrb_equal`.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:49 +09:00
Yukihiro "Matz" Matsumoto 48d9113b68 mruby-array-ext: fix use-after-free in ary_intersect_p
This commit fixes a use-after-free vulnerability in `ary_intersect_p` by
replacing pointer-based iteration with index-based loops. This prevents
raw pointers from becoming stale after a garbage collection cycle is
triggered by functions like `mrb_hash_set` or `mrb_equal`.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:49 +09:00
Yukihiro "Matz" Matsumoto 5640e1bd9e mruby-array-ext: fix use-after-free in ary_rotate
This commit fixes a use-after-free vulnerability in `ary_rotate` by replacing a
pointer-based loop with an index-based loop. This prevents a raw pointer from
becoming stale after a garbage collection cycle is triggered by `mrb_ary_push`.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:49 +09:00
Yukihiro "Matz" Matsumoto 6eaa585b80 mruby-array-ext: fix use-after-free in ary_compact
This commit fixes a use-after-free vulnerability in `ary_compact` by replacing
a pointer-based loop with an index-based loop. This prevents a raw pointer from
becoming stale after a garbage collection cycle is triggered by `mrb_ary_push`.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:49 +09:00
Yukihiro "Matz" Matsumoto 6c2a25aa1a mruby-array-ext: fix use-after-free in ary_subtract_internal
This commit fixes a use-after-free vulnerability in
`ary_subtract_internal` by replacing pointer-based iteration
with index-based loops. This prevents raw pointers from becoming
stale after a garbage collection cycle is triggered by functions like
`mrb_hash_set` or `mrb_ary_push`.

This change also ensures that array-like objects are correctly converted
to arrays before being used in the subtraction logic.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:49 +09:00
Yukihiro "Matz" Matsumoto 07b803e28a docs: replace xml-style markup with markdown in comments
Replace XML-style markup tags in comments with markdown equivalents:
- <code>...</code> to `...` (inline code)
- <tt>...</tt> to `...` (teletype/monospace)
- <i>...</i> to *...* (italics/emphasis)
- +...+ to `...` (parameter/variable references)

Updated 80+ files across core source, headers, mrbgems, and libraries
to use consistent markdown formatting in documentation comments.
Handled edge cases including special characters like <=> operators.

Co-authored-by: Atlassian Rovo Dev
2025-08-14 10:52:49 +09:00
Yukihiro "Matz" Matsumoto 95895789c8 mruby-array-ext: fix use-after-free in ary_intersection_internal
This commit fixes a use-after-free vulnerability in `ary_intersection_internal`
by replacing pointer-based iteration with index-based loops. This prevents raw
pointers from becoming stale after a garbage collection cycle is triggered by
functions like `mrb_hash_set` or `mrb_ary_push`.

This change also ensures that array-like objects are correctly converted to
arrays before being used in the intersection logic.

Co-authored-by: Gemini <gemini@google.com>
2025-08-14 10:52:49 +09:00
Yukihiro "Matz" Matsumoto 0cb5a4ba4b mruby-array-ext: fixed use-after-free in ary_union_internal() 2025-08-14 10:52:48 +09:00
Yukihiro "Matz" Matsumoto cf9596d339 mruby-array-ext: add comprehensive documentation for values_at and internal helpers
- Add complete call-seq documentation for Array#values_at method
- Add helpful comments for internal helper functions:
  * ary_ref: helper function for values_at
  * rev: helper function to reverse array elements in-place
  * flatten_internal: iterative stack-based flatten implementation
  * Updated comments for fill, uniq, normalize_index, and fetch helpers
- Improves code maintainability and follows mruby documentation standards
- Achieves 100% public API documentation coverage

Co-authored-by: Atlassian Rovo Dev
2025-07-12 08:38:39 +09:00
Yukihiro "Matz" Matsumoto 6dc73d2517 mruby-array-ext: unify array#- tests
Merged the separate "Array#-" and "Array#- with large arrays" test
blocks into a single comprehensive test. The unified test covers both
basic functionality (type checking, simple subtraction) and the
hash-based implementation for large arrays (>32 elements).

Co-authored-by: Atlassian Rovo Dev
2025-07-05 18:32:46 +09:00
Yukihiro "Matz" Matsumoto 69d278589d mruby-array-ext: add Array#deconstruct for pattern matching
Implement new method for Ruby 2.7+ pattern matching compatibility.
Returns the array itself to enable case/in pattern matching syntax.
Complements Hash#deconstruct_keys for complete pattern matching support.

Co-authored-by: Atlassian Rovo Dev
2025-07-01 22:34:01 +09:00
Yukihiro "Matz" Matsumoto f3c4d64a5e mruby-array-ext: optimize fetch_values for non-block case
Use the C-implemented `__fetch` for `Array#fetch_values` when no block
is given to improve performance.

Co-authored-by: Atlassian Rovo Dev
2025-06-30 12:17:22 +09:00
Yukihiro "Matz" Matsumoto 90fd382a9e mruby-array-ext: implement Array#fetch with hybrid approach
Moved Array#fetch from Ruby to C using hybrid implementation for
better performance. The C implementation handles all non-block cases
with unified API that eliminates Ruby conditional logic.

Key improvements:
- Fast C implementation for common cases (no blocks)
- Shared index normalization helper reusable for other methods
- Unified C call eliminates NONE sentinel comparison in Ruby
- Block cases use C helper for index normalization

Added comprehensive test coverage including edge cases, default values,
block handling, and error message format verification. Combined tests
to focus on functionality rather than implementation details.

Co-authored-by: Atlassian Rovo Dev
2025-06-30 12:17:21 +09:00
Yukihiro "Matz" Matsumoto 87c39d3c0b mruby-array-ext: implement Array#insert in C
This commit also corrects the behavior of `Array#insert` when a negative
index is out of bounds. It now raises an `IndexError`, which is
consistent with CRuby.

Co-authored-by: Gemini <gemini@google.com>
2025-06-30 12:10:34 +09:00
Yukihiro "Matz" Matsumoto f8451045fe mruby-array-ext: implement flatten and flatten! in C
This commit replaces the Ruby implementation of  and  with a C
implementation. The new implementation is iterative and uses a stack to
avoid deep recursion, which prevents stack overflows when flattening
deeply nested arrays.

Co-authored-by: Gemini <gemini@google.com>
2025-06-30 11:55:17 +09:00
Yukihiro "Matz" Matsumoto ec7d94685d mruby-array-ext: implement fast path for uniq/uniq! in c
Co-authored-by: Gemini <gemini@google.com>
2025-06-30 10:26:43 +09:00
Yukihiro "Matz" Matsumoto 9e8cda73f6 mruby-array-ext: implement Array#fill in C
Implemented shared C argument parser and separate fill logic to eliminate code
duplication while maximizing performance. The implementation uses C implemented
__fill_parse_args for unified argument handling and __fill_exec for fast
C-based value filling.

Added comprehensive test coverage for both shared argument parsing
and C fill implementation, including range arguments, block handling,
and array extension scenarios.

Co-authored-by: Atlassian Rovo Dev
Co-authored-by: Gemini <gemini@google.com>
2025-06-30 10:26:42 +09:00
Yukihiro "Matz" Matsumoto c4464fa25a array.c: expose mrb_ary_dup() as a new C API 2025-06-29 20:46:51 +09:00
Yukihiro "Matz" Matsumoto 0afe69696c mruby-array-ext: implement Array#intersection in C and refactor Array#&
Co-authored-by: Gemini <gemini@google.com>
2025-06-29 20:46:51 +09:00
Yukihiro "Matz" Matsumoto 0725f691b4 mruby-array-ext: implement Array#union in C and refactor Array#|
Co-authored-by: Gemini <gemini@google.com>
2025-06-29 20:46:51 +09:00
Yukihiro "Matz" Matsumoto fdb0a664c6 mruby-array-ext: implement Array#difference in C and refactor Array#-
The Ruby implementation of `Array#difference` was inefficient as it
called `Array#-` repeatedly, creating intermediate arrays.

This commit replaces it with a C implementation that processes all
arguments in a single pass. The core logic is extracted into a
shared helper function, `ary_subtract_internal`, which is now used
by both `Array#-` and `Array#difference`.

Co-authored-by: Gemini <gemini@google.com>
2025-06-29 20:46:51 +09:00
Yukihiro "Matz" Matsumoto f205c2233d mruby-array-ext: increase SET_OP_HASH_THRESHOLD from 16 to 32
We have more chance to avoid hash allocation in set-like methods. Since
memory situation heavily depends on the platform, we may need to make
this threshold configurable in the future.

Co-authored-by: Atlassian Rovo Dev
2025-06-29 20:46:51 +09:00
Yukihiro "Matz" Matsumoto da813e0486 mruby-array-ext: implement Array#intersect? in C for better performance
Moved Array#intersect? implementation from Ruby to C to improve memory
usage and performance with early termination optimization. The C
implementation uses hash-based lookup for large arrays (>16 elements)
and linear search for smaller arrays.

Added comprehensive test coverage including early termination scenarios,
empty arrays, size optimization verification, and edge cases with
duplicates and large arrays.

Co-authored-by: Atlassian Rovo Dev
2025-06-29 20:46:50 +09:00
Yukihiro "Matz" Matsumoto ea5de2b8da mruby-array-ext: implement Array#& in C for better performance
Moved Array#& (set intersection) implementation from Ruby to C to improve
memory usage and performance. The C implementation uses hash-based
deduplication for large arrays (>16 elements) and linear search for
smaller arrays, following the same hybrid pattern as Array#| and Array#-.

Key improvements:
- Hash-based approach uses mrb_hash_delete_key() for proper deduplication
- Linear search approach checks result array to ensure uniqueness
- Maintains order preservation from the first array
- Eliminates temporary object creation in Ruby implementation

Added comprehensive test coverage for both small and large array scenarios,
including edge cases like no intersection, complete intersection, and
duplicate handling.

Co-authored-by: Atlassian Rovo Dev
2025-06-28 01:33:04 +09:00
Yukihiro "Matz" Matsumoto df35982297 mruby-parray-ext: implement Array#| in C for better performance
The C implementation uses hash-based deduplication for large arrays
(>16 elements) and linear search for smaller arrays, following the same
pattern as other set operations.

Co-authored-by: Atlassian Rovo Dev
2025-06-28 00:47:10 +09:00
Yukihiro "Matz" Matsumoto 409f39e911 mruby-array-ext: implement Array#- in C
Refactor Array#- to a C implementation for improved memory and performance,
especially for set operations. Uses a hybrid approach for efficiency.

Co-authored-by: Gemini <gemini@google.com>
2025-06-28 00:47:09 +09:00
Yukihiro "Matz" Matsumoto c7ffb0cc55 mruby-array-ext: add README.md
The document is written by Google Jules.
2025-06-07 11:46:11 +09:00
Yukihiro "Matz" Matsumoto da4cfbf89c mruby-array-ext: add a new method Array#fetch_values 2024-09-10 10:22:34 +09:00
Yukihiro "Matz" Matsumoto aa06432776 mruby-array-ext: index should be within mrb_int range
Type check is done by `__to_int` method.
2024-08-01 07:34:20 +09:00