<table border="1" cellspacing="0" cellpadding="8">
    <tr>
        <th>Issue</th>
        <td>
            <a href=https://github.com/llvm/llvm-project/issues/56295>56295</a>
        </td>
    </tr>

    <tr>
        <th>Summary</th>
        <td>
            [bug] LLVM IR Fixed array values are not returned correctly if larger than 64 bytes when using -O0 on arm64
        </td>
    </tr>

    <tr>
      <th>Labels</th>
      <td>
      </td>
    </tr>

    <tr>
      <th>Assignees</th>
      <td>
      </td>
    </tr>

    <tr>
      <th>Reporter</th>
      <td>
          IsaacShelton
      </td>
    </tr>
</table>

<pre>
    ### Details

**Description:**  When lowering, LLVM IR Fixed array values are not returned correctly if larger than 64 bytes when using -O0 on arm64
**Target:** arm64-apple-darwin21.4.0
**Version:** LLVM 14.0.6 and earlier (until at least LLVM 13.0.1)

### Abstract

Returning a fixed array value doesn't not seem to be correctly lowered when using -O0 on arm64 if the array is larger than 64 bytes.

This issue isn't for any particular language, but I found it using the following code:

```
import 'sys/cstdio.adept'

func getValues() 9 long {
    values 9 long
    
    repeat 9 {
        values[idx] = idx as long
    }
    
    return values
}

func main {
    values 9 long = getValues()
    
    repeat 9 {
        printf('%c\n', 'A'ub + values[idx] as ubyte)
    }
}
```

When the fixed arrays have 8 items (or equivalent 64 bytes), it works correctly. But as soon as you increase it to 9 (or any fixed array with >64 bytes), the LLVM IR is not lowered correctly anymore (at least for -O0 on arm64).

To demonstrate this, here are two LLVM IR files. The only difference between them, is that the size of the fixed arrays and iteration counts are increased from 8 to 9.

Both compile correctly when using `-O1`, but the `error.ll` does not when using `-O0`.

The expected output for both programs looks like this: (but `I` is only for `error.ll` since it shows 9 characters instead of 8):
```
A
B
C
D
E
F
G
H
I
```

However, when compiling `error.ll` with `-O0` you get:
```
A
A
A
A
A
A
A
y
A
```

### Complete LLVM IR

```
ok.ll
```
```
source_filename = ""
target datalayout = "e-m:o-i64:64-i128:128-n32:64-S128"
target triple = "arm64-apple-darwin21.4.0"

@S0 = internal constant [4 x i8] c"%c\0A\00"

declare i32 @printf(i8* %0, ...)

; Function Attrs: nounwind
define private [8 x i64] @a41() #0 {
  %1 = alloca [8 x i64], align 8
  %2 = alloca i64, align 8
  store [8 x i64] zeroinitializer, [8 x i64]* %1, align 8
  store i64 0, i64* %2, align 8
  br label %13

3:                                                ; preds = %13
  %4 = load i64, i64* %2, align 8
  %5 = load i64, i64* %2, align 8
  %6 = bitcast [8 x i64]* %1 to i64*
  %7 = getelementptr i64, i64* %6, i64 %5
  store i64 %4, i64* %7, align 8
  br label %8

8:                                                ; preds = %3
  %9 = load i64, i64* %2, align 8
  %10 = add i64 %9, 1
  store i64 %10, i64* %2, align 8
  br label %13

11:                                               ; preds = %13
  %12 = load [8 x i64], [8 x i64]* %1, align 8
  ret [8 x i64] %12

13:                                               ; preds = %8, %0
  %14 = load i64, i64* %2, align 8
  %15 = icmp ult i64 %14, 8
  br i1 %15, label %3, label %11
}

; Function Attrs: nounwind
define i32 @main() #0 {
  br label %20

1:                                                ; preds = %20
  %2 = alloca [8 x i64], align 8
  %3 = alloca i64, align 8
  %4 = call [8 x i64] @a41()
  store [8 x i64] %4, [8 x i64]* %2, align 8
  store i64 0, i64* %3, align 8
  br label %17

5:                                                ; preds = %17
  %6 = load i64, i64* %3, align 8
  %7 = bitcast [8 x i64]* %2 to i64*
  %8 = getelementptr i64, i64* %7, i64 %6
  %9 = load i64, i64* %8, align 8
  %10 = trunc i64 %9 to i8
  %11 = add i8 65, %10
  %12 = call i32 (i8*, ...) @printf(i8* getelementptr inbounds ([4 x i8], [4 x i8]* @S0, i32 0, i32 0), i8 %11)
  br label %13

13:                                               ; preds = %5
  %14 = load i64, i64* %3, align 8
  %15 = add i64 %14, 1
  store i64 %15, i64* %3, align 8
  br label %17

16:                                               ; preds = %17
  ret i32 0

17:                                               ; preds = %13, %1
  %18 = load i64, i64* %3, align 8
  %19 = icmp ult i64 %18, 8
  br i1 %19, label %5, label %16

20:                                               ; preds = %0
  br label %1
}

attributes #0 = { nounwind }
```

