func (this *Dispatcher) runDispatcherToReservationStation(input channel.Channel,
	rs *reservationstation.ReservationStation, rat *registeraliastable.RegisterAliasTable, rob *reorderbuffer.ReorderBuffer) {

	incomingQueue := map[uint32]*operation.Operation{}
	currentOperationId := this.StartOperationId()

	// For each operation received to schedule, process it
	for {
		value, running := <-input.Channel()
		if !running || !this.IsActive() {
			logger.Print(" => Flushing dispatcher unit %d (dispatcher to RS)", this.Index())
			return
		}
		op := operation.Cast(value)

		// Add to current operation
		incomingQueue[op.Id()] = op

		// Send to incoming channel pending ops (if available)
		for op, exists := incomingQueue[currentOperationId]; exists; op, exists = incomingQueue[currentOperationId] {

			// Allocate in ROB if there is spacde, otherwise stall
			rob.Allocate(op)

			// Rename register in case of WAR & WAR hazards
			if this.RegisterAliasTableEntries() > 0 {
				_, destRegister := rs.GetDestinationDependency(op.Id(), op.Instruction())
				if destRegister != -1 {
					found, _ := rat.AddMap(uint32(destRegister), op.Id())
					if !found {
						// Need to stall for an available RAT entry
						logger.Collect(" => [DI%d][%03d]: No entry available in RAT. Wait for one...", this.Index(), op.Id())
						break
					}

					// Rename to physical registers
					this.renameRegisters(op.Id(), op, rat)
				}
			}

			//Redirect input operations to the required execution unit channels
			logger.Collect(" => [DI%d][%03d]: Scheduling to RS: %s, %s", this.Index(), op.Id(), op.Instruction().Info.ToString(), op.Instruction().Data.ToString())
			rs.Schedule(op)
			currentOperationId += 1
		}
		input.Release()
	}
}
func (this *Dispatcher) renameRegisters(operationId uint32, op *operation.Operation, rat *registeraliastable.RegisterAliasTable) {

	if op.Instruction().Info.Type == data.TypeI {
		data := op.Instruction().Data.(*data.DataI)
		if !op.Instruction().Info.IsBranch() {
			opcode := op.Instruction().Info.Opcode
			if opcode != set.OP_SW && opcode != set.OP_SLI && opcode != set.OP_SUI {
				reg, _ := rat.GetPhysicalRegister(operationId, data.RegisterD.ToUint32())
				op.SetRenamedDestRegister(reg)
			}
		}
		op.Instruction().Data = data
	} else if op.Instruction().Info.Type == data.TypeR {
		data := op.Instruction().Data.(*data.DataR)
		reg, _ := rat.GetPhysicalRegister(operationId, data.RegisterD.ToUint32())
		op.SetRenamedDestRegister(reg)
	}
}