diff --git a/vlib/builtin/array_test.v b/vlib/builtin/array_test.v index d50ce493e2..eb3e0fdf6f 100644 --- a/vlib/builtin/array_test.v +++ b/vlib/builtin/array_test.v @@ -910,3 +910,25 @@ fn test_array_in_mut() { array_in_mut(mut a) assert a == [2,2] } + +// test array delete in function with mut argument +fn delete_nums(mut arr []int) { + arr.delete(0) +} + +fn test_array_delete_in_mut() { + mut nums := [1, 2, 3] + delete_nums(mut nums) + assert nums == [2, 3] +} + +// test array add in function with mut argument +fn add_nums(mut arr []int) { + arr << 4 +} + +fn test_array_add_in_mut() { + mut nums := [1, 2, 3] + add_nums(mut nums) + assert nums == [1, 2, 3, 4] +} diff --git a/vlib/crypto/aes/aes_cbc.v b/vlib/crypto/aes/aes_cbc.v index cbc540c4fa..811430cdb6 100644 --- a/vlib/crypto/aes/aes_cbc.v +++ b/vlib/crypto/aes/aes_cbc.v @@ -46,7 +46,8 @@ pub fn new_cbc(b AesCipher, iv []byte) AesCbc { pub fn (x &AesCbc) block_size() int { return x.block_size } -pub fn (x &AesCbc) encrypt_blocks(mut dst []byte, src_ []byte) { +pub fn (x &AesCbc) encrypt_blocks(mut dst_ []byte, src_ []byte) { + mut dst := *dst_ mut src := src_ if src.len%x.block_size != 0 { panic('crypto.cipher: input not full blocks') @@ -54,7 +55,7 @@ pub fn (x &AesCbc) encrypt_blocks(mut dst []byte, src_ []byte) { if dst.len < src.len { panic('crypto.cipher: output smaller than input') } - if subtle.inexact_overlap((*dst)[..src.len], src_) { + if subtle.inexact_overlap(dst[..src.len], src_) { panic('crypto.cipher: invalid buffer overlap') } @@ -62,17 +63,17 @@ pub fn (x &AesCbc) encrypt_blocks(mut dst []byte, src_ []byte) { for src.len > 0 { // Write the xor to dst, then encrypt in place. - cipher.xor_bytes(mut (*dst)[..x.block_size], src[..x.block_size], iv) - x.b.encrypt(mut (*dst)[..x.block_size], mut (*dst)[..x.block_size]) + cipher.xor_bytes(mut dst[..x.block_size], src[..x.block_size], iv) + x.b.encrypt(mut dst[..x.block_size], mut dst[..x.block_size]) // Move to the next block with this block as the next iv. - iv = (*dst)[..x.block_size] + iv = dst[..x.block_size] if x.block_size >= src.len { src = [] } else { src = src[x.block_size..] } - (*dst) = (*dst)[x.block_size..] + dst = dst[x.block_size..] } // Save the iv for the next crypt_blocks call. diff --git a/vlib/crypto/aes/aes_test.v b/vlib/crypto/aes/aes_test.v index 02d8b5ebd1..4cb26b1cc0 100644 --- a/vlib/crypto/aes/aes_test.v +++ b/vlib/crypto/aes/aes_test.v @@ -21,7 +21,8 @@ fn test_crypto_aes() { panic('ciphertext is not a multiple of the block size') } mode := aes.new_cbc(block, iv) - mode.encrypt_blocks(mut ciphertext, ciphertext) + cipher_clone := ciphertext.clone() + mode.encrypt_blocks(mut ciphertext, cipher_clone) assert ciphertext.hex() == 'c210459b514668ddc44674885e4979215265a6c44431a248421254ef357a8c2a308a8bddf5623af9df91737562041cf1' } diff --git a/vlib/v/gen/fn.v b/vlib/v/gen/fn.v index 4113b6e55e..f2b83d0810 100644 --- a/vlib/v/gen/fn.v +++ b/vlib/v/gen/fn.v @@ -624,11 +624,16 @@ fn (mut g Gen) ref_or_deref_arg(arg ast.CallArg, expected_type table.Type) { } else if arg_is_ptr && !expr_is_ptr { if arg.is_mut { if exp_sym.kind == .array { - // Special case for mutable arrays. We can't `&` function - // results, have to use `(array[]){ expr }[0]` hack. - g.write('&/*111*/(array[]){') - g.expr(arg.expr) - g.write('}[0]') + if arg.expr is ast.Ident && (arg.expr as ast.Ident).kind == .variable { + g.write('&/*arr*/') + g.expr(arg.expr) + } else { + // Special case for mutable arrays. We can't `&` function + // results, have to use `(array[]){ expr }[0]` hack. + g.write('&/*111*/(array[]){') + g.expr(arg.expr) + g.write('}[0]') + } return } }