Index: io_lihata.c =================================================================== --- io_lihata.c (revision 30792) +++ io_lihata.c (revision 30793) @@ -208,6 +208,7 @@ plug_io_lihata_v1.test_parse = io_lihata_test_parse; plug_io_lihata_v1.parse_pcb = io_lihata_parse_pcb; plug_io_lihata_v1.parse_footprint = NULL; + plug_io_lihata_v1.map_footprint = io_lihata_map_footprint; /* it is enough to have this for one version so the check is done only once */ plug_io_lihata_v1.parse_font = io_lihata_parse_font; plug_io_lihata_v1.parse_font = NULL; plug_io_lihata_v1.write_font = io_lihata_write_font; Index: read.c =================================================================== --- read.c (revision 30792) +++ read.c (revision 30793) @@ -2571,3 +2571,97 @@ return res; } +/* Decide about the type of a footprint file: + - if root is li:pcb-rnd-subcircuit, it is a static footprint file + - else it is a parametric element (footprint generator) if it contains + "@@" "purpose" + - if a line of a file element starts with ## and doesn't contain @, it's a tag + - if need_tags is set, tags are saved +*/ +pcb_plug_fp_map_t *io_lihata_map_footprint(pcb_plug_io_t *ctx, FILE *f, const char *fn, pcb_plug_fp_map_t *head, int need_tags) +{ + int c, comment_len; + int first_subc = 1; + long pos = -1; + enum { + ST_WS, + ST_COMMENT, + ST_SUBC, + ST_TAG + } state = ST_WS; + gds_t tag; + + gds_init(&tag); + head->type = PCB_FP_INVALID; + while ((c = fgetc(f)) != EOF) { + pos++; + switch (state) { + case ST_WS: + if (isspace(c)) + break; + if (c == '#') { + comment_len = 0; + state = ST_COMMENT; + break; + } + else if ((first_subc) && (c == 'l')) { + char s[23]; + /* li:pcb-rnd-subcircuit */ + fgets(s, 21, f); + s[20] = '\0'; + if (strcmp(s, "i:pcb-rnd-subcircuit") == 0) { + head->type = PCB_FP_FILE; + goto out; + } + } + else if ((first_subc) && (c == 'E')) { + char s[8]; + /* Element */ + fgets(s, 7, f); + s[6] = '\0'; + if (strcmp(s, "lement") == 0) { + state = ST_SUBC; + break; + } + } + first_subc = 0; + /* fall-thru for detecting @ */ + case ST_COMMENT: + comment_len++; + if ((c == '#') && (comment_len == 1)) { + state = ST_TAG; + break; + } + if ((c == '\r') || (c == '\n')) + state = ST_WS; + if (c == '@') { + char s[10]; + maybe_purpose:; + /* "@@" "purpose" */ + fgets(s, 9, f); + s[8] = '\0'; + if (strcmp(s, "@purpose") == 0) { + head->type = PCB_FP_PARAMETRIC; + goto out; + } + } + break; + case ST_TAG: + if ((c == '\r') || (c == '\n')) { /* end of a tag */ + if (need_tags && (tag.used != 0)) + vts0_append(&head->tags, (char *)pcb_fp_tag(tag.array, 1)); + + tag.used = 0; + state = ST_WS; + break; + } + if (c == '@') + goto maybe_purpose; + gds_append(&tag, c); + } + } + +out:; + gds_uninit(&tag); + return head; +} Index: read.h =================================================================== --- read.h (revision 30792) +++ read.h (revision 30793) @@ -31,6 +31,6 @@ int io_lihata_parse_font(pcb_plug_io_t *ctx, pcb_font_t *Ptr, const char *Filename); int io_lihata_parse_element(pcb_plug_io_t *ctx, pcb_data_t *Ptr, const char *name); int io_lihata_parse_buffer(pcb_plug_io_t *ctx, pcb_buffer_t *buff, const char *filename); +pcb_plug_fp_map_t *io_lihata_map_footprint(pcb_plug_io_t *ctx, FILE *f, const char *fn, pcb_plug_fp_map_t *head, int need_tags); -