void NETLIST_OBJECT_LIST::findBestNetNameForEachNet()
{
    // Important note: NET_SHEETLABEL items of sheet items should *NOT* be considered,
    // because they live in a sheet but their names are actually used in the subsheet.
    // Moreover, in the parent sheet, the name of NET_SHEETLABEL can be not unique,
    // ( for instance when 2 different sheets share the same schematic in complex hierarchies
    // and 2 identical NET_SHEETLABEL labels can be connected to 2 different nets

    int netcode = 0;            // current netcode for tested items
    unsigned idxstart = 0;      // index of the first item of this net
    NETLIST_OBJECT* item;
    NETLIST_OBJECT* candidate;

    // Pass 1: find the best name for labelled nets:
    candidate = NULL;
    for( unsigned ii = 0; ii <= size(); ii++ )
    {
        if( ii == size() ) // last item already tested
            item = NULL;
        else
            item = GetItem( ii );

        if( !item || netcode != item->GetNet() )     // End of net found
        {
            if( candidate )         // One or more labels exists, find the best
            {
                for (unsigned jj = idxstart; jj < ii; jj++ )
                    GetItem( jj )->SetNetNameCandidate( candidate );
            }

            if( item == NULL )  // End of list
                break;

            // Prepare next net analysis:
            netcode = item->GetNet();
            candidate = NULL;
            idxstart = ii;
        }

        switch( item->m_Type )
        {
        case NET_HIERLABEL:
        case NET_LABEL:
        case NET_PINLABEL:
        case NET_GLOBLABEL:
        case NET_GLOBBUSLABELMEMBER:
            // A candidate is found: select the better between the previous
            // and this one
            if( candidate == NULL )
                candidate = item;
            else
            {
                if( evalLabelsPriority( item, candidate ) )
                    // item has a highter priority than candidate
                    // so update the best candidate
                    candidate = item;
            }
            break;

        default:
            break;
        }
    }

    // Pass 2: find the best name for not labelled nets:
    // The "default" net name is Net-<<Ref cmp>_Pad<num pad>>
    // (see NETLIST_OBJECT::GetShortNetName())
    // therefore the "best" is the short net name alphabetically classed first
    // (to avoid net names changes when the net is not modified,
    // even if components are moved or deleted and undelete or replaced, as long
    // the reference is kept)

    // Build a list of items with no net names
    NETLIST_OBJECTS    list;   // no ownership of elements being pointed at

    for( unsigned ii = 0; ii < size(); ii++ )
    {
        item = GetItem( ii );

        if( !item->HasNetNameCandidate() )
            list.push_back( item );
    }

    if( list.size() == 0 )
        return;

    idxstart = 0;
    candidate = NULL;
    netcode = list[0]->GetNet();

    for( unsigned ii = 0; ii <= list.size(); ii++ )
    {
        if( ii < list.size() )
            item = list[ii];
        else
            item = NULL;

        if( !item || netcode != item->GetNet() )     // End of net found
        {
            if( candidate )
            {
                for (unsigned jj = idxstart; jj < ii; jj++ )
                {
                    NETLIST_OBJECT* obj = list[jj];
                    obj->SetNetNameCandidate( candidate );
                }
            }

            if( !item )
                break;

            netcode = item->GetNet();
            candidate = NULL;
            idxstart = ii;
        }

        // Examine all pins of the net to find the best candidate,
        // i.e. the first net name candidate, by alphabetic order
        // the net names are built by GetShortNetName
        // (Net-<{reference}-Pad{pad number}> like Net-<U3-Pad5>
        // Not named nets do not have usually a lot of members.
        // Many have only 2 members(a pad and a non connection symbol)
        if( item->m_Type == NET_PIN )
        {
            // A candidate is found, however components which are not in
            // netlist are not candidate because some have their reference
            // changed each time the netlist is built (power components)
            // and anyway obviously they are not a good candidate
            SCH_COMPONENT* link = item->GetComponentParent();

            if( link && link->IsInNetlist() )
            {
                // select the better between the previous and this one
                item->SetNetNameCandidate( item );  // Needed to calculate GetShortNetName

                if( candidate == NULL )
                    candidate = item;
                else
                {
                    if( item->GetShortNetName().Cmp( candidate->GetShortNetName() ) < 0 )
                        candidate = item;
                }
            }
        }
    }
}
Example #2
0
/**
 * Function findBestNetNameForEachNet
 * fill the .m_NetNameCandidate member of each item of aNetItemBuffer
 * with a reference to the "best" NETLIST_OBJECT usable to give a name to the net
 * If no suitable object found, .m_NetNameCandidate is filled with 0.
 * The "best" NETLIST_OBJECT is a NETLIST_OBJECT that have the type label
 * and by priority order:
 * the label is global or local
 * the label is in the first sheet in a hierarchy (the root sheet has the most priority)
 * alphabetic order.
 */
