Index: trunk/src/Makefile.dep =================================================================== --- trunk/src/Makefile.dep (revision 6115) +++ trunk/src/Makefile.dep (revision 6116) @@ -3206,7 +3206,7 @@ obj_poly_list.h obj_poly.h polyarea.h obj_text_list.h obj_rat_list.h \ obj_rat.h layer_grp.h library.h rats_patch.h font.h box.h math_helper.h \ move.h misc_util.h data.h crosshair.h vtonpoint.h hid.h error.h drc.h \ - buffer.h rtree.h list_common.h obj_all.h + buffer.h rtree.h list_common.h obj_all.h layer_it.h draw.o: draw.c ../config.h conf_core.h conf.h global_typedefs.h \ pcb_bool.h unit.h pcb-printf.h ../src_3rd/genvector/gds_char.h \ ../src_3rd/genvector/genvector_impl.h \ @@ -3290,8 +3290,8 @@ rtree.h polygon.h search.h rats.h netlist.h library.h route_style.h \ vtroutestyle.h misc_util.h undo.h plug_io.h hid_actions.h compat_misc.h \ event.h layer_vis.h obj_all.h find_geo.c macro.h find_lookup.c \ - compat_nls.h board.h rats_patch.h font.h box.h move.h find_drc.c \ - obj_arc_draw.h obj_pad_draw.h obj_rat_draw.h obj_line_draw.h \ + compat_nls.h board.h rats_patch.h font.h box.h move.h layer_it.h \ + find_drc.c obj_arc_draw.h obj_pad_draw.h obj_rat_draw.h obj_line_draw.h \ obj_elem_draw.h obj_poly_draw.h obj_pinvia_draw.h find_misc.c \ find_clear.c find_debug.c find_print.c find_act.o: find_act.c ../config.h board.h const.h macro.h \ Index: trunk/src/data.c =================================================================== --- trunk/src/data.c (revision 6115) +++ trunk/src/data.c (revision 6116) @@ -33,6 +33,7 @@ #include "rtree.h" #include "list_common.h" #include "obj_all.h" +#include "layer_it.h" /* --------------------------------------------------------------------------- * some shared identifiers @@ -49,8 +50,10 @@ void pcb_loop_layers(void *ctx, pcb_layer_cb_t lacb, pcb_line_cb_t lcb, pcb_arc_cb_t acb, pcb_text_cb_t tcb, pcb_poly_cb_t pocb) { if ((lacb != NULL) || (lcb != NULL) || (acb != NULL) || (tcb != NULL) || (pocb != NULL)) { - LAYER_LOOP(PCB->Data, pcb_max_copper_layer + 2); - { + pcb_layer_it_t it; + pcb_layer_id_t lid; + for(lid = pcb_layer_first_all(&PCB->LayerGroups, &it); lid != -1; lid = pcb_layer_next(&it)) { + pcb_layer_t *layer = PCB->Data->Layer + lid; if (lacb != NULL) if (lacb(ctx, PCB, layer, 1)) continue; @@ -88,7 +91,6 @@ if (lacb != NULL) lacb(ctx, PCB, layer, 0); } - PCB_END_LOOP; } } @@ -258,7 +260,7 @@ hasNoObjects = (pinlist_length(&Data->Via) == 0); hasNoObjects &= (elementlist_length(&Data->Element) == 0); - for (i = 0; i < pcb_max_copper_layer + 2; i++) + for (i = 0; i < pcb_max_layer; i++) hasNoObjects = hasNoObjects && PCB_LAYER_IS_EMPTY(&(Data->Layer[i])); return (hasNoObjects); } Index: trunk/src/data.h =================================================================== --- trunk/src/data.h (revision 6115) +++ trunk/src/data.h (revision 6116) @@ -47,12 +47,16 @@ pcb_rtree_t *via_tree, *element_tree, *pin_tree, *pad_tree, *name_tree[3], /* for element names */ *rat_tree; pcb_board_t *pcb; - pcb_layer_t Layer[PCB_MAX_LAYER + 2]; /* add 2 silkscreen layers */ + pcb_layer_t Layer[PCB_MAX_LAYER + 2]; /* add 2 silkscreen layers; layer TODO: remove this hack */ pcb_plug_io_t *loader; ratlist_t Rat; }; +/* layer TODO: update and remove +2 when the silk hack is out */ +#define pcb_max_layer (PCB->Data->LayerN+2) + +/* OBSOLOTE: do not use these 4 */ #define pcb_max_group (PCB->Data->LayerN) #define pcb_max_copper_layer (PCB->Data->LayerN) #define pcb_solder_silk_layer (pcb_max_copper_layer + PCB_SOLDER_SIDE) Index: trunk/src/find.c =================================================================== --- trunk/src/find.c (revision 6115) +++ trunk/src/find.c (revision 6116) @@ -146,8 +146,8 @@ static pcb_bool IsBad = pcb_false; static pcb_cardinal_t drcerr_count; /* count of drc errors */ static pcb_cardinal_t TotalP, TotalV, NumberOfPads[2]; -static ListType LineList[PCB_MAX_LAYER], /* list of objects to */ - PolygonList[PCB_MAX_LAYER], ArcList[PCB_MAX_LAYER], PadList[2], RatList, PVList; +static ListType LineList[PCB_MAX_LAYER+2], /* list of objects to */ + PolygonList[PCB_MAX_LAYER+2], ArcList[PCB_MAX_LAYER+2], PadList[2], RatList, PVList; /* --------------------------------------------------------------------------- * some local prototypes Index: trunk/src/find_lookup.c =================================================================== --- trunk/src/find_lookup.c (revision 6115) +++ trunk/src/find_lookup.c (revision 6116) @@ -27,6 +27,7 @@ #include "compat_nls.h" #include "board.h" +#include "layer_it.h" static inline pcb_r_dir_t r_search_pt(pcb_rtree_t * rtree, const pcb_point_t * pt, int radius, @@ -82,7 +83,7 @@ return pcb_false; } -static pcb_bool ADD_LINE_TO_LIST(pcb_cardinal_t L, pcb_line_t *Ptr, int from_type, void *from_ptr, pcb_found_conn_type_t type) +static pcb_bool ADD_LINE_TO_LIST(pcb_layer_id_t L, pcb_line_t *Ptr, int from_type, void *from_ptr, pcb_found_conn_type_t type) { if (User) pcb_undo_add_obj_to_flag(PCB_TYPE_LINE, LAYER_PTR(L), (Ptr), (Ptr)); @@ -170,7 +171,7 @@ { pcb_cardinal_t i; - for (i = 0; i < pcb_max_copper_layer; i++) { + for (i = 0; i < pcb_max_layer; i++) { free(LineList[i].Data); LineList[i].Data = NULL; free(ArcList[i].Data); @@ -233,10 +234,11 @@ */ void pcb_layout_lookup_init(void) { - pcb_cardinal_t i; + pcb_layer_it_t it; + pcb_layer_id_t i; /* initialize line arc and polygon data */ - for (i = 0; i < pcb_max_copper_layer; i++) { + for(i = pcb_layer_first_any(&PCB->LayerGroups, &it, PCB_LYT_COPPER); i != -1; i = pcb_layer_next(&it)) { pcb_layer_t *layer = LAYER_PTR(i); if (linelist_length(&layer->Line)) { @@ -383,6 +385,7 @@ { pcb_cardinal_t layer; struct pv_info info; + pcb_layer_it_t it; /* loop over all PVs currently on list */ while (PVList.Location < PVList.Number) { @@ -397,7 +400,7 @@ return pcb_true; /* now all lines, arcs and polygons of the several layers */ - for (layer = 0; layer < pcb_max_copper_layer; layer++) { + for(layer = pcb_layer_first_any(&PCB->LayerGroups, &it, PCB_LYT_COPPER); layer != -1; layer = pcb_layer_next(&it)) { if (LAYER_PTR(layer)->no_drc) continue; info.layer = layer; @@ -436,7 +439,8 @@ { pcb_bool done; pcb_layer_id_t layer; - pcb_cardinal_t i, group, ratposition, + pcb_layergrp_id_t group; + pcb_cardinal_t i, ratposition, lineposition[PCB_MAX_LAYER], polyposition[PCB_MAX_LAYER], arcposition[PCB_MAX_LAYER], padposition[2]; /* copy the current LO list positions; the original data is changed @@ -443,7 +447,7 @@ * by 'LookupPVConnectionsToLOList()' which has to check the same * list entries plus the new ones */ - for (i = 0; i < pcb_max_copper_layer; i++) { + for (i = 0; i < pcb_max_layer; i++) { lineposition[i] = LineList[i].Location; polyposition[i] = PolygonList[i].Location; arcposition[i] = ArcList[i].Location; @@ -457,6 +461,7 @@ */ do { pcb_cardinal_t *position; + unsigned int flg; if (AndRats) { position = &ratposition; @@ -476,10 +481,11 @@ for (entry = 0; entry < PCB->LayerGroups.grp[group].len; entry++) { layer = PCB->LayerGroups.grp[group].lid[entry]; - /* be aware that the layer number equal pcb_max_copper_layer - * and pcb_max_copper_layer+1 have a special meaning for pads + /* be aware that the layer number equal pcb_max_layer + * and pcb_max_layer+1 have a special meaning for pads */ - if (layer < pcb_max_copper_layer) { +#warning layer TODO: reindent + { /* try all new lines */ position = &lineposition[layer]; for (; *position < LineList[layer].Number; (*position)++) @@ -498,19 +504,19 @@ if (LookupLOConnectionsToPolygon(POLYGONLIST_ENTRY(layer, *position), group)) return (pcb_true); } - else { - /* try all new pads */ - layer -= pcb_max_copper_layer; - if (layer > 1) { - pcb_message(PCB_MSG_ERROR, _("bad layer number %d pcb_max_copper_layer=%d in find.c\n"), layer, pcb_max_copper_layer); - return pcb_false; - } - position = &padposition[layer]; - for (; *position < PadList[layer].Number; (*position)++) - if (LookupLOConnectionsToPad(PADLIST_ENTRY(layer, *position), group)) - return (pcb_true); - } } + + /* try all new pads */ + /* handle the special pad layers */ + flg = pcb_layergrp_flags(group); + if (flg & PCB_LYT_BOTTOM) layer = PCB_SOLDER_SIDE; + else if (flg & PCB_LYT_TOP) layer = PCB_COMPONENT_SIDE; + else continue; /* skip pads for this group */ + + position = &padposition[layer]; + for (; *position < PadList[layer].Number; (*position)++) + if (LookupLOConnectionsToPad(PADLIST_ENTRY(layer, *position), group)) + return (pcb_true); } /* check if all lists are done; Later for-loops @@ -517,16 +523,16 @@ * may have changed the prior lists */ done = !AndRats || ratposition >= RatList.Number; - for (layer = 0; layer < pcb_max_copper_layer + 2; layer++) { - if (layer < pcb_max_copper_layer) - done = done && - lineposition[layer] >= LineList[layer].Number - && arcposition[layer] >= ArcList[layer].Number && polyposition[layer] >= PolygonList[layer].Number; - else - done = done && padposition[layer - pcb_max_copper_layer] >= PadList[layer - pcb_max_copper_layer].Number; + for (layer = 0; layer < pcb_max_layer; layer++) { + done = done && + lineposition[layer] >= LineList[layer].Number + && arcposition[layer] >= ArcList[layer].Number && polyposition[layer] >= PolygonList[layer].Number; } - } - while (!done); + + /* check the two special pad layers */ + for (layer = 0; layer < 2; layer++) + done = done && padposition[layer] >= PadList[layer].Number; + } while (!done); return (pcb_false); } @@ -709,11 +715,12 @@ */ static pcb_bool LookupPVConnectionsToLOList(pcb_bool AndRats) { - pcb_cardinal_t layer; + pcb_layer_it_t it; + pcb_layer_id_t layer; struct lo_info info; /* loop over all layers */ - for (layer = 0; layer < pcb_max_copper_layer; layer++) { + for(layer = pcb_layer_first_any(&PCB->LayerGroups, &it, PCB_LYT_COPPER); layer != -1; layer = pcb_layer_next(&it)) { if (LAYER_PTR(layer)->no_drc) continue; /* do nothing if there are no PV's */ @@ -874,6 +881,7 @@ { pcb_cardinal_t entry; struct lo_info info; + unsigned int flg; info.arc = *Arc; EXPAND_BOUNDS(&info.arc); @@ -882,9 +890,8 @@ pcb_layer_id_t layer; layer = PCB->LayerGroups.grp[LayerGroup].lid[entry]; - - /* handle normal layers */ - if (layer < pcb_max_copper_layer) { +#warning layer TODO: reindent this block + { pcb_polygon_t *polygon; gdl_iterator_t it; @@ -907,15 +914,20 @@ return pcb_true; } } - else { - info.layer = layer - pcb_max_copper_layer; - if (setjmp(info.env) == 0) - pcb_r_search(PCB->Data->pad_tree, &info.arc.BoundingBox, NULL, LOCtoArcPad_callback, &info, NULL); - else - return pcb_true; - } } - return (pcb_false); + + /* handle the special pad layers */ + flg = pcb_layergrp_flags(LayerGroup); + if (flg & PCB_LYT_BOTTOM) info.layer = PCB_SOLDER_SIDE; + else if (flg & PCB_LYT_TOP) info.layer = PCB_COMPONENT_SIDE; + else return pcb_false; + + if (setjmp(info.env) == 0) + pcb_r_search(PCB->Data->pad_tree, &info.arc.BoundingBox, NULL, LOCtoArcPad_callback, &info, NULL); + else + return pcb_true; + + return pcb_false; } static pcb_r_dir_t LOCtoLineLine_callback(const pcb_box_t * b, void *cl) @@ -986,6 +998,7 @@ { pcb_cardinal_t entry; struct lo_info info; + unsigned int flg; info.line = *Line; info.layer = LayerGroup; @@ -1002,8 +1015,8 @@ layer = PCB->LayerGroups.grp[LayerGroup].lid[entry]; - /* handle normal layers */ - if (layer < pcb_max_copper_layer) { +#warning layer TODO: reindent + { info.layer = layer; /* add lines */ if (setjmp(info.env) == 0) @@ -1027,16 +1040,20 @@ } } } - else { - /* handle special 'pad' layers */ - info.layer = layer - pcb_max_copper_layer; - if (setjmp(info.env) == 0) - pcb_r_search(PCB->Data->pad_tree, &info.line.BoundingBox, NULL, LOCtoLinePad_callback, &info, NULL); - else - return pcb_true; - } } - return (pcb_false); + + /* handle the special pad layers */ + flg = pcb_layergrp_flags(LayerGroup); + if (flg & PCB_LYT_BOTTOM) info.layer = PCB_SOLDER_SIDE; + else if (flg & PCB_LYT_TOP) info.layer = PCB_COMPONENT_SIDE; + else return pcb_false; + + if (setjmp(info.env) == 0) + pcb_r_search(PCB->Data->pad_tree, &info.line.BoundingBox, NULL, LOCtoLinePad_callback, &info, NULL); + else + return pcb_true; + + return pcb_false; } @@ -1101,6 +1118,7 @@ { pcb_cardinal_t entry; struct rat_info info; + unsigned int flg; info.Point = Point; /* loop over all layers of this group */ @@ -1108,12 +1126,9 @@ pcb_layer_id_t layer; layer = PCB->LayerGroups.grp[LayerGroup].lid[entry]; - /* handle normal layers - rats don't ever touch - arcs by definition - */ - - if (layer < pcb_max_copper_layer) { + /* handle normal layers rats don't ever touch arcs by definition */ +#warning layer TODO: reindent + { info.layer = layer; if (setjmp(info.env) == 0) r_search_pt(LAYER_PTR(layer)->line_tree, Point, 1, NULL, LOCtoRat_callback, &info, NULL); @@ -1122,16 +1137,21 @@ if (setjmp(info.env) == 0) r_search_pt(LAYER_PTR(layer)->polygon_tree, Point, 1, NULL, PolygonToRat_callback, &info, NULL); } - else { - /* handle special 'pad' layers */ - info.layer = layer - pcb_max_copper_layer; - if (setjmp(info.env) == 0) - r_search_pt(PCB->Data->pad_tree, Point, 1, NULL, LOCtoPad_callback, &info, NULL); - else - return pcb_true; - } } - return (pcb_false); + + + /* handle the special pad layers */ + flg = pcb_layergrp_flags(LayerGroup); + if (flg & PCB_LYT_BOTTOM) info.layer = PCB_SOLDER_SIDE; + else if (flg & PCB_LYT_TOP) info.layer = PCB_COMPONENT_SIDE; + else return pcb_false; + + if (setjmp(info.env) == 0) + r_search_pt(PCB->Data->pad_tree, Point, 1, NULL, LOCtoPad_callback, &info, NULL); + else + return pcb_true; + + return pcb_false; } static pcb_r_dir_t LOCtoPadLine_callback(const pcb_box_t * b, void *cl) @@ -1220,6 +1240,7 @@ struct lo_info info; int ic; pcb_bool retv = pcb_false; + unsigned int flg; /* Internal connection: if pads in the same element have the same internal connection group number, they are connected */ @@ -1279,7 +1300,8 @@ layer = PCB->LayerGroups.grp[LayerGroup].lid[entry]; /* handle normal layers */ - if (layer < pcb_max_copper_layer) { +#warning layer TODO: reindent + { info.layer = layer; /* add lines */ if (setjmp(info.env) == 0) @@ -1297,16 +1319,19 @@ else return pcb_true; } - else { - /* handle special 'pad' layers */ - info.layer = layer - pcb_max_copper_layer; - if (setjmp(info.env) == 0) - pcb_r_search(PCB->Data->pad_tree, (pcb_box_t *) & info.pad, NULL, LOCtoPadPad_callback, &info, NULL); - else - return pcb_true; - } + } - } + /* handle the special pad layers */ + flg = pcb_layergrp_flags(LayerGroup); + if (flg & PCB_LYT_BOTTOM) info.layer = PCB_SOLDER_SIDE; + else if (flg & PCB_LYT_TOP) info.layer = PCB_COMPONENT_SIDE; + else return retv; + + if (setjmp(info.env) == 0) + pcb_r_search(PCB->Data->pad_tree, (pcb_box_t *) & info.pad, NULL, LOCtoPadPad_callback, &info, NULL); + else + return pcb_true; + return retv; } @@ -1375,6 +1400,7 @@ { pcb_cardinal_t entry; struct lo_info info; + unsigned int flg; if (!Polygon->Clipped) return pcb_false; @@ -1393,7 +1419,8 @@ layer = PCB->LayerGroups.grp[LayerGroup].lid[entry]; /* handle normal layers */ - if (layer < pcb_max_copper_layer) { +#warning layer TODO: reindent + { gdl_iterator_t it; pcb_polygon_t *polygon; @@ -1417,13 +1444,18 @@ else return pcb_true; } - else { - info.layer = layer - pcb_max_copper_layer; - if (setjmp(info.env) == 0) - pcb_r_search(PCB->Data->pad_tree, (pcb_box_t *) & info.polygon, NULL, LOCtoPolyPad_callback, &info, NULL); - else - return pcb_true; - } } - return (pcb_false); + + /* handle the special pad layers */ + flg = pcb_layergrp_flags(LayerGroup); + if (flg & PCB_LYT_BOTTOM) info.layer = PCB_SOLDER_SIDE; + else if (flg & PCB_LYT_TOP) info.layer = PCB_COMPONENT_SIDE; + else return pcb_false; + + if (setjmp(info.env) == 0) + pcb_r_search(PCB->Data->pad_tree, (pcb_box_t *) & info.polygon, NULL, LOCtoPolyPad_callback, &info, NULL); + else + return pcb_true; + + return pcb_false; } Index: trunk/src/find_misc.c =================================================================== --- trunk/src/find_misc.c (revision 6115) +++ trunk/src/find_misc.c (revision 6116) @@ -38,7 +38,7 @@ empty = (PVList.Location >= PVList.Number); if (AndRats) empty = empty && (RatList.Location >= RatList.Number); - for (i = 0; i < pcb_max_copper_layer && empty; i++) + for (i = 0; i < pcb_max_layer && empty; i++) empty = empty && LineList[i].Location >= LineList[i].Number && ArcList[i].Location >= ArcList[i].Number && PolygonList[i].Location >= PolygonList[i].Number; return (empty); @@ -47,8 +47,8 @@ static void reassign_no_drc_flags(void) { int layer; - - for (layer = 0; layer < pcb_max_copper_layer; layer++) { +#warning layer TODO: decide whether it is from attribute or not + for (layer = 0; layer < pcb_max_layer; layer++) { pcb_layer_t *l = LAYER_PTR(layer); l->no_drc = pcb_attrib_get(l, "PCB::skip-drc") != NULL; } @@ -87,7 +87,7 @@ pcb_cardinal_t position; /* decrement 'i' to keep layerstack order */ - for (i = pcb_max_copper_layer - 1; i != -1; i--) { + for (i = pcb_max_layer; i != -1; i--) { pcb_cardinal_t layer = pcb_layer_stack[i]; if (PCB->Data->Layer[layer].On) { @@ -230,7 +230,7 @@ pcb_layer_id_t laynum = pcb_layer_id(PCB->Data, (pcb_layer_t *) ptr1); /* don't mess with non-conducting objects! */ - if (laynum >= pcb_max_copper_layer || ((pcb_layer_t *) ptr1)->no_drc) + if (!(pcb_layer_flags(laynum) & PCB_LYT_COPPER) || ((pcb_layer_t *) ptr1)->no_drc) return; } } @@ -426,7 +426,7 @@ PVList.Number = 0; PVList.Location = 0; - for (i = 0; i < pcb_max_copper_layer; i++) { + for (i = 0; i < pcb_max_layer; i++) { LineList[i].Location = 0; LineList[i].DrawLocation = 0; LineList[i].Number = 0; Index: trunk/src/find_print.c =================================================================== --- trunk/src/find_print.c (revision 6115) +++ trunk/src/find_print.c (revision 6116) @@ -135,7 +135,7 @@ pcb_cardinal_t layer; /* reset found LOs for the next pin */ - for (layer = 0; layer < pcb_max_copper_layer; layer++) { + for (layer = 0; layer < pcb_max_layer; layer++) { LineList[layer].Location = LineList[layer].Number = 0; ArcList[layer].Location = ArcList[layer].Number = 0; PolygonList[layer].Location = PolygonList[layer].Number = 0; Index: trunk/src/layer_it.h =================================================================== --- trunk/src/layer_it.h (revision 6115) +++ trunk/src/layer_it.h (revision 6116) @@ -47,12 +47,19 @@ pcb_layergrp_id_t gid; pcb_cardinal_t lidx; unsigned int mask; - int exact; + unsigned int exact:1; + unsigned int global:1; }; static inline PCB_FUNC_UNUSED pcb_layer_id_t pcb_layer_next(pcb_layer_it_t *it) { - for(;;) { + if (it->global) { + /* over all layers, random order, without any checks - go the cheap way, bypassing groups */ + if (it->lidx < pcb_max_layer) + return it->lidx++; + return -1; + } + else for(;;) { pcb_layer_group_t *g = &(it->stack->grp[it->gid]); pcb_layer_id_t lid; unsigned int hit; @@ -86,6 +93,7 @@ it->gid = 0; it->lidx = 0; it->exact = 1; + it->global = 0; return pcb_layer_next(it); } @@ -96,8 +104,17 @@ it->gid = 0; it->lidx = 0; it->exact = 0; + it->global = 0; return pcb_layer_next(it); } +static inline PCB_FUNC_UNUSED pcb_layer_id_t pcb_layer_first_all(pcb_layer_stack_t *stack, pcb_layer_it_t *it) +{ + it->stack = stack; + it->lidx = 0; + it->global = 1; + return pcb_layer_next(it); +} + #endif