Ejemplo n.º 1
0
void
CPersCtl::PersCtl()
{
	if (PR_htValid) {
		switch (PR_htInst) {
		case CTL_INST1: {
			BUSY_RETRY(SendCallBusy_inst1());

			SendCall_inst1(CTL_INST2);
			break;
		}
		case CTL_INST2: {
			BUSY_RETRY(SendCallBusy_Inst22());

			SendCall_Inst22(CTL_RTN);
			break;
		}
		case CTL_RTN: {
			BUSY_RETRY(SendReturnBusy_htmain());

			SendReturn_htmain();
			break;
		}
		default:
			assert(0);
		}
	}
}
Ejemplo n.º 2
0
/**
 * @brief queries the database for a set of records to be inserted into a given tree
 *
 * @param searchTree pointer to a tree where insertions will be performed; can be NULL
 * @param query set of ports that a database record must match to be inserted into the tree
 *
 * The query method browses through the database, extracts all the descriptors matching
 * the given query parameter and inserts them into the given learning tree.
 * Note that this is an append procedure, the given tree needs not to be empty.
 * A "descriptor matching the query" is a descriptor whose port id is in the query map.
 * If the given tree is empty (NULL) a new tree is created and returned.
 * 
 * @return the tree root
 *
 * @internal
 */