void NETLIST_OBJECT_LIST::findBestNetNameForEachNet()
{
    int netcode = 0;            // current netcode for tested items
    unsigned idxstart = 0;      // index of the first item of this net
    NETLIST_OBJECT* item;
    NETLIST_OBJECT* candidate;

    // Pass 1: find the best name for labelled nets:
    item = NULL;
    candidate = NULL;
    for( unsigned ii = 0; ii <= size(); ii++ )
    {

        if( ii == size() ) // last item already found
            netcode = -2;
        else
            item = GetItem( ii );

        if( netcode != item->GetNet() )     // End of net found
        {
            if( candidate )         // One or more labels exists, find the best
            {
                for (unsigned jj = idxstart; jj < ii; jj++ )
                    GetItem( jj )->SetNetNameCandidate( candidate );
            }

            if( netcode == -2 )
                break;

            netcode = item->GetNet();
            candidate = NULL;
            idxstart = ii;
        }

        switch( item->m_Type )
        {
        case NET_HIERLABEL:
        case NET_LABEL:
        case NET_PINLABEL:
        case NET_GLOBLABEL:
            // A candidate is found: select the better between the previous
            // and this one
            if( candidate == NULL )
                candidate = item;
            else
            {
                if( evalLabelsPriority( item, candidate ) )
                    // item has a highter priority than candidate
                    // so update the best candidate
                    candidate = item;
            }
            break;

        default:
            break;
        }
    }

    // Pass 2: find the best name for not labelled nets:
    // The "default" net name is Net-<<Ref cmp>_Pad<num pad>>
    // (see NETLIST_OBJECT::GetShortNetName())
    // therefore the "best" is the short net name alphabetically classed first
    // (to avoid net names changes when the net is not modified,
    // even if components are moved or deleted and undelete or replaced, as long
    // the reference is kept)

    // Build the list of items with no net names
    NETLIST_OBJECT_LIST list;
    for( unsigned ii = 0; ii < size(); ii++ )
    {
        item = GetItem( ii );
        if( !item->HasNetNameCandidate() )
            list.push_back( item );
    }

    if( list.size() == 0 )
        return;

    idxstart = 0;
    candidate = NULL;
    netcode = list.GetItemNet( 0 );

    for( unsigned ii = 0; ii <= list.size(); ii++ )
    {
        if( ii < list.size() )
            item = list.GetItem( ii );

        if( netcode != item->GetNet() || ii >= list.size() )     // End of net found
        {
            if( candidate )
            {
                for (unsigned jj = idxstart; jj < ii; jj++ )
                {
                    NETLIST_OBJECT* obj = list.GetItem( jj );
                    obj->SetNetNameCandidate( candidate );
                }
            }

            if( ii >= list.size() )
                break;

            netcode = item->GetNet();
            candidate = NULL;
            idxstart = ii;
        }

        // Examine all pins of the net to find the best candidate,
        // i.e. the first net name candidate, by alphabetic order
        // the net names are names bu_ilt by GetShortNetName
        // (Net-<{reference}-Pad{pad number}> like Net-<U3-Pad5>
        // Not named nets do not have usually a lot of members.
        // Many have only 2 members(a pad and a non connection symbol)
        if( item->m_Type == NET_PIN )
        {
            // A candidate is found, however components which are not in
            // netlist are not candidate because some have their reference
            // changed each time the netlist is built (power components)
            // and anyway obviously they are not a good candidate
            SCH_COMPONENT* link = item->GetComponentParent();
            if( link && link->IsInNetlist() )
            {
                // select the better between the previous and this one
                item->SetNetNameCandidate( item );  // Needed to calculate GetShortNetName

                if( candidate == NULL )
                    candidate = item;
                else
                {
                    if( item->GetShortNetName().Cmp( candidate->GetShortNetName() ) < 0 )
                        candidate = item;
                }
            }
        }
    }
}