일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | ||||||
2 | 3 | 4 | 5 | 6 | 7 | 8 |
9 | 10 | 11 | 12 | 13 | 14 | 15 |
16 | 17 | 18 | 19 | 20 | 21 | 22 |
23 | 24 | 25 | 26 | 27 | 28 |
Tags
- Linux custom packer
- Obfuscator
- LLVM Obfuscator
- anti debugging
- v8 optimizing
- Android
- on stack replacement
- 난독화
- pinpoint
- linux thread
- OSR
- Linux packer
- Injection
- custom packer
- tracing
- linux debugging
- pthread
- so inject
- 안티디버깅
- on-stack replacement
- LLVM
- v8 tracing
- android inject
- thread local storage
- tracerpid
- uftrace
- TLS
- LLVM 난독화
- apm
- initial-exec
Archives
- Today
- Total
Why should I know this?
[VectorCombine] Shuffle Kind 본문
SK_Select | Selects elements from the corresponding lane of either source operand. This is equivalent to a vector select with a constant condition operand. |
SK_PermuteTwoSrc | Merge elements from two source vectors into one with any shuffle mask. |
SK_PermuteSingleSrc | Shuffle elements of single source vector with any shuffle mask. |
#SK_Select
소스 피연산자의 해당 레인에서 요소를 선택합니다. 이는 상수 조건 피연산자를 가진 벡터 선택과 동일합니다.
예)
define <4 x float> @ext0_v4f32(<4 x float> %x, <4 x float> %y) {
; CHECK-LABEL: @ext0_v4f32(
; CHECK-NEXT: [[TMP1:%.*]] = fneg <4 x float> [[X:%.*]]
; CHECK-NEXT: [[R:%.*]] = shufflevector <4 x float> [[Y:%.*]], <4 x float> [[TMP1]], <4 x i32> <i32 4, i32 1, i32 2, i32 3>
; CHECK-NEXT: ret <4 x float> [[R]]
;
%e = extractelement <4 x float> %x, i32 0
%n = fneg float %e
%r = insertelement <4 x float> %y, float %n, i32 0
ret <4 x float> %r
}
https://github.com/ParkHanbum/llvm-project/commit/baab4aa1ba5f6
InstructionCost NewCost =
TTI.getArithmeticInstrCost(Instruction::FNeg, VecTy, CostKind) +
TTI.getShuffleCost(TargetTransformInfo::SK_Select, VecTy, Mask, CostKind);
위 커밋을 통해 SK_Select 가 의미하는 바를 추정하면,
벡터간 내부 요소의 순서를 변경하는 경우에 사용되는 것으로 보인다.
이 경우 다른 Shuffle 보다 비용이 "싸다"
#SK_PermuteTwoSrc
두 소스 벡터의 요소를 셔플 마스크를 사용하여 하나로 병합합니다.
define <8 x i32> @test1(<4 x i32> %0, <4 x i32> %1) {
; CHECK-LABEL: @test1(
; CHECK-NEXT: entry:
; CHECK-NEXT: [[TMP2:%.*]] = shufflevector <4 x i32> [[TMP0:%.*]], <4 x i32> [[TMP1:%.*]], <8 x i32> <i32 0, i32 1, i32 2, i32 3, i32 4, i32 5, i32 6, i32 7>
; CHECK-NEXT: [[TMP3:%.*]] = call <8 x i32> @llvm.abs.v8i32(<8 x i32> [[TMP2]], i1 false)
; CHECK-NEXT: ret <8 x i32> [[TMP3]]
;
entry:
%2 = call <4 x i32> @llvm.abs.v4i32(<4 x i32> %0, i1 false)
%3 = call <4 x i32> @llvm.abs.v4i32(<4 x i32> %1, i1 false)
%4 = shufflevector <4 x i32> %2, <4 x i32> %3, <8 x i32> <i32 0, i32 1, i32 2, i32 3, i32 4, i32 5, i32 6, i32 7>
ret <8 x i32> %4
}
위의 예처럼 두 개의 벡터를 하나로 합치는 경우
#SK_PermuteSingleSrc
단일 소스 벡터의 요소를 셔플 마스크와 함께 셔플합니다.
define <2 x double> @src_ins1_v2f64_ext3_v4f64(<2 x double> %a, <4 x double> %b) {
; CHECK-LABEL: @src_ins1_v2f64_ext3_v4f64(
; CHECK-NEXT: [[TMP1:%.*]] = shufflevector <4 x double> [[B:%.*]], <4 x double> poison, <2 x i32> <i32 3, i32 poison>
; CHECK-NEXT: [[INS:%.*]] = shufflevector <2 x double> [[A:%.*]], <2 x double> [[TMP1]], <2 x i32> <i32 0, i32 2>
; CHECK-NEXT: ret <2 x double> [[INS]]
;
%ext = extractelement <4 x double> %b, i32 3
%ins = insertelement <2 x double> %a, double %ext, i32 1
ret <2 x double> %ins
}
위의 예제와 같이 첫 번째 Shuffle 을 할 때, 지정대는 요소의 대상은 모두 Source 에 있는 경우.
Comments