Index: llvm/lib/Transforms/IPO/FunctionAttrs.cpp =================================================================== --- llvm/lib/Transforms/IPO/FunctionAttrs.cpp +++ llvm/lib/Transforms/IPO/FunctionAttrs.cpp @@ -702,6 +702,11 @@ }; CallBase &CB = cast(*I); + if (CB.isCallee(U)) { + IsRead = true; + Captures = false; // See comment in CaptureTracking for context + continue; + } if (CB.doesNotAccessMemory()) { AddUsersToWorklistIfCapturing(); continue; Index: llvm/test/Transforms/FunctionAttrs/nocapture.ll =================================================================== --- llvm/test/Transforms/FunctionAttrs/nocapture.ll +++ llvm/test/Transforms/FunctionAttrs/nocapture.ll @@ -128,7 +128,7 @@ } -; FNATTR: define void @nc3(void ()* nocapture %p) +; FNATTR: define void @nc3(void ()* nocapture readonly %p) define void @nc3(void ()* %p) { call void %p() ret void @@ -141,7 +141,7 @@ ret void } -; FNATTR: define void @nc5(void (i8*)* nocapture %f, i8* nocapture %p) +; FNATTR: define void @nc5(void (i8*)* nocapture readonly %f, i8* nocapture %p) define void @nc5(void (i8*)* %f, i8* %p) { call void %f(i8* %p) readonly nounwind call void %f(i8* nocapture %p) @@ -319,21 +319,21 @@ declare void @capture(i8*) -; FNATTR: define void @nocapture_fptr(i8* (i8*)* nocapture %f, i8* %p) +; FNATTR: define void @nocapture_fptr(i8* (i8*)* nocapture readonly %f, i8* %p) define void @nocapture_fptr(i8* (i8*)* %f, i8* %p) { %res = call i8* %f(i8* %p) call void @capture(i8* %res) ret void } -; FNATTR: define void @recurse_fptr(i8* (i8*)* nocapture %f, i8* %p) +; FNATTR: define void @recurse_fptr(i8* (i8*)* nocapture readonly %f, i8* %p) define void @recurse_fptr(i8* (i8*)* %f, i8* %p) { %res = call i8* %f(i8* %p) store i8 0, i8* %res ret void } -; FNATTR: define void @readnone_indirec(void (i8*)* nocapture readnone %f, i8* readnone %p) +; FNATTR: define void @readnone_indirec(void (i8*)* nocapture readonly %f, i8* readnone %p) define void @readnone_indirec(void (i8*)* %f, i8* %p) { call void %f(i8* %p) readnone ret void Index: llvm/test/Transforms/FunctionAttrs/writeonly.ll =================================================================== --- llvm/test/Transforms/FunctionAttrs/writeonly.ll +++ llvm/test/Transforms/FunctionAttrs/writeonly.ll @@ -92,19 +92,19 @@ ret void } -; CHECK: define void @fptr_test1(i8* %p, void (i8*)* nocapture %f) +; CHECK: define void @fptr_test1(i8* %p, void (i8*)* nocapture readonly %f) define void @fptr_test1(i8* %p, void (i8*)* %f) { call void %f(i8* %p) ret void } -; CHECK: define void @fptr_test2(i8* %p, void (i8*)* nocapture %f) +; CHECK: define void @fptr_test2(i8* %p, void (i8*)* nocapture readonly %f) define void @fptr_test2(i8* %p, void (i8*)* %f) { call void %f(i8* writeonly %p) ret void } -; CHECK: define void @fptr_test3(i8* %p, void (i8*)* nocapture %f) +; CHECK: define void @fptr_test3(i8* %p, void (i8*)* nocapture readonly %f) define void @fptr_test3(i8* %p, void (i8*)* %f) { call void %f(i8* %p) writeonly ret void