[llvm-dev] RFC: Opaque pointer status and future direction

Tim Northover via llvm-dev llvm-dev at lists.llvm.org
Wed Dec 18 07:15:31 PST 2019

Hi all,

At the dev meeting I promised to update everyone on where my work with opaque
pointers is right now. It's taken me a while, but at least it's the same year!

Current Status

I've put two branches up at https://github.com/TNorthover/llvm-project:
"opaque-ptr" which has most of the real work so far; and "opaque-ptr-always"
that additionally has a patch to force every pointer to be opaque and see what
falls over. It's about 40 patches on top of master in a few categories.

1. Serialization: bitcode <-> in-memory <-> textual IR[0].
2. Relaxing assertions in Instruction constructors and the Verifier so
   that we don't assume every pointer has an element type.
3. Modifying passes and other components to get their element types from other
   sources when needed. This is where I see the bulk of the future work in LLVM

All of them are very much from my dev machine and not prepared for real review.

To give an idea of the work ahead, on "opaque-ptr-always", running "ninja check"
there are about 4500 failures.

Many of these are of course CHECK lines looking for typed pointers that LLVM
will never again print; we'll need some kind of script to automate
converting as many
of those tests as possible.

Byeond that, there are still about 800 assertion failures, but looking at the
backtraces I think that there are "only" 75ish distinct callsites[1] that would
have to be fixed, plus whatever's revealed behind them.

Future Direction

I think this work needs to happen more incrementally. It's really not great that
I've built up a backlog of 40 patches that only I have access to and can work

So at a high level I think we should put the serialization and Instruction
changes in sooner rather than later, giving us a largely undocumented[2] dialect
of IR with opaque pointers that we can write tests against to upstream the rest
of what I've done (and others can use to continue work in parallel if they're

The risk is of course that this becomes yet another unfinished feature we drag
around for years, with a corresponding maintenance burden. And it's a real risk,
I unfortunately don't have the go ahead to work on this full time.

But I don't think the alternatives are much better. Even full time I don't think
I could do it completely alone because some choices will need input from
experts. Even if I could, it would finish with a patch bomb even bigger than
what I'm dropping here.


