<div dir="ltr">Yes, investigating it. More details in PR.</div><br><div class="gmail_quote"><div dir="ltr">ut 21. 8. 2018 o 10:41 <<a href="mailto:douglas.yung@sony.com">douglas.yung@sony.com</a>> napísal(a):<br></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Hi David,<br>
<br>
One of our tests started to fail after your commit. I have put the details in PR38657 (<a href="https://bugs.llvm.org/show_bug.cgi?id=38657" rel="noreferrer" target="_blank">https://bugs.llvm.org/show_bug.cgi?id=38657</a>), can you please take a look?<br>
<br>
Douglas Yung<br>
<br>
> -----Original Message-----<br>
> From: llvm-commits [mailto:<a href="mailto:llvm-commits-bounces@lists.llvm.org" target="_blank">llvm-commits-bounces@lists.llvm.org</a>] On<br>
> Behalf Of David Bolvansky via llvm-commits<br>
> Sent: Thursday, August 09, 2018 21:33<br>
> To: <a href="mailto:llvm-commits@lists.llvm.org" target="_blank">llvm-commits@lists.llvm.org</a><br>
> Subject: [llvm] r339410 - [InstCombine] Transform str(n)cmp to memcmp<br>
> <br>
> Author: xbolva00<br>
> Date: Thu Aug  9 21:32:54 2018<br>
> New Revision: 339410<br>
> <br>
> URL: <a href="http://llvm.org/viewvc/llvm-project?rev=339410&view=rev" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project?rev=339410&view=rev</a><br>
> Log:<br>
> [InstCombine] Transform str(n)cmp to memcmp<br>
> <br>
> Summary:<br>
> Motivation examples:<br>
> int strcmp_memcmp() {<br>
>     char buf[12];<br>
>     return strcmp(buf, "key") == 0;<br>
> }<br>
> <br>
> int strcmp_memcmp2() {<br>
>     char buf[12];<br>
>     return strcmp(buf, "key") != 0;<br>
> }<br>
> <br>
> int strncmp_memcmp() {<br>
>     char buf[12];<br>
>     return strncmp(buf, "key", 3) == 0;<br>
> }<br>
> <br>
> can be turned to memcmp.<br>
> <br>
> See test file for more cases.<br>
> <br>
> Reviewers: efriedma<br>
> <br>
> Reviewed By: efriedma<br>
> <br>
> Subscribers: spatel, llvm-commits<br>
> <br>
> Differential Revision: <a href="https://reviews.llvm.org/D50233" rel="noreferrer" target="_blank">https://reviews.llvm.org/D50233</a><br>
> <br>
> Modified:<br>
>     llvm/trunk/lib/Transforms/Utils/SimplifyLibCalls.cpp<br>
>     llvm/trunk/test/Transforms/InstCombine/strcmp-memcmp.ll<br>
> <br>
> Modified: llvm/trunk/lib/Transforms/Utils/SimplifyLibCalls.cpp<br>
> URL: <a href="http://llvm.org/viewvc/llvm-" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-</a><br>
> project/llvm/trunk/lib/Transforms/Utils/SimplifyLibCalls.cpp?rev=339410<br>
> &r1=339409&r2=339410&view=diff<br>
> =======================================================================<br>
> =======<br>
> --- llvm/trunk/lib/Transforms/Utils/SimplifyLibCalls.cpp (original)<br>
> +++ llvm/trunk/lib/Transforms/Utils/SimplifyLibCalls.cpp Thu Aug  9<br>
> 21:32:54 2018<br>
> @@ -22,6 +22,7 @@<br>
>  #include "llvm/Transforms/Utils/Local.h"<br>
>  #include "llvm/Analysis/ValueTracking.h"<br>
>  #include "llvm/Analysis/CaptureTracking.h"<br>
> +#include "llvm/Analysis/Loads.h"<br>
>  #include "llvm/IR/DataLayout.h"<br>
>  #include "llvm/IR/Function.h"<br>
>  #include "llvm/IR/IRBuilder.h"<br>
> @@ -150,6 +151,29 @@ static bool isLocallyOpenedFile(Value *F<br>
>    return true;<br>
>  }<br>
> <br>
> +static bool isOnlyUsedInComparisonWithZero(Value *V) {<br>
> +  for (User *U : V->users()) {<br>
> +    if (ICmpInst *IC = dyn_cast<ICmpInst>(U))<br>
> +      if (Constant *C = dyn_cast<Constant>(IC->getOperand(1)))<br>
> +        if (C->isNullValue())<br>
> +          continue;<br>
> +    // Unknown instruction.<br>
> +    return false;<br>
> +  }<br>
> +  return true;<br>
> +}<br>
> +<br>
> +static bool canTransformToMemCmp(CallInst *CI, Value *Str, uint64_t<br>
> Len,<br>
> +                                 const DataLayout &DL) {<br>
> +  if (!isOnlyUsedInComparisonWithZero(CI))<br>
> +    return false;<br>
> +<br>
> +  if (!isDereferenceableAndAlignedPointer(Str, 1, APInt(64, Len), DL))<br>
> +    return false;<br>
> +<br>
> +  return true;<br>
> +}<br>
> +<br>
>  //===-----------------------------------------------------------------<br>
> -----===//<br>
>  // String and Memory Library Call Optimizations<br>
>  //===-----------------------------------------------------------------<br>
> -----===//<br>
> @@ -322,6 +346,21 @@ Value *LibCallSimplifier::optimizeStrCmp<br>
>                        B, DL, TLI);<br>
>    }<br>
> <br>
> +  // strcmp to memcmp<br>
> +  if (!HasStr1 && HasStr2) {<br>
> +    if (canTransformToMemCmp(CI, Str1P, Len2, DL))<br>
> +      return emitMemCmp(<br>
> +          Str1P, Str2P,<br>
> +          ConstantInt::get(DL.getIntPtrType(CI->getContext()), Len2),<br>
> B, DL,<br>
> +          TLI);<br>
> +  } else if (HasStr1 && !HasStr2) {<br>
> +    if (canTransformToMemCmp(CI, Str2P, Len1, DL))<br>
> +      return emitMemCmp(<br>
> +          Str1P, Str2P,<br>
> +          ConstantInt::get(DL.getIntPtrType(CI->getContext()), Len1),<br>
> B, DL,<br>
> +          TLI);<br>
> +  }<br>
> +<br>
>    return nullptr;<br>
>  }<br>
> <br>
> @@ -361,6 +400,26 @@ Value *LibCallSimplifier::optimizeStrNCm<br>
>    if (HasStr2 && Str2.empty()) // strncmp(x, "", n) -> *x<br>
>      return B.CreateZExt(B.CreateLoad(Str1P, "strcmpload"), CI-<br>
> >getType());<br>
> <br>
> +  uint64_t Len1 = GetStringLength(Str1P);<br>
> +  uint64_t Len2 = GetStringLength(Str2P);<br>
> +<br>
> +  // strncmp to memcmp<br>
> +  if (!HasStr1 && HasStr2) {<br>
> +    Len2 = std::min(Len2, Length);<br>
> +    if (canTransformToMemCmp(CI, Str1P, Len2, DL))<br>
> +      return emitMemCmp(<br>
> +          Str1P, Str2P,<br>
> +          ConstantInt::get(DL.getIntPtrType(CI->getContext()), Len2),<br>
> B, DL,<br>
> +          TLI);<br>
> +  } else if (HasStr1 && !HasStr2) {<br>
> +    Len1 = std::min(Len1, Length);<br>
> +    if (canTransformToMemCmp(CI, Str2P, Len1, DL))<br>
> +      return emitMemCmp(<br>
> +          Str1P, Str2P,<br>
> +          ConstantInt::get(DL.getIntPtrType(CI->getContext()), Len1),<br>
> B, DL,<br>
> +          TLI);<br>
> +  }<br>
> +<br>
>    return nullptr;<br>
>  }<br>
> <br>
> <br>
> Modified: llvm/trunk/test/Transforms/InstCombine/strcmp-memcmp.ll<br>
> URL: <a href="http://llvm.org/viewvc/llvm-" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-</a><br>
> project/llvm/trunk/test/Transforms/InstCombine/strcmp-<br>
> memcmp.ll?rev=339410&r1=339409&r2=339410&view=diff<br>
> =======================================================================<br>
> =======<br>
> --- llvm/trunk/test/Transforms/InstCombine/strcmp-memcmp.ll (original)<br>
> +++ llvm/trunk/test/Transforms/InstCombine/strcmp-memcmp.ll Thu Aug  9<br>
> 21:32:54 2018<br>
> @@ -11,8 +11,8 @@ declare void @use(i32)<br>
>  define i32 @strcmp_memcmp([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strcmp_memcmp(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0))<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -28,8 +28,8 @@ declare i32 @strcmp(i8* nocapture, i8* n<br>
>  define i32 @strcmp_memcmp2([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strcmp_memcmp2(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]])<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -43,8 +43,8 @@ define i32 @strcmp_memcmp2([12 x i8]* de<br>
>  define i32 @strcmp_memcmp3([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strcmp_memcmp3(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0))<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp ne i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp ne i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -58,8 +58,8 @@ define i32 @strcmp_memcmp3([12 x i8]* de<br>
>  define i32 @strcmp_memcmp4([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strcmp_memcmp4(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]])<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp ne i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp ne i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -73,8 +73,8 @@ define i32 @strcmp_memcmp4([12 x i8]* de<br>
>  define i32 @strcmp_memcmp5([5 x i8]* dereferenceable (5) %buf) {<br>
>  ; CHECK-LABEL: @strcmp_memcmp5(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [5 x i8], [5<br>
> x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strcmp(i8* nonnull align 1<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0))<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -88,8 +88,8 @@ define i32 @strcmp_memcmp5([5 x i8]* der<br>
>  define i32 @strcmp_memcmp6([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strcmp_memcmp6(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0))<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp sgt i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp sgt i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -103,9 +103,9 @@ define i32 @strcmp_memcmp6([12 x i8]* de<br>
>  define i32 @strcmp_memcmp7([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strcmp_memcmp7(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]])<br>
> -; CHECK-NEXT:    [[CALL_LOBIT:%.*]] = lshr i32 [[CALL]], 31<br>
> -; CHECK-NEXT:    ret i32 [[CALL_LOBIT]]<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 4)<br>
> +; CHECK-NEXT:    [[MEMCMP_LOBIT:%.*]] = lshr i32 [[MEMCMP]], 31<br>
> +; CHECK-NEXT:    ret i32 [[MEMCMP_LOBIT]]<br>
>  ;<br>
>    %string = getelementptr inbounds [12 x i8], [12 x i8]* %buf, i64 0,<br>
> i64 0<br>
>    %call = call i32 @strcmp(i8* getelementptr inbounds ([4 x i8], [4 x<br>
> i8]* @key, i64 0, i64 0), i8* nonnull %string)<br>
> @@ -117,8 +117,8 @@ define i32 @strcmp_memcmp7([12 x i8]* de<br>
>  define i32 @strcmp_memcmp8([4 x i8]* dereferenceable (4) %buf) {<br>
>  ; CHECK-LABEL: @strcmp_memcmp8(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [4 x i8], [4<br>
> x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0))<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -132,8 +132,8 @@ define i32 @strcmp_memcmp8([4 x i8]* der<br>
>  define i32 @strcmp_memcmp9([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strcmp_memcmp9(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([8 x i8], [8 x i8]* @abc, i64<br>
> 0, i64 0))<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([8 x i8], [8 x i8]* @abc, i64<br>
> 0, i64 0), i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -148,8 +148,8 @@ define i32 @strcmp_memcmp9([12 x i8]* de<br>
>  define i32 @strncmp_memcmp([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 2)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 2)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -165,8 +165,8 @@ declare i32 @strncmp(i8* nocapture, i8*<br>
>  define i32 @strncmp_memcmp2([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp2(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 11)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp ne i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp ne i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -180,8 +180,8 @@ define i32 @strncmp_memcmp2([12 x i8]* d<br>
>  define i32 @strncmp_memcmp3([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp3(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 11)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -195,8 +195,8 @@ define i32 @strncmp_memcmp3([12 x i8]* d<br>
>  define i32 @strncmp_memcmp4([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp4(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 5)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -210,8 +210,8 @@ define i32 @strncmp_memcmp4([12 x i8]* d<br>
>  define i32 @strncmp_memcmp5([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp5(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 5)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -226,8 +226,8 @@ define i32 @strncmp_memcmp5([12 x i8]* d<br>
>  define i32 @strncmp_memcmp6([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp6(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 5)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp ne i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp ne i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -241,8 +241,8 @@ define i32 @strncmp_memcmp6([12 x i8]* d<br>
>  define i32 @strncmp_memcmp7([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp7(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 4)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -256,8 +256,8 @@ define i32 @strncmp_memcmp7([12 x i8]* d<br>
>  define i32 @strncmp_memcmp8([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp8(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 3)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([4 x i8], [4 x i8]* @key, i64<br>
> 0, i64 0), i64 3)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -271,8 +271,8 @@ define i32 @strncmp_memcmp8([12 x i8]* d<br>
>  define i32 @strncmp_memcmp9([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp9(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 5)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp sgt i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp sgt i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -286,9 +286,9 @@ define i32 @strncmp_memcmp9([12 x i8]* d<br>
>  define i32 @strncmp_memcmp10([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp10(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 5)<br>
> -; CHECK-NEXT:    [[CALL_LOBIT:%.*]] = lshr i32 [[CALL]], 31<br>
> -; CHECK-NEXT:    ret i32 [[CALL_LOBIT]]<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 4)<br>
> +; CHECK-NEXT:    [[MEMCMP_LOBIT:%.*]] = lshr i32 [[MEMCMP]], 31<br>
> +; CHECK-NEXT:    ret i32 [[MEMCMP_LOBIT]]<br>
>  ;<br>
>    %string = getelementptr inbounds [12 x i8], [12 x i8]* %buf, i64 0,<br>
> i64 0<br>
>    %call = call i32 @strncmp(i8* getelementptr inbounds ([4 x i8], [4 x<br>
> i8]* @key, i64 0, i64 0), i8* nonnull %string, i64 5)<br>
> @@ -300,8 +300,8 @@ define i32 @strncmp_memcmp10([12 x i8]*<br>
>  define i32 @strncmp_memcmp11([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp11(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 12)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -315,8 +315,8 @@ define i32 @strncmp_memcmp11([12 x i8]*<br>
>  define i32 @strncmp_memcmp12([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp12(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 12)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* getelementptr<br>
> inbounds ([4 x i8], [4 x i8]* @key, i64 0, i64 0), i8* nonnull<br>
> [[STRING]], i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -330,8 +330,8 @@ define i32 @strncmp_memcmp12([12 x i8]*<br>
>  define i32 @strncmp_memcmp13([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp13(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([8 x i8], [8 x i8]* @abc, i64<br>
> 0, i64 0), i64 2)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([8 x i8], [8 x i8]* @abc, i64<br>
> 0, i64 0), i64 2)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> @@ -345,8 +345,8 @@ define i32 @strncmp_memcmp13([12 x i8]*<br>
>  define i32 @strncmp_memcmp14([12 x i8]* dereferenceable (12) %buf) {<br>
>  ; CHECK-LABEL: @strncmp_memcmp14(<br>
>  ; CHECK-NEXT:    [[STRING:%.*]] = getelementptr inbounds [12 x i8],<br>
> [12 x i8]* [[BUF:%.*]], i64 0, i64 0<br>
> -; CHECK-NEXT:    [[CALL:%.*]] = call i32 @strncmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([8 x i8], [8 x i8]* @abc, i64<br>
> 0, i64 0), i64 12)<br>
> -; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[CALL]], 0<br>
> +; CHECK-NEXT:    [[MEMCMP:%.*]] = call i32 @memcmp(i8* nonnull<br>
> [[STRING]], i8* getelementptr inbounds ([8 x i8], [8 x i8]* @abc, i64<br>
> 0, i64 0), i64 4)<br>
> +; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[MEMCMP]], 0<br>
>  ; CHECK-NEXT:    [[CONV:%.*]] = zext i1 [[CMP]] to i32<br>
>  ; CHECK-NEXT:    ret i32 [[CONV]]<br>
>  ;<br>
> <br>
> <br>
> _______________________________________________<br>
> llvm-commits mailing list<br>
> <a href="mailto:llvm-commits@lists.llvm.org" target="_blank">llvm-commits@lists.llvm.org</a><br>
> <a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits" rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits</a><br>
</blockquote></div>