Skip to content

implement @memcpy and @memset for tuples #15479

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
andrewrk opened this issue Apr 26, 2023 · 4 comments
Open

implement @memcpy and @memset for tuples #15479

andrewrk opened this issue Apr 26, 2023 · 4 comments
Labels
bug Observed behavior contradicts documented or intended behavior enhancement Solving this issue will likely involve adding new logic or components to the codebase. frontend Tokenization, parsing, AstGen, Sema, and Liveness.
Milestone

Comments

@andrewrk
Copy link
Member

Extracted from #15278.

This test should pass:

const std = @import("std");
const expect = std.testing.expect;

test "memset a tuple" {
    var t: struct { i32, i32 } = .{ 12, 34 };
    @memset(&t, [_]i32{ 56, 78 });
    try expect(t[0] == 56);
    try expect(t[1] == 78);
}

test "memcpy a tuple" {
    var t1: struct { i32, i32 } = .{ 12, 34 };
    var t2: struct { i32, i32 } = .{ 56, 78 };
    @memset(&t1, &t2);
    try expect(t1[0] == 56);
    try expect(t1[1] == 78);
}

Instead, this happens:

$ stage4/bin/zig test test.zig 
test.zig:6:13: error: type '*test.test.memset a tuple__struct_1040' does not support indexing
    @memset(&t, [_]i32{ 56, 78 });
            ^~
test.zig:6:13: note: for loop operand must be an array, slice, tuple, or vector
test.zig:14:13: error: type '*test.test.memcpy a tuple__struct_1041' does not support indexing
    @memset(&t1, &t2);
            ^~~
test.zig:14:13: note: for loop operand must be an array, slice, tuple, or vector
@andrewrk andrewrk added bug Observed behavior contradicts documented or intended behavior enhancement Solving this issue will likely involve adding new logic or components to the codebase. frontend Tokenization, parsing, AstGen, Sema, and Liveness. labels Apr 26, 2023
@andrewrk andrewrk added this to the 0.12.0 milestone Apr 26, 2023
@InKryption
Copy link
Contributor

What's the use case behind this? Why would one opt for the builtins when we can already do foo = bar and foo = .{ 12, 14 }, bar = .{0} ** bar.len?

@andrewrk
Copy link
Member Author

andrewrk commented Apr 26, 2023

Same as the reason that @memcpy supports both src and dest being an array, even though it is equivalent to dest.* = src.*. The reason being language consistency.

@mlugg
Copy link
Member

mlugg commented Aug 27, 2023

To implement this reasonably, as well as for more general consistency between arrays and tuples, Zig should define homogeneous tuples (by which I mean tuples whose fields all have the same type) as having the same memory layout as arrays (i.e. fields laid out contiguously in memory with no extra padding). Is this something which the (theoretical) spec already guarantees? (As far as I know the implementation does, although I haven't checked.)

@mlugg
Copy link
Member

mlugg commented Feb 7, 2025

I think this is no longer intended behavior given our recent restriction of the definition of @memcpy.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Observed behavior contradicts documented or intended behavior enhancement Solving this issue will likely involve adding new logic or components to the codebase. frontend Tokenization, parsing, AstGen, Sema, and Liveness.
Projects
None yet
Development

No branches or pull requests

3 participants