IX_ETH_DB_PUBLIC
MacTreeNode* ixEthDBQuery(MacTreeNode *searchTree, IxEthDBPortMap query, IxEthDBRecordType recordFilter, UINT32 maxEntries)
{
    HashIterator iterator;
    UINT32 entryCount = 0;

    /* browse database */
    BUSY_RETRY(ixEthDBInitHashIterator(&dbHashtable, &iterator));

    while (IS_ITERATOR_VALID(&iterator))
    {
        MacDescriptor *descriptor = (MacDescriptor *) iterator.node->data;

        IX_ETH_DB_UPDATE_TRACE("DB: (PortUpdate) querying [%s]:%d on port map ... ", 
            mac2string(descriptor->macAddress), 
            descriptor->portID);

	if ((descriptor->type & recordFilter) != 0 
            && IS_PORT_INCLUDED(descriptor->portID, query))
	{
            MacDescriptor *descriptorClone = ixEthDBCloneMacDescriptor(descriptor);

            IX_ETH_DB_UPDATE_TRACE("match\n");

            if (descriptorClone != NULL)
            {
                /* add descriptor to tree */
                searchTree = ixEthDBTreeInsert(searchTree, descriptorClone);

                entryCount++;
            }
        }
        else
        {
            IX_ETH_DB_UPDATE_TRACE("no match\n");
        }

        if (entryCount < maxEntries)
        {
            /* advance to the next record */
	        BUSY_RETRY(ixEthDBIncrementHashIterator(&dbHashtable, &iterator));
        }
        else
        {
            /* the NPE won't accept more entries so we can stop now */
            ixEthDBReleaseHashIterator(&iterator);

            IX_ETH_DB_UPDATE_TRACE("DB: (PortUpdate) number of elements reached maximum supported by port\n");

            break;
        }
    }

    IX_ETH_DB_UPDATE_TRACE("DB: (PortUpdate) query inserted %d records in the search tree\n", entryCount);

    return ixEthDBTreeRebalance(searchTree);
}
Ejemplo n.º 3
0
IX_ETH_DB_PUBLIC
IxEthDBStatus ixEthDBDatabaseClear(IxEthDBPortId portID, IxEthDBRecordType recordType)
{
    IxEthDBPortMap triggerPorts;
    HashIterator iterator;

    if (portID >= IX_ETH_DB_NUMBER_OF_PORTS && portID != IX_ETH_DB_ALL_PORTS)
    {
        return IX_ETH_DB_INVALID_PORT;
    }

    /* check if the user passes some extra bits */
    if ((recordType | IX_ETH_DB_ALL_RECORD_TYPES) != IX_ETH_DB_ALL_RECORD_TYPES)
    {
        return IX_ETH_DB_INVALID_ARG;
    }

    SET_EMPTY_DEPENDENCY_MAP(triggerPorts);
    
    /* browse database and age entries */
    BUSY_RETRY(ixEthDBInitHashIterator(&dbHashtable, &iterator));

    while (IS_ITERATOR_VALID(&iterator))
    {
        MacDescriptor *descriptor = (MacDescriptor *) iterator.node->data;

        if (((descriptor->portID == portID) || (portID == IX_ETH_DB_ALL_PORTS))
            && ((descriptor->type & recordType) != 0))
        {
            /* add to trigger if automatic updates are required */
            if (ixEthDBPortUpdateRequired[descriptor->type])
            {
                /* add port to the set of update trigger ports */
                JOIN_PORT_TO_MAP(triggerPorts, descriptor->portID);
            }

            /* delete entry */
            BUSY_RETRY(ixEthDBRemoveEntryAtHashIterator(&dbHashtable, &iterator));
        }
        else
        {
            /* move to the next record */
            BUSY_RETRY(ixEthDBIncrementHashIterator(&dbHashtable, &iterator));
        }
    }

    /* update ports which lost records */
    ixEthDBUpdatePortLearningTrees(triggerPorts);
    
    return IX_ETH_DB_SUCCESS;
}
Ejemplo n.º 4
0
void
CPersVadd::PersVadd()
{
	if (PR_htValid) {
		switch (PR_htInst) {
		case VADD_ENTER: {
			BUSY_RETRY(ReadStreamBusy_A());
			BUSY_RETRY(ReadStreamBusy_B());
			BUSY_RETRY(WriteStreamBusy_C());

			S_sum = 0;

			if (!PR_vecLen) {
				HtContinue(VADD_RETURN);
				break;
			}

			MemAddr_t addrA = SR_op1Addr + PR_offset * sizeof(uint64_t);
			MemAddr_t addrB = SR_op2Addr + PR_offset * sizeof(uint64_t);
			MemAddr_t addrC = SR_resAddr + PR_offset * sizeof(uint64_t);

			ReadStreamOpen_A(addrA, PR_vecLen);
			ReadStreamOpen_B(addrB, PR_vecLen);
			WriteStreamOpen_C(addrC, PR_vecLen);

			WriteStreamPause_C(VADD_RETURN);
			break;
		}
		case VADD_RETURN: {
			BUSY_RETRY(SendReturnBusy_htmain());

			SendReturn_htmain(S_sum);
		}
		break;
		default:
			assert(0);
		}
	}

	if (ReadStreamReady_A() &&
	    ReadStreamReady_B() &&
	    WriteStreamReady_C()) {
		uint64_t a = ReadStream_A();
		uint64_t b = ReadStream_B();
		uint64_t c = a + b;

		S_sum += c;
		WriteStream_C(c);
	}
}
Ejemplo n.º 5
0
void
CPersRelu::PersRelu()
{
	if (PR_htValid) {
		switch (PR_htInst) {
		case RELU_LD1: {
			BUSY_RETRY(ReadMemBusy());

			// Memory read request
			//printf("calculate address  idx: %u", P_vecIdx);
			fflush(stdout);
			MemAddr_t memRdAddr = SR_op1Addr + (P_vecIdx << 3);
			//printf("About to read ");
			ReadMem_op1(memRdAddr);
			ReadMemPause(RELU_ST);
		}
		break;
		case RELU_ST: {
			BUSY_RETRY(WriteMemBusy());
			uint64_t basemask = 0x000000000000FFFF;
			P_result = 0;
			for(int i = 0; i < 64; i+=16){
				if((int16_t)(PR_op1 >> i) > 0){
					P_result = P_result | (PR_op1 & (basemask << i));
				}else{
					//Rectify the i'th element to 0
					//P_result = 0;
				}
			}
			//printf("ST op1: %ld => %ld\n",PR_op1, P_result);

			// Memory write request
			MemAddr_t memWrAddr = SR_resAddr + (P_vecIdx << 3);
			WriteMem(memWrAddr, P_result);
			WriteMemPause(RELU_RTN);
		}
		break;
		case RELU_RTN: {
			BUSY_RETRY(SendReturnBusy_relu());

			SendReturn_relu();
		}
		break;
		default:
			assert(0);
		}
	}
Ejemplo n.º 6
0
void
CPersOver::PersOver()
{
	if (PR_htValid) {
		switch (PR_htInstr) {
		case OVER_RD: {
			BUSY_RETRY(ReadMemBusy());

			ReadMem_data(P_addr);
			ReadMemPause(OVER_WR);
		}
		break;
		case OVER_WR: {
			BUSY_RETRY(WriteMemBusy());

			WriteMem(P_addr, ~PR_data);
			WriteMemPause(OVER_RSM);
		}
		break;
		case OVER_RSM: {
			S_bResume = true;
			HtPause(OVER_RTN);
		}
		break;
		case OVER_RTN: {
			BUSY_RETRY(SendReturnBusy_htmain());

			SendReturn_htmain();
		}
		break;
		default:
			assert(0);
		}
	}

	if (SR_bResume) {
		S_bResume = false;
		HtResume(0);
	}
}
Ejemplo n.º 7
0
void
CPersCtl::PersCtl()
{
	if (PR_htValid) {
		switch (PR_htInst) {
		case CTL_ENTRY: {
			S_sum = 0;
			P_result = 0;
			HtContinue(CTL_ADD);
		}
		break;
		case CTL_ADD: {
			BUSY_RETRY(SendCallBusy_add());

			if (P_vecIdx < SR_vecLen) {
				SendCallFork_add(CTL_JOIN, P_vecIdx);
				HtContinue(CTL_ADD);
				P_vecIdx += P_vecStride;
			} else {
				RecvReturnPause_add(CTL_RTN);
			}
		}
		break;
		case CTL_JOIN: {
			S_sum += P_result;
			RecvReturnJoin_add();
		}
		break;
		case CTL_RTN: {
			BUSY_RETRY(SendReturnBusy_htmain());

			SendReturn_htmain(S_sum);
		}
		break;
		default:
			assert(0);
		}
	}
}
Ejemplo n.º 8
0
void
CPersCtl::PersCtl()
{
	if (PR_htValid) {
		switch (PR_htInst) {
		case CTL_ENTRY: {
			printf("Task: %d\n",PR_task);

			if(PR_task == CONV_FORWARD ){
				BUSY_RETRY(SendCallBusy_conv_fwd());
				SendCall_conv_fwd(CTL_RTN, PR_rank, PR_rankStride);
			}
			else if(PR_task == CONV_BACKWARD_DATA ){
				BUSY_RETRY(SendCallBusy_load_filters());
				SendCall_load_filters(CTL_RTN, PR_rank, PR_rankStride,  PR_task);
			}
			else if(PR_task == CONV_BACKWARD_BIAS && PR_rank == 0 ){
				BUSY_RETRY(SendCallBusy_conv_back_bias());
				SendCall_conv_back_bias(CTL_RTN);
			}
			else if(PR_task == CONV_BACKWARD_FILTER ){
				BUSY_RETRY(SendCallBusy_load_filters());
				SendCall_load_filters(CTL_RTN, PR_rank, PR_rankStride,  PR_task);
			}
			else{
				HtContinue(CTL_RTN);
			}
		}
		break;
		case CTL_RTN: {
			BUSY_RETRY(SendReturnBusy_htmain());
			SendReturn_htmain();
		}
		break;
		default:
			assert(0);
		}
	}
}
Ejemplo n.º 9
0
void
CPersGupsCore::PersGupsCore()
{
    MemAddr_t rndIdx = SR_base + ((PR_ran & (SR_tblSize - 1)) << 3); // QW index
    if (PR_htValid) {
        switch (PR_htInst) {
            case PGC_ENTRY: {
                P_ran = (uint64_t)(PR_ran << 1) ^ ((int64_t) PR_ran < 0 ? POLY : 0);
		HtContinue(PGC_READ);
		break;
            }
            case PGC_READ: {
                BUSY_RETRY(ReadMemBusy());
                ReadMem_intData(rndIdx);
                ReadMemPause(PGC_WRITE);
		break;
            }
            case PGC_WRITE: {
                BUSY_RETRY(WriteMemBusy());
                WriteMem(rndIdx, PR_intData^PR_ran, /*orderChk=*/ false);
                P_ran = (uint64_t)(PR_ran << 1) ^ ((int64_t) PR_ran < 0 ? POLY : 0);
                P_vecIdx += 1;
                if (P_vecIdx < SR_vecLen) {
                    HtContinue(PGC_READ);
                } else
                    HtContinue(PGC_RTN);
		break;
            }
            case PGC_RTN: {
                BUSY_RETRY(SendReturnBusy_GupsCore());
                SendReturn_GupsCore();
		break;
            }
            default:
                assert(0);
        }
    }
}
Ejemplo n.º 10
0
void
CPersRepl::PersRepl()
{
	if (PR_htValid) {
		switch (PR_htInstr) {
		case REPL_RTN: {
			BUSY_RETRY(SendReturnBusy_repl());

			printf("InstInstID %d, InstReplID %d, ReplReplID %d\n", PR_instInstId, PR_instReplId, SR_replId);

			SendReturn_repl();
		}
		break;
		default:
			assert(0);
		}
	}
}
Ejemplo n.º 11
0
void
CPersInst::PersInst()
{
	if (PR_htValid) {
		switch (PR_htInst) {
		case INST_ENTRY: {
			HtContinue(INST_RTN);
			break;
		}
		case INST_RTN: {
			BUSY_RETRY(SendReturnBusy_inst());

			SendReturn_inst();
		}
		break;
		default:
			assert(0);
		}
	}
}
Ejemplo n.º 12
0
/**
 * @brief search a record in the Ethernet datbase
 *
 * @param macAddress MAC address to perform the search on
 * @param portID port ID to perform the search on
 * @param typeFilter type of records to consider for matching
 *
 * @warning if searching is successful an implicit write lock
 * to the search result is granted, therefore unlock the 
 * entry using @ref ixEthDBReleaseHashNode() as soon as possible.
 *
 * @see ixEthDBReleaseHashNode()
 *
 * @return the search result, or NULL if a record with the given
 * MAC address/port ID combination was not found
 *
 * @internal
 */
IX_ETH_DB_PUBLIC
HashNode* ixEthDBPortSearch(IxEthDBMacAddr *macAddress, IxEthDBPortId portID, IxEthDBRecordType typeFilter)
{
    HashNode *searchResult = NULL;
    MacDescriptor reference;
    
    if (macAddress == NULL)
    {
        return NULL;
    }
    
    /* fill search fields */
    memcpy(reference.macAddress, macAddress, sizeof (IxEthDBMacAddr));
    reference.portID = portID;
    
    /* set acceptable record types */
    reference.type = typeFilter;

    BUSY_RETRY(ixEthDBSearchHashEntry(&dbHashtable, IX_ETH_DB_MAC_PORT_KEY, &reference, &searchResult));

    return searchResult;
}
Ejemplo n.º 13
0
/**
 * @brief search a record in the Ethernet datbase
 *
 * @param macAddress MAC address to perform the search on
 * @param vlanID VLAN ID to perform the search on
 * @param typeFilter type of records to consider for matching
 *
 * @warning if searching is successful an implicit write lock
 * to the search result is granted, therefore unlock the 
 * entry using @ref ixEthDBReleaseHashNode() as soon as possible.
 *
 * @see ixEthDBReleaseHashNode()
 *
 * @return the search result, or NULL if a record with the given
 * MAC address/VLAN ID combination was not found
 *
 * @internal
 */
IX_ETH_DB_PUBLIC
HashNode* ixEthDBVlanSearch(IxEthDBMacAddr *macAddress, IxEthDBVlanId vlanID, IxEthDBRecordType typeFilter)
{
    HashNode *searchResult = NULL;
    MacDescriptor reference;
    
    if (macAddress == NULL)
    {
        return NULL;
    }
    
    /* fill search fields */
    memcpy(reference.macAddress, macAddress, sizeof (IxEthDBMacAddr));
    reference.recordData.filteringVlanData.ieee802_1qTag = 
            IX_ETH_DB_SET_VLAN_ID(reference.recordData.filteringVlanData.ieee802_1qTag, vlanID);
    
    /* set acceptable record types */
    reference.type = typeFilter;

    BUSY_RETRY(ixEthDBSearchHashEntry(&dbHashtable, IX_ETH_DB_MAC_VLAN_KEY, &reference, &searchResult));

    return searchResult;
}
Ejemplo n.º 14
0
/**
 * @brief search a record in the Ethernet datbase
 *
 * @param macAddress MAC address to perform the search on
 * @param typeFilter type of records to consider for matching
 *
 * @warning if searching is successful an implicit write lock
 * to the search result is granted, therefore unlock the 
 * entry using @ref ixEthDBReleaseHashNode() as soon as possible.
 *
 * @see ixEthDBReleaseHashNode()
 *
 * @return the search result, or NULL if a record with the given
 * MAC address was not found
 *
 * @internal
 */
IX_ETH_DB_PUBLIC
HashNode* ixEthDBSearch(IxEthDBMacAddr *macAddress, IxEthDBRecordType typeFilter)
{
    HashNode *searchResult = NULL;
    MacDescriptor reference;
    
    TEST_FIXTURE_INCREMENT_DB_CORE_ACCESS_COUNTER;

    if (macAddress == NULL)
    {
        return NULL;
    }

    /* fill search fields */
    memcpy(reference.macAddress, macAddress, sizeof (IxEthDBMacAddr));
    
    /* set acceptable record types */
    reference.type = typeFilter;
    
    BUSY_RETRY(ixEthDBSearchHashEntry(&dbHashtable, IX_ETH_DB_MAC_KEY, &reference, &searchResult));

    return searchResult;
}
Ejemplo n.º 15
0
void
CPersVadd::PersVadd()
{
    if (PR_htValid) {
        switch (PR_htInst) {
        case VADD_RESET:
            if (SR_msgDelay < 500 || SendHostMsgBusy()) {
                S_msgDelay += 1;
                HtRetry();
                break;
            }
            SendHostMsg(VADD_TYPE_SIZE, (XDIM_LEN << 8) | TYPE_SIZE);
            HtTerminate();
            break;
        case VADD_ENTER:
            S_yIdx[PR_htId] = 0;
            S_yDimLen[PR_htId] = PR_yDimLen;
            S_xIdx[PR_htId] = 0;
            S_xDimLen[PR_htId] = PR_xDimLen;
            S_sum[PR_htId] = 0;

            P_addrA = SR_addrA + PR_yAddrOff;
            P_addrB = SR_addrB + PR_yAddrOff;
            P_addrC = SR_addrC + PR_yAddrOff;

            HtContinue(VADD_OPEN);

            break;
        case VADD_OPEN:

            // Open read stream A, once for each xDim to be processed
            if (PR_yOpenAIdx < PR_yDimLen && !ReadStreamBusy_A(PR_htId)) {
                ht_uint32 remLen = (ht_uint32)((PR_yDimLen - PR_yOpenAIdx) * PR_xDimLen);
                ReadStreamOpen_A(PR_htId, PR_addrA, remLen > 0x3f ? (ht_uint6)0x3f : (ht_uint6)remLen, P_yOpenAIdx);

                P_addrA+= PR_xDimLen * TYPE_SIZE;
                P_yOpenAIdx += 1;
            }

            // Open read stream B, once for each xDim to be processed
            if (PR_yOpenBIdx < PR_yDimLen && !ReadStreamBusy_B(PR_htId)) {
                ReadStreamOpen_B(PR_htId, PR_addrB, PR_xDimLen);

                P_addrB += PR_xDimLen * TYPE_SIZE;
                P_yOpenBIdx += 1;
            }

            // Open write stream, once for each xDim to be processed
            if (PR_yOpenCIdx < SR_yDimLen[PR_htId] && !WriteStreamBusy_C(PR_htId)) {
#if VADD_STRM_RSP_GRP_HTID == 0 && VADD_HTID_W == 0 && VADD_RSP_GRP_W > 0
                WriteStreamOpen_C(PR_htId, 1u, PR_addrC);
#elif VADD_STRM_RSP_GRP_HTID || VADD_HTID_W == 0
                WriteStreamOpen_C(PR_htId, PR_addrC);
#else
                WriteStreamOpen_C(PR_htId, PR_htId ^ 1, PR_addrC);
#endif
                P_addrC += PR_xDimLen * TYPE_SIZE;
                P_yOpenCIdx += 1;
            }

            if (PR_yOpenAIdx == PR_yDimLen && PR_yOpenBIdx == PR_yDimLen && PR_yOpenCIdx == PR_yDimLen)
#if VADD_STRM_RSP_GRP_HTID == 0 && VADD_HTID_W == 0 && VADD_RSP_GRP_W > 0
                WriteStreamPause_C(1, VADD_RETURN);
#elif VADD_STRM_RSP_GRP_HTID || VADD_HTID_W == 0
                WriteStreamPause_C(VADD_RETURN);
#else
                WriteStreamPause_C(PR_htId ^ 1, VADD_RETURN);
#endif
            else
                HtContinue(VADD_OPEN);

            break;
        case VADD_RETURN: {
            BUSY_RETRY(SendReturnBusy_htmain());

            SendReturn_htmain(S_sum[PR_htId]);
        }
        break;
        default:
            assert(0);
        }
    }
Ejemplo n.º 16
0
/**
 * @brief adds a new entry to the Ethernet database
 *
 * @param newRecordTemplate address of the record template to use
 * @param updateTrigger port map containing the update triggers
 * resulting from this update operation
 *
 * Creates a new database entry, populates it with the data
 * copied from the given template and adds the record to the
 * database hash table.
 * It also checks whether the new record type is registered to trigger
 * automatic updates; if it is, the update trigger will contain the
 * port on which the record insertion was performed, as well as the
 * old port in case the addition was a record migration (from one port
 * to the other). The caller can use the updateTrigger to trigger
 * automatic updates on the ports changed as a result of this addition.
 *
 * @retval IX_ETH_DB_SUCCESS addition successful
 * @retval IX_ETH_DB_NOMEM insertion failed, no memory left in the mac descriptor memory pool
 * @retval IX_ETH_DB_BUSY database busy, cannot insert due to locking
 *
 * @internal
 */
IX_ETH_DB_PUBLIC
IxEthDBStatus ixEthDBAdd(MacDescriptor *newRecordTemplate, IxEthDBPortMap updateTrigger)
{
    IxEthDBStatus result;
    MacDescriptor *newDescriptor;
    IxEthDBPortId originalPortID;
    HashNode *node = NULL;

    BUSY_RETRY(ixEthDBSearchHashEntry(&dbHashtable, ixEthDBKeyType[newRecordTemplate->type], newRecordTemplate, &node));

    TEST_FIXTURE_INCREMENT_DB_CORE_ACCESS_COUNTER;

    if (node == NULL)
    {
        /* not found, create a new one */
        newDescriptor = ixEthDBAllocMacDescriptor();

        if (newDescriptor == NULL)
        {
            return IX_ETH_DB_NOMEM; /* no memory */
        }

        /* old port does not exist, avoid unnecessary updates */
        originalPortID = newRecordTemplate->portID;
    }
    else
    {
        /* a node with the same key exists, will update node */
        newDescriptor = (MacDescriptor *) node->data;

        /* save original port id */
        originalPortID = newDescriptor->portID;
    }

    /* copy/update fields into new record */
    memcpy(newDescriptor->macAddress, newRecordTemplate->macAddress, sizeof (IxEthDBMacAddr));
    memcpy(&newDescriptor->recordData, &newRecordTemplate->recordData, sizeof (IxEthDBRecordData));

    newDescriptor->type   = newRecordTemplate->type;
    newDescriptor->portID = newRecordTemplate->portID;
    newDescriptor->user   = newRecordTemplate->user;

    if (node == NULL)
    {
        /* new record, insert into hashtable */
        BUSY_RETRY_WITH_RESULT(ixEthDBAddHashEntry(&dbHashtable, newDescriptor), result);

        if (result != IX_ETH_DB_SUCCESS)
        {
            ixEthDBFreeMacDescriptor(newDescriptor);

            return result; /* insertion failed */
        }
    }

    if (node != NULL)
    {
        /* release access */
        ixEthDBReleaseHashNode(node);
    }

    /* trigger add/remove update if required by type */
    if (updateTrigger != NULL &&
        ixEthDBPortUpdateRequired[newRecordTemplate->type])
    {
        /* add new port to update list */
        JOIN_PORT_TO_MAP(updateTrigger, newRecordTemplate->portID);

        /* check if record has moved, we'll need to update the old port as well */
        if (originalPortID != newDescriptor->portID)
        {
            JOIN_PORT_TO_MAP(updateTrigger, originalPortID);
        }
    }

    return IX_ETH_DB_SUCCESS;
}
Ejemplo n.º 17
0
/**
 * @brief disables a port
 *
 * @param portID ID of the port to disable
 *
 * This function is fully documented in the
 * main header file, IxEthDB.h
 *
 * @return IX_ETH_DB_SUCCESS if disabling was
 * successful or an appropriate error message 
 * otherwise
 */
IX_ETH_DB_PUBLIC
IxEthDBStatus ixEthDBPortDisable(IxEthDBPortId portID)
{
    HashIterator iterator;
    IxEthDBPortMap triggerPorts; /* ports who will have deleted records and therefore will need updating */
    BOOL result;
    PortInfo *portInfo;
    IxEthDBFeature learningEnabled;
    IxEthDBPriorityTable classZeroTable;

    IX_ETH_DB_CHECK_PORT_EXISTS(portID);

    IX_ETH_DB_CHECK_SINGLE_NPE(portID);
    
    portInfo = &ixEthDBPortInfo[portID];

    if (!portInfo->enabled)
    {
        /* redundant */
        return IX_ETH_DB_SUCCESS;
    }

    if (ixEthDBPortDefinitions[portID].type == IX_ETH_NPE)
    {
        /* save filtering state */
        ixEthDBPortState[portID].firewallMode            = portInfo->firewallMode;
        ixEthDBPortState[portID].frameFilter             = portInfo->frameFilter;
        ixEthDBPortState[portID].taggingAction           = portInfo->taggingAction;
        ixEthDBPortState[portID].stpBlocked              = portInfo->stpBlocked;
        ixEthDBPortState[portID].srcAddressFilterEnabled = portInfo->srcAddressFilterEnabled;
        ixEthDBPortState[portID].maxRxFrameSize          = portInfo->maxRxFrameSize;
        ixEthDBPortState[portID].maxTxFrameSize          = portInfo->maxTxFrameSize;

        memcpy(ixEthDBPortState[portID].vlanMembership, portInfo->vlanMembership, sizeof (IxEthDBVlanSet));
        memcpy(ixEthDBPortState[portID].transmitTaggingInfo, portInfo->transmitTaggingInfo, sizeof (IxEthDBVlanSet));
        memcpy(ixEthDBPortState[portID].priorityTable, portInfo->priorityTable, sizeof (IxEthDBPriorityTable));

        ixEthDBPortState[portID].saved = TRUE;

        /* now turn off all EthDB filtering features on the port */

        /* VLAN & QoS */
        if ((portInfo->featureCapability & IX_ETH_DB_VLAN_QOS) != 0)
        {
            ixEthDBPortVlanMembershipRangeAdd((IxEthDBPortId) portID, 0, IX_ETH_DB_802_1Q_MAX_VLAN_ID);
            ixEthDBEgressVlanRangeTaggingEnabledSet((IxEthDBPortId) portID, 0, IX_ETH_DB_802_1Q_MAX_VLAN_ID, FALSE);
            ixEthDBAcceptableFrameTypeSet((IxEthDBPortId) portID, IX_ETH_DB_ACCEPT_ALL_FRAMES);
            ixEthDBIngressVlanTaggingEnabledSet((IxEthDBPortId) portID, IX_ETH_DB_PASS_THROUGH);

            memset(classZeroTable, 0, sizeof (classZeroTable));
            ixEthDBPriorityMappingTableSet((IxEthDBPortId) portID, classZeroTable);
        }

        /* STP */
        if ((portInfo->featureCapability & IX_ETH_DB_SPANNING_TREE_PROTOCOL) != 0)
        {
            ixEthDBSpanningTreeBlockingStateSet((IxEthDBPortId) portID, FALSE);
        }

        /* Firewall */
        if ((portInfo->featureCapability & IX_ETH_DB_FIREWALL) != 0)
        {
            ixEthDBFirewallModeSet((IxEthDBPortId) portID, IX_ETH_DB_FIREWALL_BLACK_LIST);
            ixEthDBFirewallTableDownload((IxEthDBPortId) portID);
            ixEthDBFirewallInvalidAddressFilterEnable((IxEthDBPortId) portID, FALSE);
        }

        /* Frame size filter */
        ixEthDBFilteringPortMaximumFrameSizeSet((IxEthDBPortId) portID, IX_ETH_DB_DEFAULT_FRAME_SIZE);

        /* WiFi */
        if ((portInfo->featureCapability & IX_ETH_DB_WIFI_HEADER_CONVERSION) != 0)
        {
            ixEthDBWiFiConversionTableDownload((IxEthDBPortId) portID);
        }

        /* save and disable the learning feature bit */
        learningEnabled          = portInfo->featureStatus & IX_ETH_DB_LEARNING;
        portInfo->featureStatus &= ~IX_ETH_DB_LEARNING;
    }
    else
    {
        /* save the learning feature bit */
        learningEnabled          = portInfo->featureStatus & IX_ETH_DB_LEARNING;
    }
    
    SET_EMPTY_DEPENDENCY_MAP(triggerPorts);
    
    ixEthDBUpdateLock();
    
    /* wipe out current entries for this port */
    BUSY_RETRY(ixEthDBInitHashIterator(&dbHashtable, &iterator));

    while (IS_ITERATOR_VALID(&iterator))
    {
        MacDescriptor *descriptor =  (MacDescriptor *) iterator.node->data;
    
        /* check if the port match. If so, remove the entry  */
        if (descriptor->portID == portID 
                && (descriptor->type == IX_ETH_DB_FILTERING_RECORD || descriptor->type == IX_ETH_DB_FILTERING_VLAN_RECORD)
                && !descriptor->recordData.filteringData.staticEntry)
        {
            /* delete entry */
            BUSY_RETRY(ixEthDBRemoveEntryAtHashIterator(&dbHashtable, &iterator));
            
            /* add port to the set of update trigger ports */
            JOIN_PORT_TO_MAP(triggerPorts, portID);
        }
        else
        {
            /* move to the next record */
            BUSY_RETRY(ixEthDBIncrementHashIterator(&dbHashtable, &iterator));
        }
    }
    
    if (ixEthDBPortDefinitions[portID].type == IX_ETH_NPE)
    {
        if (portInfo->updateMethod.searchTree != NULL)
        {
            ixEthDBFreeMacTreeNode(portInfo->updateMethod.searchTree);
            portInfo->updateMethod.searchTree = NULL;
        }

        ixEthDBNPEUpdateHandler(portID, IX_ETH_DB_FILTERING_RECORD);
    }

    /* mark as disabled */
    portInfo->enabled = FALSE;
    
    /* disable updates unless the user has specifically altered the default behavior */
    if (ixEthDBPortDefinitions[portID].type == IX_ETH_NPE)
    {
        if (!portInfo->updateMethod.userControlled)
        {  
            portInfo->updateMethod.updateEnabled = FALSE;
        }
            
        /* make sure we re-initialize the NPE learning tree when the port is re-enabled */
        portInfo->updateMethod.treeInitialized = FALSE;
    }

    ixEthDBUpdateUnlock();

    /* restore learning feature bit */
    portInfo->featureStatus |= learningEnabled;

    /* if we've removed any records or lost any events make sure to force an update */
    IS_EMPTY_DEPENDENCY_MAP(result, triggerPorts);

    if (!result)
    {
        ixEthDBUpdatePortLearningTrees(triggerPorts);
    }
    
    return IX_ETH_DB_SUCCESS;
}
Ejemplo n.º 18
0
void
CPersVwrk::PersVwrk()
{
	VertImages_t p1_vImgIdx = PR1_imageIdx & VERT_IMAGES_MASK;

	// staging for memAddr to allow Vivado to infer a DSP for the multiply
	T1_blkCol = (McuCols_t)((P1_outMcuColStart <<
			(S_jobInfo[p1_vImgIdx].m_vcp[P1_compIdx].m_blkColsPerMcu == 2 ? 1 : 0)) | P1_preMcuBlkCol);
	T1_blkRow = (McuRows_t)((P1_preMcuRow <<
			(S_jobInfo[p1_vImgIdx].m_vcp[P1_compIdx].m_blkRowsPerMcu == 2 ? 1 : 0)) | P1_preMcuBlkRow);
	T1_inCompBlkCols = S_jobInfo[p1_vImgIdx].m_vcp[P1_compIdx].m_inCompBlkCols;

	VertImages_t p2_vImgIdx = PR2_imageIdx & VERT_IMAGES_MASK;
	T2_jobInfo = S_jobInfo[p2_vImgIdx];
	// use signed math since the DSP adder is signed
	T2_memAddrSum1 = (ht_int48)(T2_jobInfo.m_vcp[P2_compIdx].m_pInCompBuf + (T2_blkCol << MEM_LINE_SIZE_W));
	T2_memAddrSum2 = (ht_int48)(T2_blkRow * (T2_inCompBlkCols << MEM_LINE_SIZE_W));

	T3_memAddr = T3_memAddrSum1 + T3_memAddrSum2; // will not use DSP adder because no output reg before use?

    T2_loopVcp = T2_jobInfo.m_vcp[P2_compIdx];

	T1_bReadMem = false;

	// fix timing for memory read instructions
	T2_preMcuRow_lt_inMcuRowEnd = PR2_preMcuRow < PR2_inMcuRowEnd;
	T2_pendMcuRow_lt_inMcuRowEnd = PR2_pendMcuRow < PR2_inMcuRowEnd;
	T2_mcuBufInUseCnt_lt_VERT_PREFETCH_MCUS = S_mcuBufInUseCnt[PR2_htId] < VERT_PREFETCH_MCUS_FULL;
	T2_preMcuBlkColP1_eq_blkColsPerMcu = PR2_preMcuBlkCol+1 == S_jobInfo[p2_vImgIdx].m_vcp[PR2_compIdx].m_blkColsPerMcu;

	if (PR3_htValid) {

		switch (PR3_htInst) {
		case VWRK_ENTRY: {

			if (!PR3_bHtIdPushed) {
				S_readOrderQue.push(PR3_htId);
				S_pendOrderQue.push(PR3_htId);
				P3_bHtIdPushed = true;
			}

			VertState vrs;
			vrs.m_bUpScale = T3_jobInfo.m_maxBlkRowsPerMcu == 2 && T3_loopVcp.m_blkRowsPerMcu == 1;
			ImageRows_t outRow = (ImageRows_t)(P3_outMcuRowStart * DCTSIZE << (T3_loopVcp.m_blkRowsPerMcu == 2 ? 1 : 0));
			ImageRows_t outRowEnd = (ImageRows_t)(outRow + ((4 * DCTSIZE) << (T3_loopVcp.m_blkRowsPerMcu == 2 ? 1 : 0)));
			if (outRowEnd > T3_loopVcp.m_outCompRows) outRowEnd = T3_loopVcp.m_outCompRows;

			ht_uint1 mcuBlkRowFirst;

			if (vrs.m_bUpScale) {
				PntWghtCpInt_t filterWidth = (PntWghtCpInt_t)((T3_jobInfo.m_filterWidth >> 1) + 1);
				PntWghtCpInt_t filterOffset = (PntWghtCpInt_t)(18 - (filterWidth << 1));
				PntWghtCpInt_t negFilterOffset = -filterOffset;
				bool bInRowSel = P3_pntWghtStart < negFilterOffset;
				vrs.m_inRow = bInRowSel ? 0 : ((P3_pntWghtStart + filterOffset) >> 1);
				vrs.m_rowDataPos = bInRowSel ? (PntWghtCpInt_t)-18 : (PntWghtCpInt_t)((P3_pntWghtStart & ~1) - (filterWidth << 1));
				vrs.m_inRowOutDiff = 0;
				vrs.m_inRowIgnore = 0;
				mcuBlkRowFirst = 0;
			} else {
				PntWghtCpInt_t filterWidth = (PntWghtCpInt_t)T3_jobInfo.m_filterWidth;
				PntWghtCpInt_t filterOffset = (PntWghtCpInt_t)(17 - filterWidth);
				PntWghtCpInt_t negFilterOffset = -filterOffset;
				bool bInRowSel = P3_pntWghtStart < negFilterOffset;
				vrs.m_inRow = bInRowSel ? (ImageRows_t)0 : (ImageRows_t)(P3_pntWghtStart + filterOffset);
				vrs.m_rowDataPos = bInRowSel ? -17 : (P3_pntWghtStart - filterWidth);
				vrs.m_inRowOutDiff = 0;
				vrs.m_inRowIgnore = 0;
				mcuBlkRowFirst = (ht_uint1)((vrs.m_inRow >> 3) & (T3_loopVcp.m_blkRowsPerMcu-1));
			}

			P3_preMcuBlkRowFirst[P3_compIdx] = mcuBlkRowFirst;
			P3_wrkMcuBlkRowFirst[P3_compIdx] = mcuBlkRowFirst;

			// setup for VWRK_LOOP
			P3_preMcuRow = (McuRows_t)(P3_inImageRowStart >> 
				((T3_jobInfo.m_maxBlkRowsPerMcu == 2 ? 1 : 0) + DCTSIZE_W));
			P3_pendMcuRow = P3_preMcuRow;
			P3_inMcuRowEnd = (McuRows_t)((P3_inImageRowEnd + 
				(T3_jobInfo.m_maxBlkRowsPerMcu == 2 ? 2 : 1) * DCTSIZE - 1) >>
				((T3_jobInfo.m_maxBlkRowsPerMcu == 2 ? 1 : 0) + DCTSIZE_W));
			P3_readBufIdx = 0;
			P3_pendBufIdx = 0;
			S_mcuBufInUseCnt[PR3_htId] = 0;
			P3_preMcuBlkRow = P3_preMcuBlkRowFirst[0];
			P3_preMcuBlkCol = 0;
			P3_rdReqGrpId = PR3_htId << VERT_PREFETCH_MCUS_W;
			P3_rdPollGrpId = PR3_htId << VERT_PREFETCH_MCUS_W;
			P3_mcuReadPendCnt = 0;
			P3_bFirstWorkMcu = true;
			
			P3_mcuBlkCol += 1;
			if (P3_mcuBlkCol == T3_loopVcp.m_blkColsPerMcu) {
				P3_mcuBlkCol = 0;
				P3_compIdx += 1;
				if (P3_compIdx == T3_jobInfo.m_compCnt) {
					P3_compIdx = 0;

					HtContinue(VWRK_PREREAD_WAIT);
					break;
				}
			}

			HtContinue(VWRK_ENTRY);
		}
		break;
		case VWRK_PREREAD_WAIT: {
			// wait for other threads to complete reads
			if (S_readBusy != 0 || S_readOrderQue.front() != PR3_htId) {
				S_readPaused[PR3_htId] = true;
				HtPause(VWRK_PREREAD_WAIT);
			} else {
				S_readPaused[PR3_htId] = false;
				S_readBusy = true;
				S_readHtId = PR3_htId;
				S_readOrderQue.pop();
				HtContinue(VWRK_PREREAD);
			}
		}
		break;
		case VWRK_PREREAD: {
			T1_bMcuBufFull = S_mcuBufInUseCnt[PR3_htId] == VERT_PREFETCH_MCUS_FULL;
			T1_bMcuRowEnd = P3_preMcuRow == P3_inMcuRowEnd;
			T1_bReadMemBusy = ReadMemBusy();

			// issue reads until all needed reads are issued or buffer space is exceeded
			BUSY_RETRY(ReadMemBusy());

#ifndef _HTV
			// these next statements were moved to the P1 stage to give the multiple additional registers stages
			McuRows_t blkRow = (McuRows_t)(P3_preMcuRow * (T3_loopVcp.m_blkRowsPerMcu == 2 ? 2 : 1) | P3_preMcuBlkRow);
			McuCols_t blkCol = (McuCols_t)(P3_outMcuColStart * (T3_loopVcp.m_blkColsPerMcu == 2 ? 2 : 1) | P3_preMcuBlkCol);
			ht_uint26 pos = (ht_uint26)((blkRow * T3_loopVcp.m_inCompBlkCols + blkCol) * MEM_LINE_SIZE);
			ht_uint48 memAddr = T3_loopVcp.m_pInCompBuf + pos;
			assert(memAddr == T3_memAddr);
#endif
			if (SR_mcuBufInUseCnt[PR3_htId] < VERT_PREFETCH_MCUS_FULL && PR3_preMcuRow < PR3_inMcuRowEnd) {
				sc_uint<4+VERT_PREFETCH_MCUS_W> bufIdx = (P3_compIdx << (VERT_PREFETCH_MCUS_W+2)) | 
					(P3_preMcuBlkRow << (VERT_PREFETCH_MCUS_W+1)) | (P3_preMcuBlkCol << VERT_PREFETCH_MCUS_W) | P3_readBufIdx;

				ReadMem_rowPref(T3_memAddr, bufIdx, PR3_htId, 0, 8);

				T1_bReadMem = true;

				if (TR3_preMcuBlkColP1_eq_blkColsPerMcu) {
					P3_preMcuBlkCol = 0;
					if (P3_preMcuBlkRow+1 == T3_loopVcp.m_blkRowsPerMcu) {
						if (P3_compIdx+1 == T3_jobInfo.m_compCnt) {
							P3_compIdx = 0;
							P3_preMcuRow += 1;
							P3_rdReqGrpId = (PR3_htId << VERT_PREFETCH_MCUS_W) | ((P3_rdReqGrpId+1) & (VERT_PREFETCH_MCUS-1));
							P3_preMcuBlkRowFirst[P3_compIdx] = 0;

							P3_readBufIdx += 1;
							P3_mcuReadPendCnt += 1;
							S_mcuBufInUseCnt[PR3_htId] += 1;

						} else
							P3_compIdx += 1;
						P3_preMcuBlkRow = P3_preMcuBlkRowFirst[P3_compIdx];
					} else
						P3_preMcuBlkRow += 1;
				} else
					P3_preMcuBlkCol += 1;

				HtContinue(VWRK_PREREAD);

			} else {
				if (PR3_preMcuRow == PR3_inMcuRowEnd) {
					// free read interface for next thread
					S_readBusy = false;
				}

				HtContinue(VWRK_VRS_WAIT);
			}
		}
		break;
		case VWRK_VRS_WAIT: {
			// wait until a vrs structure is available, we double buffer
			BUSY_RETRY(S_pendOrderQue.front() != PR3_htId || S_vrsAvl == 0);

			P3_vrsIdx = (S_vrsAvl & 1) ? 0 : 1;
			S_vrsAvl &= (S_vrsAvl & 1) ? 2u : 1u;
				
			HtContinue(VWRK_VRS_INIT);
		}
		break;
		case VWRK_VRS_INIT: {
			// init vrs structure

			VertState vrs;
			vrs.m_bUpScale = T3_jobInfo.m_maxBlkRowsPerMcu == 2 && T3_loopVcp.m_blkRowsPerMcu == 1;
			ImageRows_t outRow = (ImageRows_t)(P3_outMcuRowStart * DCTSIZE << (T3_loopVcp.m_blkRowsPerMcu == 2 ? 1 : 0));
			ImageRows_t outRowEnd = (ImageRows_t)(outRow + ((4 * DCTSIZE) << (T3_loopVcp.m_blkRowsPerMcu == 2 ? 1 : 0)));
			if (outRowEnd > T3_loopVcp.m_outCompRows) outRowEnd = T3_loopVcp.m_outCompRows;

			if (vrs.m_bUpScale) {
				PntWghtCpInt_t filterWidth = (PntWghtCpInt_t)((T3_jobInfo.m_filterWidth >> 1) + 1);
				PntWghtCpInt_t filterOffset = (PntWghtCpInt_t)(18 - (filterWidth << 1));
				PntWghtCpInt_t negFilterOffset = -filterOffset;
				bool bInRowSel = P3_pntWghtStart < negFilterOffset;
				vrs.m_inRow = bInRowSel ? 0 : ((P3_pntWghtStart + filterOffset) >> 1);
				vrs.m_rowDataPos = bInRowSel ? (PntWghtCpInt_t)-18 : (PntWghtCpInt_t)((P3_pntWghtStart & ~1) - (filterWidth << 1));
				vrs.m_inRowOutDiff = 0;
				vrs.m_inRowIgnore = 0;
			} else {
Ejemplo n.º 19
0
void
CPersStencil::PersStencil()
{
	if (PR_htValid) {
		switch (PR_htInst) {
		case STENCIL_ENTER: {
			// Split offset calucation from source stencil to destination location over
			// two cytles for timing. OFF = ((Y_ORIGIN * (PR_cols + X_SIZE-1) + X_ORIGIN) * sizeof(StType_t);
			//
			uint32_t offset = Y_ORIGIN * (PR_cols + X_SIZE-1);

			S_rdAddr = PR_rdAddr;
			S_wrAddr = offset;
			S_rdRowIdx = 0;
			S_wrRowIdx = Y_ORIGIN;
			S_cols = PR_cols;
			S_rows = PR_rows;
			S_coef = PR_coef;

			HtContinue(STENCIL_START);
		}
		break;
		case STENCIL_START: {
			S_bStart = true;

			S_wrAddr = ((uint32_t)S_wrAddr + X_ORIGIN) * sizeof(StType_t) + PR_wrAddr;

			StencilBufferInit_5x5r2((ht_uint11)PR_cols, (ht_uint11)PR_rows);

			HtContinue(STENCIL_WAIT);
		}
		break;
		case STENCIL_WAIT: {
			if (S_wrRowIdx == S_rows)
				WriteStreamPause(STENCIL_RETURN);
			else
				HtContinue(STENCIL_WAIT);
		}
		break;
		case STENCIL_RETURN: {
			BUSY_RETRY(SendReturnBusy_htmain());

			SendReturn_htmain();
		}
		break;
		default:
			assert(0);
		}
	}

	// start read stream per row
	if (SR_bStart && SR_rdRowIdx < SR_rows + Y_SIZE-1 && !ReadStreamBusy()) {
		ReadStreamOpen(SR_rdAddr, SR_cols + X_SIZE-1);
		S_rdAddr += (SR_cols + X_SIZE-1) * sizeof(StType_t);
		S_rdRowIdx += 1;
	}

	// start write stream per row
	if (SR_bStart && SR_wrRowIdx < SR_rows + Y_ORIGIN && !WriteStreamBusy()) {
		WriteStreamOpen(SR_wrAddr, SR_cols);
		S_wrAddr += (SR_cols + X_SIZE-1) * sizeof(StType_t);
		S_wrRowIdx += 1;
	}

	CStencilBufferIn_5x5r2 stIn;
	stIn.m_bValid = ReadStreamReady() && WriteStreamReady();
	stIn.m_data = stIn.m_bValid ? ReadStream() : 0;

	CStencilBufferOut_5x5r2 stOut;

	StencilBuffer_5x5r2(stIn, stOut);

	//
	// compute stencil
	//
	T1_bValid = stOut.m_bValid;

	for (uint32_t x = 0; x < X_SIZE; x += 1)
		for (uint32_t y = 0; y < Y_SIZE; y += 1)
			T1_mult[y][x] = (StType_t)(stOut.m_data[y][x] * SR_coef.m_coef[y][x]);

	for (uint32_t x = 0; x < X_SIZE; x += 1) {
		T2_ysum[x] = 0;
		for (uint32_t y = 0; y < Y_SIZE; y += 1)
			T2_ysum[x] += T2_mult[y][x];
	}

	T3_rslt = 0;
	for (uint32_t x = 0; x < X_SIZE; x += 1)
		T3_rslt += T3_ysum[x];

	if (T3_bValid)
		WriteStream(T3_rslt);
}
Ejemplo n.º 20
0
IX_ETH_DB_PUBLIC
void ixEthDBDatabaseMaintenance()
{
    HashIterator iterator;
    UINT32 portIndex;
    BOOL agingRequired = FALSE;

    /* ports who will have deleted records and therefore will need updating */
    IxEthDBPortMap triggerPorts;

    if (IX_FEATURE_CTRL_SWCONFIG_ENABLED !=
        ixFeatureCtrlSwConfigurationCheck (IX_FEATURECTRL_ETH_LEARNING))
    {
        return;
    }

    SET_EMPTY_DEPENDENCY_MAP(triggerPorts);

    /* check if there's at least a port that needs aging */
    for (portIndex = 0 ; portIndex < IX_ETH_DB_NUMBER_OF_PORTS ; portIndex++)
    {
        if (ixEthDBPortInfo[portIndex].agingEnabled && ixEthDBPortInfo[portIndex].enabled)
        {
            agingRequired = TRUE;
        }
    }

    if (agingRequired)
    {
        /* ask each NPE port to write back the database for aging inspection */
        for (portIndex = 0 ; portIndex < IX_ETH_DB_NUMBER_OF_PORTS ; portIndex++)
        {
            if (ixEthDBPortDefinitions[portIndex].type == IX_ETH_NPE
                && ixEthDBPortInfo[portIndex].agingEnabled
                && ixEthDBPortInfo[portIndex].enabled)
            {
                IxNpeMhMessage message;
                IX_STATUS result;
                
                /* send EDB_GetMACAddressDatabase message */
                FILL_GETMACADDRESSDATABASE(message, 
                    0 /* unused */, 
                    IX_OSAL_MMU_VIRT_TO_PHYS(ixEthDBPortInfo[portIndex].updateMethod.npeUpdateZone));

                IX_ETHDB_SEND_NPE_MSG(IX_ETHNPE_PHYSICAL_ID_TO_NODE(portIndex), message, result);

                if (result == IX_SUCCESS)
                {
                    /* analyze NPE copy */
                    ixEthDBNPESyncScan(portIndex, ixEthDBPortInfo[portIndex].updateMethod.npeUpdateZone, FULL_ELT_BYTE_SIZE);

                    IX_ETH_DB_SUPPORT_TRACE("DB: (API) Finished scanning NPE tree on port %d\n", portIndex);
                }
                else
                {
                     ixOsalLog(IX_OSAL_LOG_LVL_WARNING,
                        IX_OSAL_LOG_DEV_STDOUT, 
                        "EthDB: (Maintenance) warning, Clearing Database records for all types for port %d\n",
                        portIndex, 0, 0, 0, 0, 0);

                    ixEthDBDatabaseClear(portIndex, IX_ETH_DB_ALL_RECORD_TYPES);
                }
            }
        }

        /* browse database and age entries */
        BUSY_RETRY(ixEthDBInitHashIterator(&dbHashtable, &iterator));

        while (IS_ITERATOR_VALID(&iterator))
        {
            MacDescriptor *descriptor = (MacDescriptor *) iterator.node->data;
            UINT32 *age               = NULL;
            BOOL staticEntry          = TRUE;

            if (descriptor->type == IX_ETH_DB_FILTERING_RECORD)
            {
                age         = &descriptor->recordData.filteringData.age;
                staticEntry = descriptor->recordData.filteringData.staticEntry;
            }
            else if (descriptor->type == IX_ETH_DB_FILTERING_VLAN_RECORD)
            {
                age         = &descriptor->recordData.filteringVlanData.age;
                staticEntry = descriptor->recordData.filteringVlanData.staticEntry;
            }
            else
            {
                staticEntry = TRUE;
            }

            if (ixEthDBPortInfo[descriptor->portID].agingEnabled && (staticEntry == FALSE))
            {
                /* manually increment the age if the port has no such capability */
                if ((ixEthDBPortDefinitions[descriptor->portID].capabilities & IX_ETH_ENTRY_AGING) == 0)
                {
                    *age += (IX_ETH_DB_MAINTENANCE_TIME / 60);
                }

                /* age entry if it exceeded the maximum time to live */
                if (*age >= (IX_ETH_DB_LEARNING_ENTRY_AGE_TIME / 60))
                {
                    /* add port to the set of update trigger ports */
                    JOIN_PORT_TO_MAP(triggerPorts, descriptor->portID);

                    /* delete entry */
                    BUSY_RETRY(ixEthDBRemoveEntryAtHashIterator(&dbHashtable, &iterator));
                }
                else
                {
                    /* move to the next record */
                    BUSY_RETRY(ixEthDBIncrementHashIterator(&dbHashtable, &iterator));
                }
            }
            else
            {
                /* move to the next record */
                BUSY_RETRY(ixEthDBIncrementHashIterator(&dbHashtable, &iterator));
            }
        }

        /* update ports which lost records */
        ixEthDBUpdatePortLearningTrees(triggerPorts);
    }
}
Ejemplo n.º 21
0
void
CPersVadd::PersVadd()
{
	if (PR_htValid) {
		switch (PR_htInst) {
		case VADD_RESET:
			if (SR_msgDelay < 500 || SendHostMsgBusy()) {
				S_msgDelay += 1;
				HtRetry();
				break;
			}
			SendHostMsg(VADD_TYPE_SIZE, (XDIM_LEN << 8) | TYPE_SIZE);
			HtTerminate();
			break;
		case VADD_ENTER:
			S_yIdx = 0;
			S_yDimLen = PR_yDimLen;
			S_xIdx = 0;
			S_xDimLen = PR_xDimLen;
			S_sum = 0;

			S_addrA += PR_yAddrOff;
			S_addrB += PR_yAddrOff;
			S_addrC += PR_yAddrOff;

			WriteStreamPause_C(VADD_OPEN);

			break;
		case VADD_OPEN:

			// Open read stream A, once for each xDim to be processed
			if (PR_yOpenAIdx < PR_yDimLen && !ReadStreamBusy_A()) {
				ht_uint32 remLen = (ht_uint32)((PR_yDimLen - PR_yOpenAIdx) * PR_xDimLen);
				ReadStreamOpen_A(SR_addrA, remLen > 0x3f ? (ht_uint6)0x3f : (ht_uint6)remLen, P_yOpenAIdx);

				S_addrA += PR_xDimLen * TYPE_SIZE;
				P_yOpenAIdx += 1;
			}

			// Open read stream B, once for each xDim to be processed
			if (PR_yOpenBIdx < PR_yDimLen && !ReadStreamBusy_B()) {
				ReadStreamOpen_B(SR_addrB, PR_xDimLen);

				S_addrB += PR_xDimLen * TYPE_SIZE;
				P_yOpenBIdx += 1;
			}

			// Open write stream, once for each xDim to be processed
			if (PR_yOpenCIdx < SR_yDimLen && !WriteStreamBusy_C()) {
				WriteStreamOpen_C(SR_addrC);

				S_addrC += PR_xDimLen * TYPE_SIZE;
				P_yOpenCIdx += 1;
			}

			if (PR_yOpenAIdx == PR_yDimLen && PR_yOpenBIdx == PR_yDimLen && PR_yOpenCIdx == PR_yDimLen)
				WriteStreamPause_C(VADD_RETURN);
			else
				HtContinue(VADD_OPEN);

			break;
		case VADD_RETURN: {
			BUSY_RETRY(SendReturnBusy_htmain());

			SendReturn_htmain(S_sum);
		}
		break;
		default:
			assert(0);
		}
	}

	if (SR_yIdx < SR_yDimLen &&
		ReadStreamReady_A() &&
		ReadStreamReady_B() &&
		WriteStreamReady_C())
	{
		PersType_t a, b;
		a = ReadStream_A();
		b = ReadStream_B();

		PersType_t c = a + b;

		S_sum += (ht_uint32)c;
		WriteStream_C(c);

		assert_msg(SR_yIdx == ReadStreamTag_A(), "ReadStreamTag_A() error");

		if (SR_xIdx + 1 < SR_xDimLen)
			S_xIdx += 1;
		else {
			ReadStreamClose_A();
			WriteStreamClose_C();
			S_xIdx = 0;
			S_yIdx += 1;
		}
	}
}
Ejemplo n.º 22
0
void CPersHsmw::PersHsmw()
{
	if (PR_htValid) {
		switch (PR_htInst) {
		case HSMW_ENTRY: {

			P_compIdx = 0;
			P_mcuBlkRow = 0;
			P_mcuBlkCol = 0;
			P_rowInBlk = 0;

			P_mcuPendCnt = 0;
			P_readDone = false;
			P_pollDone = false;

			P_bRstFirst = true;

			P_rdReqGrpId = (PR_htId << 1) | S_readBufIdx[PR_htId];

			P_mcuCol = 0;
			P_mcuRow = P_rstIdx;

			HtContinue(HSMW_LOOP);
		}
		break;
		case HSMW_LOOP: {
			if (S_bufInUse[PR_htId] < 2 && !P_readDone && !ReadMemBusy() ) {

				// issue read
				ht_uint13 compRow = (ht_uint13)((P_mcuRow * S_dec.m_dcp[P_compIdx].m_blkRowsPerMcu + P_mcuBlkRow) * 8 + P_rowInBlk);

				if (compRow < S_dec.m_dcp[P_compIdx].m_compRows) {

					ht_uint27 rowPos = (ht_uint27)(compRow * S_dec.m_dcp[P_compIdx].m_compBufColLines * MEM_LINE_SIZE);
					ht_uint13 colPos = (ht_uint13)((P_mcuCol * S_dec.m_dcp[P_compIdx].m_blkColsPerMcu + (P_mcuBlkCol * 8)) * 8);
					assert(rowPos + colPos < S_dec.m_dcp[P_compIdx].m_compRows * S_dec.m_dcp[P_compIdx].m_compBufColLines * MEM_LINE_SIZE);

					ht_uint48 memAddr = S_dec.m_dcp[P_compIdx].m_pCompBuf + rowPos + colPos;

					sc_uint<HSMW_HTID_W+5> varAddr1 = (PR_htId << 5) | (S_readBufIdx[PR_htId] << 4) | (P_compIdx << 2) | (P_mcuBlkRow << 1) | P_mcuBlkCol;

					//printf("Read offset ci %d, mcuBlkCol %d, mcuBlkRow %d, rowPos %d, colPos %d, varAddr1 0x%x\n",
					//	(int)P_compIdx, (int)P_mcuBlkCol, (int)P_mcuBlkRow, (int)rowPos, (int)colPos, (int)varAddr1);

					ReadMem_mcuBuf(memAddr, varAddr1, 0, P_rowInBlk, 8);
				}

				if (P_rowInBlk+1 == DCTSIZE) {
					P_rowInBlk = 0;
					if (P_mcuBlkCol+1 == S_dec.m_dcp[P_compIdx].m_blkColsPerMcu) {
						P_mcuBlkCol = 0;
						if (P_mcuBlkRow+1 == S_dec.m_dcp[P_compIdx].m_blkRowsPerMcu) {
							P_mcuBlkRow = 0;
							if (P_compIdx+1 == S_dec.m_compCnt) {
								P_compIdx = 0;

								S_readBufIdx[PR_htId] ^= 1;
								P_rdReqGrpId = (PR_htId << 1) | S_readBufIdx[PR_htId];

								P_mcuPendCnt += 1;
								S_bufInUse[PR_htId] += 1;

								if (P_mcuCol+8 >= S_dec.m_mcuCols) {
									P_mcuCol = 0;
									P_mcuRow += 1;

									P_readDone = S_dec.m_rstMcuCnt > 0 || P_mcuRow >= S_dec.m_mcuRows;
								} else
									P_mcuCol += 8;

								//printf("McuRead done: PR_htId %d, S_mcuBufInUseCnt[%d] %d, P_mcuReadPendCnt %d, P_readBufIdx %d\n",
								//	(int)PR_htId, (int)PR_htId, (int)S_mcuBufInUseCnt[PR_htId], (int)P_mcuReadPendCnt, (int)P_readBufIdx);
							} else
								P_compIdx += 1;
						} else
							P_mcuBlkRow += 1;
					} else
						P_mcuBlkCol += 1;
				} else
					P_rowInBlk += 1;
			}

			sc_uint<HSMW_HTID_W+1> pollReqGrpId = (PR_htId << 1) | S_pollBufIdx[PR_htId];
			if (P_mcuPendCnt > 0 && !S_hsmwIhufQue[PR_htId].full() && !ReadMemPoll(pollReqGrpId)) {
				HsmwIhufMsg msg;

				msg.m_jobId = 0;
				msg.m_imageIdx = P_imageIdx;
				msg.m_rstIdx = (ht_uint10)P_rstIdx;
				msg.m_bufIdx = S_pollBufIdx[PR_htId];
				msg.m_bRstFirst = P_bRstFirst;
				msg.m_bRstLast = false;
				msg.m_bEndOfImage = false;

				P_bRstFirst = false;

				S_hsmwIhufQue[PR_htId].push( msg );

				P_mcuPendCnt -= 1;
				S_pollBufIdx[PR_htId] ^= 1;
			}

			if (P_readDone && P_mcuPendCnt == 0)
				HtContinue(HSMW_RETURN);
			else
				HtContinue(HSMW_LOOP);
		}
		break;
		case HSMW_RETURN: {
			BUSY_RETRY( SendReturnBusy_hsmw() );

			SendReturn_hsmw();
		}
		break;
		default:
			assert(0);
		}
	}

	T1_bPushJdm = false;

	if (!GR_htReset && !S_hsmwIhufQue[S_ihufQueIdx].empty() && !SendMsgBusy_jdm()) {
		HsmwIhufMsg msg = S_hsmwIhufQue[S_ihufQueIdx].front();

		if (msg.m_bRstFirst)
			S_mcuRow[S_ihufQueIdx] = msg.m_rstIdx;

		T1_bPushJdm = true;
		T1_jdm.m_compIdx = S_compIdx[S_ihufQueIdx];
		T1_jdm.m_decPipeId = S_ihufQueIdx;		// ihuf index
		T1_jdm.m_rstIdx = msg.m_rstIdx;
		T1_jdm.m_bRstLast = false;		// last data for restart
		T1_jdm.m_bEndOfImage = false;	// last data for image
		T1_jdm.m_bEndOfMcuRow = false;
		T1_jdm.m_imageIdx = msg.m_imageIdx;		// image index for double buffering
		T1_jdm.m_jobId = msg.m_jobId;		// host job info index (for debug)

		T1_outCol = S_outCol[S_ihufQueIdx];
		T1_mcuCol = S_mcuCol[S_ihufQueIdx];
		T1_mcuBlkCol = S_mcuBlkCol[S_ihufQueIdx];
		T1_mcuBlkRow = S_mcuBlkRow[S_ihufQueIdx];

		ht_uint10 blkInRow = (ht_uint10)(S_mcuCol[S_ihufQueIdx] * S_dec.m_dcp[S_compIdx[S_ihufQueIdx]].m_blkColsPerMcu + S_mcuBlkCol[S_ihufQueIdx]);

		ht_uint1 blkColSel = S_dec.m_dcp[S_compIdx[S_ihufQueIdx]].m_blkColsPerMcu == 1 ? 0 : ((S_mcuCol[S_ihufQueIdx] >> 2) & 1);
		sc_uint<HSMW_HTID_W+5> varAddr1 = (sc_uint<HSMW_HTID_W+5>)((S_ihufQueIdx << 5) | (msg.m_bufIdx << 4) | (S_compIdx[S_ihufQueIdx] << 2) |
			(S_mcuBlkRow[S_ihufQueIdx] << 1) | blkColSel);

		for (int r = 0; r < 8; r += 1)
			S_mcuBuf[r].read_addr(varAddr1, blkInRow & 7);

		if (S_outCol[S_ihufQueIdx] == 7) {
			S_outCol[S_ihufQueIdx] = 0;

			if (S_mcuBlkCol[S_ihufQueIdx]+1 == S_dec.m_dcp[S_compIdx[S_ihufQueIdx]].m_blkColsPerMcu) {
				S_mcuBlkCol[S_ihufQueIdx] = 0;
				if (S_mcuBlkRow[S_ihufQueIdx]+1 == S_dec.m_dcp[S_compIdx[S_ihufQueIdx]].m_blkRowsPerMcu) {
					S_mcuBlkRow[S_ihufQueIdx] = 0;
					if (S_compIdx[S_ihufQueIdx]+1 == S_dec.m_compCnt) {
						S_compIdx[S_ihufQueIdx] = 0;

						if ((S_mcuCol[S_ihufQueIdx] & 7) == 7 || S_mcuCol[S_ihufQueIdx]+1 == S_dec.m_mcuCols) {
							//printf("S_mcuRow 0x%x, S_mcuCol 0x%x\n", (int)S_mcuRow[S_ihufQueIdx], (int)S_mcuCol[S_ihufQueIdx]);

							if (S_mcuCol[S_ihufQueIdx]+1 == S_dec.m_mcuCols) {
								S_mcuCol[S_ihufQueIdx] = 0;

								T1_jdm.m_bEndOfMcuRow = true;

								if (S_dec.m_rstMcuCnt > 0)
									T1_jdm.m_bRstLast = true;

								if (S_mcuRow[S_ihufQueIdx]+1 == S_dec.m_mcuRows) {
									S_mcuRow[S_ihufQueIdx] = 0;
									T1_jdm.m_bEndOfImage = true;
									T1_jdm.m_bRstLast = true;
								} else
									S_mcuRow[S_ihufQueIdx] += 1;

							} else
								S_mcuCol[S_ihufQueIdx] += 1;

							S_bufInUse[S_ihufQueIdx] -= 1;

							S_hsmwIhufQue[S_ihufQueIdx].pop();
						} else
							S_mcuCol[S_ihufQueIdx] += 1;

						//printf("McuRead done: PR_htId %d, S_mcuBufInUseCnt[%d] %d, P_mcuReadPendCnt %d, P_readBufIdx %d\n",
						//	(int)PR_htId, (int)PR_htId, (int)S_mcuBufInUseCnt[PR_htId], (int)P_mcuReadPendCnt, (int)P_readBufIdx);
					} else
						S_compIdx[S_ihufQueIdx] += 1;
				} else
					S_mcuBlkRow[S_ihufQueIdx] += 1;
			} else
				S_mcuBlkCol[S_ihufQueIdx] += 1;

			if (S_skipIdx == 4)
				S_skipIdx = 0;
			else
#if HSMW_HTID_W==0
				S_ihufQueIdx = 0;
#else
				S_ihufQueIdx = S_ihufQueIdx + 1u;
#endif
		} else
			S_outCol[S_ihufQueIdx] += 1;
	} else
Ejemplo n.º 23
0
/**
 * @brief displays all the filtering records belonging to a port
 *
 * @param portID ID of the port to display
 *
 * Note that this function is documented in the main component
 * header file, IxEthDB.h.
 *
 * @warning deprecated, use @ref ixEthDBFilteringDatabaseShowRecords() 
 * instead. Calling this function is equivalent to calling
 * ixEthDBFilteringDatabaseShowRecords(portID, IX_ETH_DB_FILTERING_RECORD)
 */
IX_ETH_DB_PUBLIC
IxEthDBStatus ixEthDBFilteringDatabaseShow(IxEthDBPortId portID)
{
    IxEthDBStatus local_result;
    HashIterator iterator;
    PortInfo *portInfo;
    UINT32 recordCount = 0;

    IX_ETH_DB_CHECK_PORT(portID);

    IX_ETH_DB_CHECK_SINGLE_NPE(portID);

    portInfo = &ixEthDBPortInfo[portID];

    /* display table header */
    printf("Ethernet database records for port ID [%d]\n", portID);
    
    ixEthDBDependencyPortMapShow(portID, portInfo->dependencyPortMap);
    
    if (ixEthDBPortDefinitions[portID].type == IX_ETH_NPE)
    {
        printf("NPE updates are %s\n\n", portInfo->updateMethod.updateEnabled ? "enabled" : "disabled");
    }
    else
    {
        printf("updates disabled (not an NPE)\n\n");
    }

    printf("    MAC address    |   Age  | Type \n");
    printf("___________________________________\n");

    /* browse database */
    BUSY_RETRY(ixEthDBInitHashIterator(&dbHashtable, &iterator));

    while (IS_ITERATOR_VALID(&iterator))
    {
      MacDescriptor *descriptor = (MacDescriptor *) iterator.node->data;

      if (descriptor->portID == portID && descriptor->type == IX_ETH_DB_FILTERING_RECORD)
      {
          recordCount++;

          /* display entry */
          printf(" %02X:%02X:%02X:%02X:%02X:%02X | %5d  | %s\n",
              descriptor->macAddress[0],
              descriptor->macAddress[1],
              descriptor->macAddress[2],
              descriptor->macAddress[3],
              descriptor->macAddress[4],
              descriptor->macAddress[5],
              descriptor->recordData.filteringData.age,
              descriptor->recordData.filteringData.staticEntry ? "static" : "dynamic");
      }

      /* move to the next record */
      BUSY_RETRY_WITH_RESULT(ixEthDBIncrementHashIterator(&dbHashtable, &iterator), local_result);

      /* debug */
      if (local_result == IX_ETH_DB_BUSY)
      {
          return IX_ETH_DB_FAIL;
      }
    }

    /* display number of records */
    printf("\nFound %d records\n", recordCount);

    return IX_ETH_DB_SUCCESS;
}