I'm trying to implement *MUL_LOHI for my processor. My processor has mulxss (e.g.) that gives the 32 high bits of a 64 bit multiply. I tried this in ios2ISelDAGToDAG.cpp: /// Mul/Div with two results case ISD::SMUL_LOHI: case ISD::UMUL_LOHI: { SDValue Op1 = Node->getOperand(0); SDValue Op2 = Node->getOperand(1); AddToISelQueue(Op1); AddToISelQueue(Op2); unsigned Op; Op = (Opcode == ISD::UMUL_LOHI ? Nios2::MULxu : Nios2::MULx); SDNode *Hi = CurDAG->getTargetNode(Op, MVT::Flag, Op1, Op2); SDNode *Lo = CurDAG->getTargetNode(Nios2::MUL, MVT::Flag, Op1, Op2); if (!N.getValue(0).use_empty()) ReplaceUses(N.getValue(0), SDValue(Lo,0)); if (!N.getValue(1).use_empty()) ReplaceUses(N.getValue(1), SDValue(Hi,0)); return NULL; } The code generator complains: nios2-elf-ecc: /home/rich/llvm-trunk-new/lib/CodeGen/SelectionDAG/ScheduleDAG.cpp:141: void llvm::ScheduleDAG::BuildSchedUnits(): Assertion `N->getNodeId() == -1 && "Node already inserted!"' failed I'm guessing that's because I'm reusing Op1 and Op2. What is the right way to reuse DAG operands? -Rich
On Thu, Sep 11, 2008 at 6:09 PM, Richard Pennington <rich at pennware.com> wrote:> I'm trying to implement *MUL_LOHI for my processor. > > My processor has mulxss (e.g.) that gives the 32 high bits of a 64 bit > multiply.I haven't looked at the rest of the email carefully, but why aren't you just implementing MULHU and MULHS? There's no point to implementing the *MUL_LOHI variants if the processor doesn't have them. -Eli
This isn't due to node reuse. Rather it's the scheduler complaining of a malformed DAG. You should dump out the DAG before scheduling and look for multiple use of a FLAG value. Evan On Sep 11, 2008, at 6:09 PM, Richard Pennington wrote:> I'm trying to implement *MUL_LOHI for my processor. > > My processor has mulxss (e.g.) that gives the 32 high bits of a 64 bit > multiply. > > I tried this in ios2ISelDAGToDAG.cpp: > /// Mul/Div with two results > case ISD::SMUL_LOHI: > case ISD::UMUL_LOHI: { > SDValue Op1 = Node->getOperand(0); > SDValue Op2 = Node->getOperand(1); > AddToISelQueue(Op1); > AddToISelQueue(Op2); > > unsigned Op; > Op = (Opcode == ISD::UMUL_LOHI ? Nios2::MULxu : Nios2::MULx); > SDNode *Hi = CurDAG->getTargetNode(Op, MVT::Flag, Op1, Op2); > SDNode *Lo = CurDAG->getTargetNode(Nios2::MUL, MVT::Flag, Op1, > Op2); > if (!N.getValue(0).use_empty()) > ReplaceUses(N.getValue(0), SDValue(Lo,0)); > if (!N.getValue(1).use_empty()) > ReplaceUses(N.getValue(1), SDValue(Hi,0)); > return NULL; > } > > The code generator complains: > nios2-elf-ecc: > /home/rich/llvm-trunk-new/lib/CodeGen/SelectionDAG/ScheduleDAG.cpp: > 141: > void llvm::ScheduleDAG::BuildSchedUnits(): Assertion `N->getNodeId() > => -1 && "Node already inserted!"' failed > > I'm guessing that's because I'm reusing Op1 and Op2. > What is the right way to reuse DAG operands? > > -Rich > _______________________________________________ > LLVM Developers mailing list > LLVMdev at cs.uiuc.edu http://llvm.cs.uiuc.edu > http://lists.cs.uiuc.edu/mailman/listinfo/llvmdev
Eli Friedman wrote:> I haven't looked at the rest of the email carefully, but why aren't > you just implementing MULHU and MULHS? There's no point to > implementing the *MUL_LOHI variants if the processor doesn't have > them.I have implemented MULHU and MULHS. But if I take out my *MUL_LOHI stuff, the error I get is [~/ellcc/ellcc] main% ./nios2-elf-ecc -S test.c Cannot yet select: 0xaf93a34: i32,i32 = umul_lohi 0xaf9345c, 0xaf93924 What could I be doing to make the code generator think that umul_lohi is legal? -Rich