Short term (because otherwise we can't do it for another six months):

1. Add inalloca(<ty>) support.
2. Document for January release the planned removal of:
  * Old style byval
  * Old style inalloca
  * Typeless CreateCall, CreateLoad, CreateGEP.
3. Soon after January branch, strip out those bits. The third in
particular should prevent front-end regression, I had to fix a fair
few new deprecated callsites in Clang when rebasing everything this

Short/medium term:

1. Commit serialization and Instruction changes.
2. Use that to add tests for patches I already have and upstream them.
3. Keep fixing the issues, but no-one not working on opaque pointers should need
   to change their behaviour other than a general encouragement to not use
   getElementType unless they have to.

Long term:

As we get close to everything working, we should shift the expectations so that
new uses of getElementPtr aren't allowed in LLVM.

Front-ends (including Clang) will need more work I suspect.

No doubt there will be performance issues where having a pointee type helps some
heuristic be a bit better. We'll have to decide what to do about those.

[0] See attached opaque.ll for some proposed IR.
[1] See attached asserts.txt if interested.
[2] Or perhaps more likely documented with "don't use it unless you're working
on opaque pointers" warnings.
-------------- next part --------------
llvm::promoteLoopAccessesToScalars                                                                  63
llvm::Value::getPointerDereferenceableBytes                                                         58
llvm::TargetTransformInfoImplCRTPBase                                                               55
llvm::AMDGPU::HSAMD::MetadataStreamerV2::getValueType                                               36
getBaseAlign                                                                                        35
getAdjustedPtr                                                                                      33
llvm::InductionDescriptor::isInductionPHI                                                           32
promoteArguments                                                                                    29
isSupportedType                                                                                     28
matchIntrinsicType                                                                                  25
llvm::AMDGPU::HSAMD::MetadataStreamerV3::getValueType                                               24
llvm::getMallocAllocatedType                                                                        23
llvm::CallInst                                                                                      23
llvm::BTFDebug::processGlobals                                                                      21
llvm::CallSiteBase                                                                                  20
llvm::coro::Shape::getResumeFunctionType                                                            20
cloneInstructionWithNewAddressSpace                                                                 14
llvm::Function::getParamByValType                                                                   14
llvm::InstCombiner::visitAddrSpaceCast                                                              13
llvm::isSafeToLoadUnconditionally                                                                   13
isVectorPromotionViableForSlice                                                                     12
llvm::ARMTargetLowering::getTgtMemIntrinsic                                                         12
getVectorType                                                                                       12
llvm::ConstantFoldGetElementPtr                                                                     11
llvm::IRBuilderBase::CreateMaskedLoad                                                               9
llvm::TargetLowering::LowerCallTo                                                                   7
llvm::InterleavedAccessInfo::collectConstStrideAccesses                                             7
llvm::IRBuilderBase::CreateMaskedStore                                                              6
llvm::ObjectSizeOffsetVisitor::visitArgument                                                        6
genLoopLimit                                                                                        6
llvm::getCallsiteCost                                                                               6
llvm::InvokeInst                                                                                    6
BuildConstantFromSCEV                                                                               5
llvm::Value::getPointerAlignment                                                                    5
llvm::Interpreter::visitAllocaInst                                                                  5
llvm::IRBuilderBase::CreateMaskedScatter                                                            5
llvm::MemCpyOptPass::tryMergingIntoMemset                                                           5
llvm::InvokeInst::Create                                                                            4
llvm::ConstantHoistingPass::emitBaseConstants                                                       4
llvm::CallBase::getParamByValType                                                                   4
llvm::OpenMPIRBuilder::getOrCreateIdent                                                             3
getFoldedSizeOf                                                                                     3
llvm::NVPTXAsmPrinter::emitFunctionParamList                                                        3
llvm::GlobalAlias::create                                                                           3
llvm::IRBuilder                                                                                     3
llvm::SCEVExpander::expand                                                                          2
LLVMBuildCall                                                                                       2
llvm::fuzzerop::sizedPtrType                                                                        2
llvm::MemCpyOptPass::processByValArgument                                                           2
createMemMoveLoop                                                                                   2
cloneConstantExprWithNewAddressSpace                                                                2
llvm::FastISel::lowerCallTo                                                                         2
llvm::RISCVTargetLowering::getTgtMemIntrinsic                                                       2
llvm::SparcTargetLowering::LowerCall_32                                                             2
addByteCountSuffix                                                                                  2
tryToShorten                                                                                        2
llvm::InstCombiner::visitAllocaInst                                                                 2
llvm::MemCpyOptPass::performCallSlotOptzn                                                           2
LLVMBuildLoad                                                                                       1
LLVMAddAlias                                                                                        1
llvm::AMDGPU::HSAMD::MetadataStreamerV3::emitKernelArg                                              1
llvm::Function                                                                                      1
getFrameType                                                                                        1
eliminateSwiftErrorArgument                                                                         1
TryToShrinkGlobalToBoolean                                                                          1
llvm::InstCombiner::visitGetElementPtrInst                                                          1
rewriteGEPAsOffset                                                                                  1
llvm::ConstantFoldExtractElementInstruction                                                         1
canTailPredicateLoop                                                                                1
llvm::IRBuilderBase::CreateMaskedGather                                                             1
llvm::MemCpyOptPass::processMemSetMemCpyDependence                                                  1
llvm::slpvectorizer::BoUpSLP::isLoadCombineReductionCandidate                                       1
-------------- next part --------------
A non-text attachment was scrubbed...
Name: opaque.ll
Type: application/octet-stream
Size: 1538 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-dev/attachments/20191218/761e8893/attachment.obj>

More information about the llvm-dev mailing list