snu-sf-class / swpp202401

Principles and Practices of Software Development Main Repository
14 stars 4 forks source link

[Project] Question about register endian #138

Open sbkim28 opened 6 months ago

sbkim28 commented 6 months ago

안녕하세요, 프로젝트 스펙과 관련하여 궁금한 점이 있어서 질문을 드리고자 합니다.

다음은 제가 임의로 작성한 LLVM IR 코드입니다.

define dso_local i32 @main() #0 {
entry:
  %v0 = insertelement <4 x i64> undef, i64 0, i32 0
  %v1 = insertelement <4 x i64> %v0, i64 1, i32 1

  %v32x8 = bitcast <4 x i64> %v3 to <8 x i32>

  %e0 = extractelement <8 x i32> %v32x8, i32 0
  %i0 = zext i32 %e0 to i64
  %e1 = extractelement <8 x i32> %v32x8, i32 1
  %i1 = zext i32 %e1 to i64
  %e2 = extractelement <8 x i32> %v32x8, i32 2
  %i2 = zext i32 %e2 to i64
  %e3 = extractelement <8 x i32> %v32x8, i32 3
  %i3 = zext i32 %e3 to i64
  call void @write(i64 noundef %i0)
  call void @write(i64 noundef %i1)
  call void @write(i64 noundef %i2)
  call void @write(i64 noundef %i3)
  ret i32 0
}

프로젝트 assembly spec에 따르면 register는 big-endian이므로, 저는 해당 코드가 0 0 0 1을 출력할 것으로 기대하였습니다.

그러나 실제 이를 실행해보면 0 0 1 0이 출력됩니다. vector register의 각 element가 little endian처럼 동작하는 것 같은데, 제가 assembly spec을 잘못 이해한 것인지 궁금하여 여쭙습니다.

감사합니다.

strikef commented 6 months ago

설명이 다소 부족했던 것 같습니다. 정확히는 scalar register의 경우 big endian으로 저장되지만 vector register의 경우 각 원소(?)의 순서는 little endian으로 저장되는 것이 맞습니다. 즉 64비트 scalar register에서 16비트만 떼온다고 하면 하위 (오른쪽) 16비트를 떼오는 게 맞지만, vector register에서 0번째 32비트 숫자 하나를 떼온다고 하면 상위(왼쪽) 32비트를 떼오게 됩니다. 이때도 떼온 32비트를 숫자로 해석할(?) 때는 다시 big endian으로 해석합니다.