```
error.ll
```
```
source_filename = ""
target datalayout = "e-m:o-i64:64-i128:128-n32:64-S128"
target triple = "arm64-apple-darwin21.4.0"

@S0 = internal constant [4 x i8] c"%c\0A\00"

declare i32 @printf(i8* %0, ...)

; Function Attrs: nounwind
define private [9 x i64] @a41() #0 {
  %1 = alloca [9 x i64], align 8
  %2 = alloca i64, align 8
  store [9 x i64] zeroinitializer, [9 x i64]* %1, align 8
  store i64 0, i64* %2, align 8
  br label %13

3:                                                ; preds = %13
  %4 = load i64, i64* %2, align 8
  %5 = load i64, i64* %2, align 8
  %6 = bitcast [9 x i64]* %1 to i64*
  %7 = getelementptr i64, i64* %6, i64 %5
  store i64 %4, i64* %7, align 8
  br label %8

8:                                                ; preds = %3
  %9 = load i64, i64* %2, align 8
  %10 = add i64 %9, 1
  store i64 %10, i64* %2, align 8
  br label %13

11:                                               ; preds = %13
  %12 = load [9 x i64], [9 x i64]* %1, align 8
  ret [9 x i64] %12

13:                                               ; preds = %8, %0
  %14 = load i64, i64* %2, align 8
  %15 = icmp ult i64 %14, 9
  br i1 %15, label %3, label %11
}

; Function Attrs: nounwind
define i32 @main() #0 {
  br label %20

1:                                                ; preds = %20
  %2 = alloca [9 x i64], align 8
  %3 = alloca i64, align 8
  %4 = call [9 x i64] @a41()
  store [9 x i64] %4, [9 x i64]* %2, align 8
  store i64 0, i64* %3, align 8
  br label %17

5:                                                ; preds = %17
  %6 = load i64, i64* %3, align 8
  %7 = bitcast [9 x i64]* %2 to i64*
  %8 = getelementptr i64, i64* %7, i64 %6
  %9 = load i64, i64* %8, align 8
  %10 = trunc i64 %9 to i8
  %11 = add i8 65, %10
  %12 = call i32 (i8*, ...) @printf(i8* getelementptr inbounds ([4 x i8], [4 x i8]* @S0, i32 0, i32 0), i8 %11)
  br label %13

13:                                               ; preds = %5
  %14 = load i64, i64* %3, align 8
  %15 = add i64 %14, 1
  store i64 %15, i64* %3, align 8
  br label %17

16:                                               ; preds = %17
  ret i32 0

17:                                               ; preds = %13, %1
  %18 = load i64, i64* %3, align 8
  %19 = icmp ult i64 %18, 9
  br i1 %19, label %5, label %16

20:                                               ; preds = %0
  br label %1
}

attributes #0 = { nounwind }
```
</pre>
<img width="1px" height="1px" alt="" src="http://email.email.llvm.org/o/eJztWllv2zgQ_jXyC2FDh3U9-CFHsw3QRYG26D4uaIm2uZVELUnFcX_9zlCHJVt24jToAm0CwxIlco6PM99wAi9FultYrld_yC3TlGfKsm8t-6r5dvFzy1Qieam5KCyveUbIXxtWkExsmeTF2nJvyIcPX_8k95_IHX9kKaFS0h15oFnFFAwYKYQmkulKFvA2EVKyRGc7wlcko3LNJNEbWpBgTpY7DUu2KL5SIJtMP9pEFCAkD-Z9u77gOr03yUyY0rLM2DSlcssL15nNZ3Z_zVcm1cAPY7UDs2YBoUVKGJUZB2ssN6oKzTNCNckYVbqZ6cFMx3LjIUwthldLpSVNdP_tJ-M0OkLJ6hAbkgqmCssNtQFIMZYTLciS9SAyIMOyE5AghHrDGqlcjeI561v0ZQOzuFKgnjfKV0KC-ztSUql5UoEIEFOsK7pmuLfLSpN7mFQBQlw3RqDSlcjAPBwlImUIax-XwG4-ZsjzUkgNyIZqpyz3LlE65WJGU1ZqeNhfuaqKhMDmfjXxA3sBiJMYkABFVnhdTyLw1wRY_Wr_eH8nWclgC-Phsv1Sy7_m6aPl3xLLuyVwS6g6FBbejkvGfW3F1Ma3M3te5JQXZ2w2ag88vcyPEhJQr8zK0HL9xPJvCnN7g1BDcIbVEu6ujxwGRysMjqHGzoXuZriL9bfJfhMA-4hWZEMfGIkgQliuMIMgqNi_FQfFrNBdLKI-MA7iaCvkN7WP9Bm5hjgDs5TA4FZkJyrCi0RC_jGcD5kRN3IxWPvZtOV6A1i-O1CCJrbEBEGPOdam0z7BQFYugKJAcpftmBAD4nHjYQ4JkrJcFJjvmoEerlDfBkQbutNb0Sle8QwykHwBW0QB-lK-WsG8ImGQ6HrLaihzA4rCvNXGbsW_w4LVMczUZCEDxUBl4AcQVc2xLVYpWUmRw04gYAOzrwXAlIi8BJN6CPSoBTZ6-tHB7W7yHtXDkEkp5CzL4NaQlsHycB2GyQHVMMIeS9ACRolKl1UN7RLtKKVYS5pjvgmIg4x_a4D0rnAvUDnIu0eNgIuBDtceGAPaExMdaiO2mFbJhiIHA9MDIEozmiKKJrG8cWZqwakvN_WlCf939eWuvvxRX97Xl_szGfIewuyBSUTRoFSD3iDVt7-O3BY9E_NNWTtj6vMvu8Fo1NR9_boBIzOmu5w5w-biG9o_KnQ4VKKSCfsbk6CgOTOEZ7kufsx7bco4SammGQXvdTuDTXNAQUw5ZJ93BaWdO0By3hV8TwvPrZ99xmcHojScVrJO0cljQbuq-Z7bn-26CBQQOwXNYMsgfCgwF3DmnDwSHiFtJsZ4w7OwCr4OJaUsyUw2ei4BqR0_w3IXA9s3qTWbzQ6PEd41uYOSYbL6SmtpEqGA9Aab01b2ihcMOf8BaQcMi9AwQAgr2Nymc6eplrCddr9YgF7HuEehYid0uBQNohlfF5Am-_lufz5OPJ6ltCHOgRnfmRS84JrD3O91BhwoMyg4J8XBNGIwMjrNZHdk8hLPKEuWGWFeH0kPgbvwD9EvoS6oJm46kQaKuXmaCeCSBojztsFj__IlgVmy5DrBEjQKGlJ6Lae3LmxPESxjOZTaUstjnUEzNLYdA45ODheET2Ae9SGPXgPyPuLx5fA5df7SNG09MmcAZ9RZ54cizHEu9_d8hDnu3uGj3Hxu_sCZ9JATUPLA8hckx5HlUX269O2-Ay_IEadOEp7kJaky3e2NWd3fBu7U0_F5tyXeYOQ4o4fwC1i1IWw8sZ8g0X5AuIMa-oJ4OIbV7ePpXsjW3tNs3RFZAtPOFI9z7N7yxFhIju3ySUr3nkq4QUfovwqlh0dkOx6uY7Z1PHuOn91Rfo6ew89hj5-DZxJhdJYItcQGtKVCY9lglrOny4gEfpPTjn3MSiZeTHo0x5j9CWbkiHPgaLHE_xuYhrB_kGqCqDe-IuYQZlwEXf2bumOMmjzfR-gZhn4NnvOfy28nAqbht15FqqntREnyfyRDnOA1SlKXIVhKavD7OsLXKXtNpPWRil6AbjxePaIT1SMe1IthLXGCvp9AxD_upz26Z6NFikJd4tDvMtWUHJQQXndlipz_b8zBw667fOvO_u_uLH55dxa_YncWP9WdxW_d2eXd2TFob93Z79GdxYfd2bPyp-nO4l-iO-sfwd66syfZ-iXd2YnicY7de93ZUUj-dt3ZMQJv3dlbd_bWnZ3X8VO6s5Hq8Ut1Z5N04aWxF9OJ5jpjC0ilZbVGhv4pP5OZVDJbbLQulfmlyx181lxvquUsETkMsuyhvUxLKf4BJTA0PwnBX2b4gRv7k83Cj0MvjFLHD9K546U2C2NvxZgXBCFL08ibGOAUegeuTfjCtV3XhsVwjexgtvITP4nTZRD4gR8t50AgDOp3NkPFMyHXE7kwNgA2Cl5mXGm1f0mVgqBirJVPK70RcnGvKE0-b1imRTExNi-Mwf8BlSlJBw">