/** Responsible for traversing within a design */ @Override protected void traverse(Design node) { if (_schedule.db) _schedule.ln(_schedule.GDA, "Traversing Design " + node); for (Task task : node.getTasks()) { ((Visitable) task).accept(this); } }
public void stateLogic(Module module, StateMachine mach, Design design) { /* * if(allGos) begin <statements> end */ SequentialBlock AllGos = new SequentialBlock(); ConditionalStatement ifAllGos = new ConditionalStatement(mach.getAllGoWire(), AllGos); // benchNumReads = benchNumReads + 1; // AllGos.add( new Assign.Blocking( benchNumReads, new org.xronos.openforge.verilog.model.Math.Add( benchNumReads, new Constant(1, benchNumReads.getWidth())))); // benchInReadZone = 1; // AllGos.add(new Assign.Blocking(benchInReadZone, new Constant(1, benchInReadZone.getWidth()))); /* * if(benchWorkInProgress === 0) begin benchWorkInProgress = 1; * benchFirstReadCycle = benchClockCount ; end */ SequentialBlock bwp = new SequentialBlock(); bwp.add(new Assign.Blocking(benchWorkInProgress, new Constant(1, benchInReadZone.getWidth()))); bwp.add(new Assign.Blocking(benchFirstReadCycle, benchClockCount)); Compare.EQ eq1 = new Compare.EQ(benchWorkInProgress, new Constant(0, benchWorkInProgress.getWidth())); ConditionalStatement ifbwp = new ConditionalStatement(eq1, bwp); AllGos.add(ifbwp); // benchReadZoneCyclesCounterSave = benchReadZoneCyclesCounter; AllGos.add(new Assign.Blocking(benchReadZoneCyclesCounterSave, benchReadZoneCyclesCounter)); // benchCoreCyclesCounter = 0; AllGos.add( new Assign.Blocking( benchCoreCyclesCounter, new Constant(0, benchCoreCyclesCounter.getWidth()))); /* * if(benchInWriteZone === 1) begin benchWriteZoneCycles = * benchWriteZoneCycles + benchWrietZoneCyclesCounterSave + 1; * benchWriteZoneCYlcesCounter = 0; benchInWriteZone = 0; end */ SequentialBlock bwz = new SequentialBlock(); bwz.add( new Assign.Blocking( benchWriteZoneCycles, new Math.Add( new Math.Add(benchWriteZoneCycles, benchWriteZoneCyclesCounterSave), new Constant(1, 32)))); bwz.add( new Assign.Blocking( benchWriteZoneCyclesCounter, new Constant(0, benchWriteZoneCyclesCounter.getWidth()))); bwz.add(new Assign.Blocking(benchInWriteZone, new Constant(0, benchInWriteZone.getWidth()))); Compare.EQ eq2 = new Compare.EQ(benchInWriteZone, new Constant(1, benchInWriteZone.getWidth())); ConditionalStatement ifbwz = new ConditionalStatement(eq2, bwz); AllGos.add(ifbwz); /* * if(benchIdleFlag == 1) begin benchIdleCycles = benchIdleCycles + * benchIdleCyclesCounter - 1; benchIdleFlag = 0; end */ SequentialBlock bif = new SequentialBlock(); bif.add( new Assign.Blocking( benchIdleCycles, new Math.Subtract( new Math.Add(benchIdleCycles, benchIdleCyclesCounter), new Constant(1, benchIdleCycles.getWidth())))); bif.add(new Assign.Blocking(benchIdleFlag, new Constant(0, benchIdleFlag.getWidth()))); Compare.EQ eq3 = new Compare.EQ(benchIdleFlag, new Constant(1, benchIdleFlag.getWidth())); ConditionalStatement ifbif = new ConditionalStatement(eq3, bif); AllGos.add(ifbif); /* * if(allDones) begin <statements> end */ SequentialBlock AllDones = new SequentialBlock(); ConditionalStatement ifAllDones = new ConditionalStatement(mach.getAllDoneWire(), AllDones); // benchNumWrites = benchNumWrites + 1; // AllDones.add( new Assign.Blocking( benchNumWrites, new Math.Add(benchNumWrites, new Constant(1, benchNumWrites.getWidth())))); // benchInWriteZone = 1; // AllDones.add( new Assign.Blocking(benchInWriteZone, new Constant(1, benchInWriteZone.getWidth()))); /* * if(benchInReadZone === 1) begin benchReadZoneCycles = * benchReadZoneCycles + benchReadZoneCyclesCounterSave + 1; * benchReadZoneCyclesCounter = 0; benchInReadZone = 0; * benchWriteZoneCyclesCounter = 0; benchCoreCycles = benchCoreCycles + * benchCoreCyclesCounetr end */ SequentialBlock brz = new SequentialBlock(); brz.add( new Assign.Blocking( benchReadZoneCycles, new Math.Add( new Math.Add(benchReadZoneCycles, benchReadZoneCyclesCounterSave), new Constant(1, benchReadZoneCycles.getWidth())))); brz.add( new Assign.Blocking( benchReadZoneCyclesCounter, new Constant(0, benchReadZoneCyclesCounter.getWidth()))); brz.add(new Assign.Blocking(benchInReadZone, new Constant(0, benchInReadZone.getWidth()))); brz.add( new Assign.Blocking( benchWriteZoneCyclesCounter, new Constant(0, benchWriteZoneCyclesCounter.getWidth()))); brz.add( new Assign.Blocking( benchCoreCycles, new Math.Add(benchCoreCycles, benchCoreCyclesCounter))); Compare.EQ eq4 = new Compare.EQ(benchInReadZone, new Constant(1, benchInReadZone.getWidth())); ConditionalStatement ifbrz = new ConditionalStatement(eq4, brz); AllDones.add(ifbrz); /* * if(allGos==1) begin benchCoreCycles = benchCoreCycles + 1; end */ AllDones.add( new ConditionalStatement( new Compare.EQ(mach.getAllGoWire(), new Constant(1, 1)), new Assign.Blocking( benchCoreCycles, new Math.Add(benchCoreCycles, new Constant(1, benchCoreCycles.getWidth()))))); // benchWriteZoneCyclesCounterSave = benchWriteZoneCyclesCounter; AllDones.add(new Assign.Blocking(benchWriteZoneCyclesCounterSave, benchWriteZoneCyclesCounter)); // benchLastWriteCycle = benchClockCount + 1; AllDones.add( new Assign.Blocking( benchLastWriteCycle, new Math.Add(benchClockCount, new Constant(1, benchClockCount.getWidth())))); // benchIdleFlag = 1; AllDones.add(new Assign.Blocking(benchIdleFlag, new Constant(1, benchIdleFlag.getWidth()))); // benchIdleCyclesCounter = 0; AllDones.add( new Assign.Blocking( benchIdleCyclesCounter, new Constant(0, benchIdleCyclesCounter.getWidth()))); /* * if(done) begin <statements> end */ SequentialBlock done = new SequentialBlock(); ConditionalStatement ifdone = new ConditionalStatement(mach.getDone(), done); // benchWriteZoneCycles = benchWriteZoneCycles + // benchWriteZoneCyclesCounterSave + 1; done.add( new Assign.Blocking( benchWriteZoneCycles, new Math.Add( new Math.Add(benchWriteZoneCycles, benchWriteZoneCyclesCounterSave), new Constant(1, benchWriteZoneCycles.getWidth())))); // benchTotalCycles = benchLastWriteCycle - benchFirstReadCycle; done.add( new Assign.Blocking( benchTotalCycles, new Math.Subtract(benchLastWriteCycle, benchFirstReadCycle))); // Find the number of input bytes and number of outputbytes // Collection<Task> tasks = design.getTasks(); // System.out.println("Number of tasks = " + tasks.size()); int inputsize = 0, outputsize = 0; Iterator<Task> iter = tasks.iterator(); while (iter.hasNext()) { Task task = iter.next(); Call call = task.getCall(); for (Port port : call.getDataPorts()) { inputsize += port.getSize(); } // System.out.println("Input Size Bits = " + inputsize); for (Bus bus : call.getExit(Exit.DONE).getDataBuses()) { outputsize += bus.getSize(); } // System.out.println("Output Size Bits = " + outputsize); } Constant benchArgSizeBytes = new Constant(inputsize / 8, 32); Constant benchResSizeBytes = new Constant(outputsize / 8, 32); Constant hunderd = new Constant(100, 32); // benchThroughput = (benchNumReads * // benchArgSizeBits/8.0)/(benchTotalCycles); done.add( new Assign.Blocking( benchThroughput, new Math.Divide( new Math.Multiply(benchNumReads, benchArgSizeBytes), benchTotalCycles))); // benchOverallInputUtil = (benchNumReads / benchTotalCycles) * 100.0; done.add( new Assign.Blocking( benchOverallInputUtil, new Math.Multiply(new Math.Divide(benchNumReads, benchTotalCycles), hunderd))); // benchOverallOutputUtil = (benchNumWrites / benchTotalCycles) * 100.0; done.add( new Assign.Blocking( benchOverallOutputUtil, new Math.Multiply(new Math.Divide(benchNumWrites, benchTotalCycles), hunderd))); // benchOverallCoreUtil = (benchCoreCycles / benchTotalCycles) * 100.0; done.add( new Assign.Blocking( benchOverallCoreUtil, new Math.Multiply(new Math.Divide(benchCoreCycles, benchTotalCycles), hunderd))); // benchIdlePercentage = (benchIdleCycles / benchTotalCycles) * 100.0; done.add( new Assign.Blocking( benchIdlePercentage, new Math.Multiply(new Math.Divide(benchIdleCycles, benchTotalCycles), hunderd))); // benchZoneInputUtil = (benchNumReads/benchReadZoneCycles) * 100.0; done.add( new Assign.Blocking( benchZoneInputUtil, new Math.Multiply(new Math.Divide(benchNumReads, benchReadZoneCycles), hunderd))); // benchZoneOutputUtil = (benchNumWrites/benchWriteZoneCycles) * 100.0; done.add( new Assign.Blocking( benchZoneOutputUtil, new Math.Multiply(new Math.Divide(benchNumWrites, benchWriteZoneCycles), hunderd))); // benchZoneCoreUtil = (benchCoreCycles/benchCoreCycles) * 100.0; done.add( new Assign.Blocking( benchZoneCoreUtil, new Math.Multiply(new Math.Divide(benchCoreCycles, benchCoreCycles), hunderd))); // WUSIWUG ! // CommaDelimitedStatement cds = new CommaDelimitedStatement(); cds.append( new StringStatement("**********************************************************\\n")); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); cds = new CommaDelimitedStatement(); cds.append( new StringStatement("******************** BENCHMARK REPORT ********************\\n")); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); cds = new CommaDelimitedStatement(); cds.append( new StringStatement("**********************************************************\\n")); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Total Number of Cycles : %0d\n", benchClockCount); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Total Number of Cycles : %0d\\n")); cds.append(benchClockCount); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Data Crunching Cycles : %0d\n", benchTotalCycles); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Data Crunching Cycles : %0d\\n")); cds.append(benchTotalCycles); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Number of Idle Cycles : %0d\n", benchIdleCycles); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Number of Idle Cycles : %0d\\n")); cds.append(benchIdleCycles); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Number of Reads : %0d\n", benchNumReads); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Number of Reads : %0d\\n")); cds.append(benchNumReads); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Bytes Consumed : %0g\n", benchNumReads * // benchArgSizeBits/8.0); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Bytes Consumed : %0d\\n")); cds.append(new Math.Multiply(benchNumReads, benchArgSizeBytes)); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Number of Writes : %0d\n", benchNumWrites); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Number of Writes : %0d\\n")); cds.append(benchNumWrites); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Bytes Produced : %0g\n", benchNumWrites * // benchResSizeBits/8.0); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Bytes Produced : %0d\\n")); cds.append(new Math.Multiply(benchNumWrites, benchResSizeBytes)); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "First Read Cycle : %0d\n", benchFirstReadCycle); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("First Read Cycle : %0d\\n")); cds.append(benchFirstReadCycle); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Last Write Cycle : %0d\n", benchLastWriteCycle); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Last Write Cycle : %0d\\n")); cds.append(benchLastWriteCycle); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Throughput(Bytes Consumed/Cycle) : %0g\n", benchThroughput); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Throughput(Bytes Consumed/Cycle) : %0g\\n")); cds.append(benchThroughput); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "****** Overall *******************************************\n"); cds = new CommaDelimitedStatement(); cds.append( new StringStatement("****** Overall *******************************************\\n")); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Overall Input Link Utilization : %0g\n", // benchOverallInputUtil); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Overall Input Link Utilization : %0g\\n")); cds.append(benchOverallInputUtil); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Overall Core Utilization : %0g\n", // benchOverallCoreUtil); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Overall Core Utilization : %0g\\n")); cds.append(benchOverallCoreUtil); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Overall Output Link Utilization : %0g\n", // benchOverallOutputUtil); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Overall Output Link Utilization : %0g\\n")); cds.append(benchOverallOutputUtil); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Percentage of Idle Cycles : %0g\n", benchIdlePercentage); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Percentage of Idle Cycles : %0g\\n")); cds.append(benchIdlePercentage); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "******** Zonal *******************************************\n"); cds = new CommaDelimitedStatement(); cds.append( new StringStatement("******** Zonal *******************************************\\n")); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Zone Input Link Utilization : %0g\n", benchZoneInputUtil); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Zone Input Link Utilization : %0g\\n")); cds.append(benchZoneInputUtil); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Zone Core Utilization : %0g\n", benchZoneCoreUtil); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Zone Core Utilization : %0g\\n")); cds.append(benchZoneCoreUtil); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "Zone Output Link Utilization : %0g\n", benchZoneOutputUtil); cds = new CommaDelimitedStatement(); cds.append(new StringStatement("Zone Output Link Utilization : %0g\\n")); cds.append(benchZoneOutputUtil); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); // $fwrite (benchmarkReportFile, // "**********************************************************\n"); cds = new CommaDelimitedStatement(); cds.append( new StringStatement("**********************************************************\\n")); done.add(new FStatement.FWrite(reportFile.getHandle(), cds)); SequentialBlock sblock = new SequentialBlock(); sblock.add(ifAllGos); sblock.add(ifAllDones); sblock.add(ifdone); // benchClockCount = benchClockCount + 1; sblock.add( new Assign.Blocking( benchClockCount, new Math.Add(benchClockCount, new Constant(1, benchClockCount.getWidth())))); // benchIdleCyclesCounter = benchIdleFlag == 1 ? benchIdleCyclesCounter // + 1 : benchIdleCyclesCounter; sblock.add( new ConditionalStatement( new Compare.EQ(benchIdleFlag, new Constant(1, benchIdleFlag.getWidth())), new Assign.Blocking( benchIdleCyclesCounter, new Math.Add( benchIdleCyclesCounter, new Constant(1, benchIdleCyclesCounter.getWidth()))), new Assign.Blocking(benchIdleCyclesCounter, benchIdleCyclesCounter))); // benchCoreCyclesCounter = benchCoreCyclesCounter + 1; sblock.add( new Assign.Blocking( benchCoreCyclesCounter, new Math.Add( benchCoreCyclesCounter, new Constant(1, benchCoreCyclesCounter.getWidth())))); // benchReadZoneCyclesCounter = benchInReadZone == 1 ? // benchReadZoneCyclesCounter + 1 : benchReadZoneCyclesCounter; sblock.add( new ConditionalStatement( new Compare.EQ(benchInReadZone, new Constant(1, benchInReadZone.getWidth())), new Assign.Blocking( benchReadZoneCyclesCounter, new Math.Add( benchReadZoneCyclesCounter, new Constant(1, benchReadZoneCyclesCounter.getWidth()))), new Assign.Blocking(benchReadZoneCyclesCounter, benchReadZoneCyclesCounter))); // benchWriteZoneCyclesCounter = benchInWriteZone == 1 ? // benchWriteZoneCyclesCounter + 1 : benchWriteZoneCyclesCounter; sblock.add( new ConditionalStatement( new Compare.EQ(benchInWriteZone, new Constant(1, benchInWriteZone.getWidth())), new Assign.Blocking( benchWriteZoneCyclesCounter, new Math.Add( benchWriteZoneCyclesCounter, new Constant(1, benchWriteZoneCyclesCounter.getWidth()))), new Assign.Blocking(benchWriteZoneCyclesCounter, benchWriteZoneCyclesCounter))); ProceduralTimingBlock ptb = new ProceduralTimingBlock( new EventControl(new EventExpression.PosEdge(mach.getClock())), sblock); module.state(new Always(ptb)); }
private void generateKickers() { final GenericJob job = EngineThread.getGenericJob(); final boolean blockIO = !job.getUnscopedBooleanOptionValue(OptionRegistry.NO_BLOCK_IO); // If // Do // BlockIO final boolean doBlockSched = !job.getUnscopedBooleanOptionValue(OptionRegistry.SCHEDULE_NO_BLOCK_SCHEDULING); final boolean moduleBuilder = EngineThread.getGenericJob().getUnscopedBooleanOptionValue(OptionRegistry.MODULE_BUILDER); final Map<String, Kicker> kickers = new HashMap<String, Kicker>(); for (Task task : design.getTasks()) { final Call call = task.getCall(); final String domainSpec = (String) ((OptionString) EngineThread.getGenericJob().getOption(OptionRegistry.CLOCK_DOMAIN)) .getValue(call.getSearchLabel()); if (!task.isKickerRequired()) { // Ensure that the Go port is validly connected if (!call.getGoPort().isConnected()) { job.warn("Task " + call.showIDLogical() + " is not autostart and has no enabling signal"); Constant constant = new SimpleConstant(0, 1, false); constant.pushValuesForward(); call.getGoPort().setBus(constant.getValueBus()); call.getGoPort().pushValueForward(); } continue; } Kicker kicker; final String kickerKey; if (doBlockSched && !moduleBuilder) { // Connect up a KickerContinuous that will keep us running at // max rate indefinately. We expect only one task in block // io, but if we have more than one, we need individual // kickers so that we use the right clock/reset for each. kicker = new Kicker.KickerContinuous(); // Use the kickers string b/c there will be a (unique) // feedback from the task done kickerKey = kicker.toString(); } else if (blockIO) { boolean fbRequired = checkFeedback(call.getProcedure().getBody()); // System.out.println("Generated perpetual kicker withT/withoutF " // + fbRequired + " feedback flop required"); // Connect up a KickerPerpetual that will keep us running // indefinately. We expect only one task in block io, but // if we have more than one, each needs its own kicker // anyway (since we OR back in the done). We could use // just one kicker for all and put the OR external but // there is no Design level module to put this stuff in. // Argh! kicker = new Kicker.KickerPerpetual(fbRequired); // Use the kickers string b/c there will be a (unique) // feedback from the task done kickerKey = kicker.toString(); } else { if (moduleBuilder) { continue; } // find a kicker that matches this calls clk and reset // kickerKey = call.getClockName() + call.getResetName(); kickerKey = domainSpec; kicker = kickers.get(kickerKey); // if we didn't find it, construct a new one if (kicker == null) { kicker = new Kicker(); } } if (!kickers.containsKey(kickerKey)) { kickers.put(kickerKey, kicker); design.addComponentToDesign(kicker); design.getClockDomain(domainSpec).connectComponentToDomain(kicker); } if (call.getGoPort().isUsed()) { call.getGoPort().setBus(kicker.getDoneBus()); } if (kicker.getRepeatPort() != null) { Bus callDone = call.getExit(Exit.DONE).getDoneBus(); if (!callDone.isUsed()) { // there is the off-chance that it has fixed timing // and thus needs no done. Create a sequence of flops // to bypass. if (!call.getLatency().isFixed()) { EngineThread.getEngine() .fatalError( "Unexpected internal state. Design does not have a control structure and has variable timing"); } Bus done = kicker.getDoneBus(); for (int i = 0; i < call.getLatency().getMinClocks(); i++) { // Needs RESET b/c it is in the control path Reg flop = Reg.getConfigurableReg(Reg.REGR, ID.showLogical(call) + "_go_done_" + i); design.getClockDomain(domainSpec).connectComponentToDomain(flop); flop.getInternalResetPort().setBus(flop.getResetPort().getBus()); flop.getDataPort().setBus(done); // Ensure that we've constant propagated the flop flop.propagateValuesForward(); done = flop.getResultBus(); design.addComponentToDesign(flop); } callDone = done; } kicker.getRepeatPort().setBus(callDone); } } }
/** * Creates Pins on the design to connect each task's I/O. * * @param design the Design to be connected */ @SuppressWarnings("deprecation") private void connectTasks(Design design) { // Map kickers = new HashMap(); for (Task task : design.getTasks()) { Call call = task.getCall(); // Note: when creating the InputPins, they are based on the related // procedure port instead of the call port, because the InputPin // needs // the Port's peer bus to get sizing information // might have a this port if (task.getCall().getThisPort() != null) { int width = task.getCall().getThisPort().getValue().getSize(); /* * The base address of the top level object reference is always * 0, since it isn't actually stored in memory. */ Constant constant = new SimpleConstant(0, width, false); task.setHiddenConstant(constant); } // If module_builder, then publish the ports, and don't use a kicker if (EngineThread.getGenericJob() .getUnscopedBooleanOptionValue(OptionRegistry.MODULE_BUILDER)) { // get the entry method EntryMethod em = call.getProcedure().getEntryMethod(); Port go = call.getGoPort(); if (go.isUsed()) { Pin p = connectInputPin(design, call, go, call.getGoName()); if (em != null) { p.setApiPin(em.getGoPin()); } } List<Port> dataPorts = new ArrayList<Port>(call.getDataPorts()); // 'this' port is handled specially. dataPorts.remove(call.getThisPort()); int index = 0; for (Port port : dataPorts) { if (port.getTag().equals(Component.NORMAL)) { if (port.isUsed()) { Pin p = connectInputPin(design, call, port, null); if (em != null) { p.setApiPin(em.getArgPin(index)); } } } index++; } Exit exit = call.getExit(Exit.DONE); Bus done = exit.getDoneBus(); if (done.isUsed()) { OutputPin pin = connectOutputPin(design, call, done, call.getProcedure().getDoneName()); if (em != null) { pin.setApiPin(em.getDonePin()); } } for (Bus bus : exit.getDataBuses()) { if (bus.getTag().equals(Component.NORMAL)) { if (bus.isUsed()) { OutputPin pin = connectOutputPin(design, call, bus, call.getProcedure().getResultName()); if (em != null) { pin.setApiPin(em.getResultPin()); } } } } } } }