char *Reference_List (HText *text, BOOL titles) { char *temp = malloc(1000); char *output = malloc(1000); int refs = HText_sourceAnchors(text); if (refs <= 0) { return("\n\nThere are no references from this document.\n\n"); } else { int cnt; StrAllocCat(output,"\n*** References from this document ***\n"); for (cnt=1; cnt<=refs; cnt++) { HTAnchor *dest = HTAnchor_followMainLink((HTAnchor *) HText_childNumber(text, cnt)); HTParentAnchor * parent = HTAnchor_parent(dest); char * address = HTAnchor_address(dest); const char * title = titles ? HTAnchor_title(parent) : NULL; sprintf(temp, "[%d] ", cnt); StrAllocCat(output, temp); sprintf(temp, "%s\n", (char *)(title ? title : address)); StrAllocCat(output, temp); HT_FREE(address); } } }
static void print_refs(FILE *fp, BOOLEAN titles, int refs) { int cnt; char *address = NULL; const char *desc = gettext("unknown field or link"); void *helper = NULL; /* init */ for (cnt = 1; cnt <= refs; cnt++) { HTChildAnchor *child = HText_childNextNumber(cnt, &helper); HTAnchor *dest; HTParentAnchor *parent; const char *title; if (child == 0) { /* * child should not be 0 unless form field numbering is on and * cnt is the number of a form input field. * HText_FormDescNumber() will set desc to a description of * what type of input field this is. We'll create a * within-document link to ensure that the link numbers on the * list page match the numbering in the original document, but * won't create a forward link to the form. - FM && LE */ if (fields_are_numbered()) { HText_FormDescNumber(cnt, &desc); fprintf(fp, "%4d. form field = %s\n", cnt, desc); } continue; } dest = HTAnchor_followLink(child); /* * Ignore if child anchor points to itself, i.e., we had something * like <A NAME=xyz HREF="#xyz"> and it is not treated as a hidden * link. Useful if someone 'P'rints the List Page (which isn't a * very useful action to do, but anyway...) - kw */ if (dest == (HTAnchor *) child) continue; parent = HTAnchor_parent(dest); title = titles ? HTAnchor_title(parent) : NULL; address = HTAnchor_address(dest); fprintf(fp, "%4d. %s%s\n", cnt, ((HTAnchor *) parent != dest) && title ? "in " : "", (title ? title : address)); FREE(address); #ifdef VMS if (HadVMSInterrupt) break; #endif /* VMS */ } }
/* Output the title line ** --------------------- */ PRIVATE void display_title (HText * text) { const char * title = HTAnchor_title(text->node_anchor); char percent[20], format[20]; if (text->lines > (DISPLAY_LINES-1)) { #ifdef NOPE sprintf(percent, " (p%d of %d)", (text->top_of_screen/(DISPLAY_LINES-1)) + 1, (text->lines-1)/(DISPLAY_LINES-1) + 1); sprintf(percent, " (%d%%)", 100*(text->top_of_screen+DISPLAY_LINES-1)/ /* Seen */ (text->lines)); /* Total */ #else sprintf(percent, " (%d/%d)", text->top_of_screen+DISPLAY_LINES-1, /* Seen */ text->lines); /* Total */ #endif } else { percent[0] = 0; /* Null string */ } sprintf(format, "%%%d.%ds%%s\n", /* Generate format string */ (int)(HTScreenWidth-strlen(percent)), (int)(HTScreenWidth-strlen(percent)) ); #ifdef CURSES mvwprintw(w_top, 0, 0, format, title, percent); wrefresh(w_top); #else if (!text->target) OutputData(LineMode_getView(text->pLm), format, title, percent); else { char * line; if ((line = (char *) HT_MALLOC(HTScreenWidth+10)) == NULL) HT_OUTOFMEM("display_titile"); sprintf(line, format, title, percent); PUTS(line); HT_FREE(line); } #endif }
PRIVATE void split_line (HText * text, int split) { HTStyle * style = text->style; int spare; int indent = (int) (text->in_line_1 ? text->style->indent1st : text->style->leftIndent); /* Make new line */ HTLine * previous = text->last_line; HTLine * line; if ((line = (HTLine *) HT_MALLOC(LINE_SIZE(MAX_LINE))) == NULL) HT_OUTOFMEM("split_line"); text->lines++; previous->next->prev = line; line->prev = previous; line->next = previous->next; previous->next = line; text->last_line = line; line->size = 0; line->offset = 0; /* Split at required point */ if (split) { /* Delete space at "split" splitting line */ char * p; previous->data[previous->size] = 0; for (p = &previous->data[split]; *p; p++) if (*p != ' ') break; strcpy(line->data, p); line->size = strlen(line->data); previous->size = split; } while ((previous->size > 0) && (previous->data[previous->size-1] == ' ')) /* Strip trailers */ previous->size--; if ((previous = (HTLine *) HT_REALLOC(previous, LINE_SIZE(previous->size)))==NULL) HT_OUTOFMEM("split_line"); previous->prev->next = previous; /* Link in new line */ previous->next->prev = previous; /* Could be same node of course */ /* Terminate finished line for printing */ previous->data[previous->size] = 0; /* Align left, right or center */ spare = (int) (HTScreenWidth - style->rightIndent + style->leftIndent - previous->size); /* @@ first line indent */ switch (style->alignment) { case HT_CENTER : previous->offset = previous->offset + indent + spare/2; break; case HT_RIGHT : previous->offset = previous->offset + indent + spare; break; case HT_LEFT : case HT_JUSTIFY : /* Not implemented */ default: previous->offset = previous->offset + indent; break; } /* switch */ text->chars = text->chars + previous->size + 1; /* 1 for the line */ text->in_line_1 = NO; /* unless caller sets it otherwise */ /* If displaying as we go, output it: */ if (text->display_on_the_fly) { if (text->display_on_the_fly == DISPLAY_LINES) { /* First line */ if (previous->size == 0) { text->top_of_screen++; /* Scroll white space off top */ return; } if (HTAnchor_title(text->node_anchor)) { /* Title exists */ display_title(text); text->display_on_the_fly--; } } display_line(text, previous); text->display_on_the_fly--; /* Loop to top of next page? */ if (!text->display_on_the_fly && text->all_pages) { PUTS("\f\n"); /* Form feed on its own line a la rfc1111 */ text->display_on_the_fly = DISPLAY_LINES; } } } /* split_line */
/* Output a page ** ------------- */ PRIVATE void display_page (HText * text, int line_number) { HTLine * line = text->last_line->prev; int i; const char * title = HTAnchor_title(text->node_anchor); int lines_of_text = title ? (DISPLAY_LINES-TITLE_LINES) : DISPLAY_LINES; int last_screen = text->lines - lines_of_text; /* Constrain the line number to be within the document */ if (text->lines <= lines_of_text) line_number = 0; else if (line_number>last_screen) line_number = last_screen; else if (line_number < 0) line_number = 0; for(i=0, line = text->last_line->next; /* Find line */ i<line_number && (line!=text->last_line); i++, line=line->next) /* Loop */ assert(line->next != NULL); while((line!=text->last_line) && (line->size==0)) { /* Skip blank lines */ assert(line->next != NULL); line = line->next; line_number ++; } /* Can we just scroll to it? */ #ifndef VM /* No scrolling */ if (!text->stale && (line_number>=text->top_of_screen) && (line_number < text->top_of_screen + DISPLAY_LINES)) { /* Yes */ lines_of_text = line_number - text->top_of_screen; line = text->next_line; text->top_of_screen = line_number; #ifdef CURSES scrollok(w_text, TRUE); for (i = 0; i < lines_of_text; i++) { scroll(w_text); } #endif } else #endif { clear_screen(); /* No */ text->top_of_screen = line_number; if (title) display_title(text); } /* Bug: when we scroll to a part slightly futher down a page which previously fitted all on one screen including the [End], the code below will add an extra [End] to the screen, giving a total of two, one underneath the other. */ /* print it */ if (line) { for(i=0; (i< lines_of_text) && (line != text->last_line); i++) { assert(line != NULL); display_line(text, line); line = line->next; } fill_screen(text, lines_of_text - i); } text->next_line = line; /* Line after screen */ text->stale = NO; /* Display is up-to-date */ }
PRIVATE void parse_menu ARGS2 ( CONST char *, arg, HTParentAnchor *,anAnchor) { char gtype; char ch; char line[BIG]; char address[BIG]; char *name, *selector; /* Gopher menu fields */ char *host; char *port; char *p = line; #define TAB '\t' #define HEX_ESCAPE '%' if (!HTAnchor_title(anAnchor)) HTAnchor_setTitle(anAnchor, arg);/* Tell user something's happening */ node_anchor = anAnchor; HT = HText_new(anAnchor); HText_beginAppend(HT); HText_appendText(HT, "Select one of:<P>\n<UL>"); /* HText_appendText(HT, "Select one of:<P>\n<UL>"); */ while ((ch=NEXT_CHAR) != (char)EOF) { if (ch != '\n') { *p = ch; /* Put character in line */ if (p< &line[BIG-1]) p++; } else { *p++ = 0; /* Terminate line */ p = line; /* Scan it to parse it */ port = 0; /* Flag "not parsed" */ if (TRACE) fprintf(stderr, "HTGopher: Menu item: %s\n", line); gtype = *p++; /* Break on line with a dot by itself */ if ((gtype=='.') && ((*p=='\r') || (*p==0))) break; if (gtype && *p) { name = p; selector = strchr(name, TAB); if (selector) { *selector++ = 0; /* Terminate name */ host = strchr(selector, TAB); if (host) { *host++ = 0; /* Terminate selector */ port = strchr(host, TAB); if (port) { char *junk; port[0] = ':'; /* delimit host a la W3 */ junk = strchr(port, 13 /* was TAB */); if (junk) *junk++ = 0; /* Chop port */ if ((port[1]=='0') && (!port[2])) port[0] = 0; /* 0 means none */ } /* no port */ } /* host ok */ } /* selector ok */ } /* gtype and name ok */ if (gtype == GOPHER_WWW) { /* Gopher pointer to W3 */ HText_appendText(HT, "<LI> "); write_anchor(name, selector); HText_appendText(HT, "\n"); /* HText_appendParagraph(HT); */ } else if (port) { /* Other types need port */ if (gtype == GOPHER_TELNET) { if (*selector) sprintf(address, "telnet://%s@%s/", selector, host); else sprintf(address, "telnet://%s/", host); } else if (gtype == GOPHER_TN3270) { if (*selector) sprintf(address, "tn3270://%s@%s/", selector, host); else sprintf(address, "tn3270://%s/", host); } else { /* If parsed ok */ char *q; char *p; sprintf(address, "gopher://%s/%c", host, gtype); q = address+ strlen(address); for(p=selector; *p; p++) { /* Encode selector string */ /* fprintf (stderr, "Checking %d (%c) for acceptable.\n", *p, *p); */ if (acceptable[*p]) *q++ = *p; else { *q++ = HEX_ESCAPE; /* Means hex coming */ *q++ = hex[(TOASCII(*p)) >> 4]; *q++ = hex[(TOASCII(*p)) & 15]; } } *q++ = 0; /* terminate address */ } /* HText_appendText(HT, " "); */ /* Prettier JW/TBL */ HText_appendText(HT, "<LI> "); /* Error response from Gopher doesn't deserve to be a hyperlink. */ if (strcmp (address, "gopher://error.host:1/0")) write_anchor(name, address); else HText_appendText(HT, name); HText_appendText(HT, "\n"); /* HText_appendParagraph(HT); */ } else { /* parse error */ if (TRACE) fprintf(stderr, "HTGopher: Bad menu item.\n"); HText_appendText(HT, line); HText_appendParagraph(HT); } /* parse error */ p = line; /* Start again at beginning of line */ } /* if end of line */ } /* Loop over characters */
PRIVATE void HTML_start_element (HTStructured * me, int element_number, const BOOL * present, const char ** value) { HTChildAnchor * address = NULL; if (!me->started) { HTextImp_build(me->text, HTEXT_BEGIN); me->started = YES; } /* Look at what element was started */ switch (element_number) { case HTML_A: if (present[HTML_A_HREF] && value[HTML_A_HREF]) { address = HTAnchor_findChildAndLink( me->node_anchor, /* parent */ present[HTML_A_NAME] ? value[HTML_A_NAME] : NULL, /* Tag */ value[HTML_A_HREF], /* Addresss */ present[HTML_A_REL] && value[HTML_A_REL] ? (HTLinkType) HTAtom_caseFor(value[HTML_A_REL]) : NULL); if (present[HTML_A_TITLE] && value[HTML_A_TITLE]) { HTLink * link = HTAnchor_mainLink((HTAnchor *) address); HTParentAnchor * dest = HTAnchor_parent(HTLink_destination(link)); if (!HTAnchor_title(dest)) HTAnchor_setTitle(dest, value[HTML_A_TITLE]); } HTextImp_foundLink(me->text, element_number, HTML_A_HREF, address, present, value); HTTRACE(SGML_TRACE, "HTML Parser. Anchor `%s\'\n" _ value[HTML_A_HREF]); } break; case HTML_AREA: if (present[HTML_AREA_HREF] && value[HTML_AREA_HREF]) { address = HTAnchor_findChildAndLink(me->node_anchor, NULL, value[HTML_AREA_HREF], NULL); HTextImp_foundLink(me->text, element_number, HTML_AREA_HREF, address, present, value); HTTRACE(SGML_TRACE, "HTML Parser. Image map area `%s\'\n" _ value[HTML_AREA_HREF]); } break; case HTML_BASE: if (present[HTML_BASE_HREF] && value[HTML_BASE_HREF]) { HTAnchor_setBase(me->node_anchor, (char *) value[HTML_BASE_HREF]); HTTRACE(SGML_TRACE, "HTML Parser. New base `%s\'\n" _ value[HTML_BASE_HREF]); } break; case HTML_BODY: if (present[HTML_BODY_BACKGROUND] && value[HTML_BODY_BACKGROUND]) { address = HTAnchor_findChildAndLink(me->node_anchor, NULL, value[HTML_BODY_BACKGROUND], NULL); HTextImp_foundLink(me->text, element_number, HTML_BODY_BACKGROUND, address, present, value); HTTRACE(SGML_TRACE, "HTML Parser. Background `%s\'\n" _ value[HTML_BODY_BACKGROUND]); } break; case HTML_FORM: if (present[HTML_FORM_ACTION] && value[HTML_FORM_ACTION]) { address = HTAnchor_findChildAndLink(me->node_anchor, NULL, value[HTML_FORM_ACTION], NULL); HTextImp_foundLink(me->text, element_number, HTML_FORM_ACTION, address, present, value); } break; case HTML_FRAME: if (present[HTML_FRAME_SRC] && value[HTML_FRAME_SRC]) { address = HTAnchor_findChildAndLink(me->node_anchor, NULL, value[HTML_FRAME_SRC], NULL); HTextImp_foundLink(me->text, element_number, HTML_FRAME_SRC, address, present, value); HTTRACE(SGML_TRACE, "HTML Parser. Frame `%s\'\n" _ value[HTML_FRAME_SRC]); } break; case HTML_INPUT: if (present[HTML_INPUT_SRC] && value[HTML_INPUT_SRC]) { address = HTAnchor_findChildAndLink(me->node_anchor, NULL, value[HTML_INPUT_SRC], NULL); HTextImp_foundLink(me->text, element_number, HTML_INPUT_SRC, address, present, value); } break; case HTML_IMG: if (present[HTML_IMG_SRC] && value[HTML_IMG_SRC]) { address = HTAnchor_findChildAndLink(me->node_anchor, NULL, value[HTML_IMG_SRC], NULL); HTextImp_foundLink(me->text, element_number, HTML_IMG_SRC, address, present, value); } break; case HTML_ISINDEX: HTAnchor_setIndex(me->node_anchor); break; case HTML_LINK: if (present[HTML_LINK_HREF] && value[HTML_LINK_HREF]) { HTParentAnchor * dest = NULL; address = HTAnchor_findChildAndLink( me->node_anchor, /* parent */ present[HTML_A_NAME] ? value[HTML_A_NAME] : NULL, /* Tag */ present[HTML_A_HREF] ? value[HTML_A_HREF] : NULL, /* Addresss */ NULL); /* Rels */ dest = HTAnchor_parent(HTAnchor_followMainLink((HTAnchor *) address)); /* If forward reference */ if ((present[HTML_LINK_REL] && value[HTML_LINK_REL])) { char * strval = NULL; char * ptr = NULL; char * relation = NULL; StrAllocCopy(strval, value[HTML_LINK_REL]); ptr = strval; while ((relation = HTNextLWSToken(&ptr)) != NULL) { HTLink_add((HTAnchor *) me->node_anchor, (HTAnchor *) dest, (HTLinkType) HTAtom_caseFor(relation), METHOD_INVALID); } HT_FREE(strval); } /* If reverse reference */ if ((present[HTML_LINK_REV] && value[HTML_LINK_REV])) { char * strval = NULL; char * ptr = NULL; char * relation = NULL; StrAllocCopy(strval, value[HTML_LINK_REV]); ptr = strval; while ((relation = HTNextLWSToken(&ptr)) != NULL) { HTLink_add((HTAnchor *) dest, (HTAnchor *) me->node_anchor, (HTLinkType) HTAtom_caseFor(relation), METHOD_INVALID); } HT_FREE(strval); } /* If we got any type information as well */ if (present[HTML_LINK_TYPE] && value[HTML_LINK_TYPE]) { if (HTAnchor_format(dest) == WWW_UNKNOWN) HTAnchor_setFormat(dest, (HTFormat) HTAtom_caseFor(value[HTML_LINK_TYPE])); } /* Call out to the layout engine */ HTextImp_foundLink(me->text, element_number, HTML_LINK_HREF, address, present, value); } break; case HTML_META: if (present[HTML_META_NAME] && value[HTML_META_NAME]) { HTAnchor_addMeta (me->node_anchor, value[HTML_META_NAME], (present[HTML_META_CONTENT] && value[HTML_META_CONTENT]) ? value[HTML_META_CONTENT] : ""); } break; case HTML_OBJECT: if (present[HTML_OBJECT_CLASSID] && value[HTML_OBJECT_CLASSID]) { address = HTAnchor_findChildAndLink(me->node_anchor, NULL, value[HTML_OBJECT_CLASSID], NULL); HTextImp_foundLink(me->text, element_number, HTML_OBJECT_CLASSID, address, present, value); } if (present[HTML_OBJECT_CODEBASE] && value[HTML_OBJECT_CODEBASE]) { address = HTAnchor_findChildAndLink(me->node_anchor, NULL, value[HTML_OBJECT_CODEBASE], NULL); HTextImp_foundLink(me->text, element_number, HTML_OBJECT_CODEBASE, address, present, value); } if (present[HTML_OBJECT_DATA] && value[HTML_OBJECT_DATA]) { address = HTAnchor_findChildAndLink(me->node_anchor, NULL, value[HTML_OBJECT_DATA], NULL); HTextImp_foundLink(me->text, element_number, HTML_OBJECT_DATA, address, present, value); } if (present[HTML_OBJECT_ARCHIVE] && value[HTML_OBJECT_ARCHIVE]) { address = HTAnchor_findChildAndLink(me->node_anchor, NULL, value[HTML_OBJECT_ARCHIVE], NULL); HTextImp_foundLink(me->text, element_number, HTML_OBJECT_ARCHIVE, address, present, value); } if (present[HTML_OBJECT_USEMAP] && value[HTML_OBJECT_USEMAP]) { address = HTAnchor_findChildAndLink(me->node_anchor, NULL, value[HTML_OBJECT_USEMAP], NULL); HTextImp_foundLink(me->text, element_number, HTML_OBJECT_USEMAP, address, present, value); } break; case HTML_PRE: if (me->comment_end) HTextImp_addText(me->text, me->comment_end, strlen(me->comment_end)); break; case HTML_TITLE: HTChunk_truncate(me->title,0); break; } /* Update our parse stack */ if (SGML_findTagContents(me->dtd, element_number) != SGML_EMPTY) { if (me->sp == me->stack) { HTTRACE(SGML_TRACE, "HTML Parser. Maximum nesting of %d exceded!\n" _ MAX_NESTING); me->overflow++; return; } --(me->sp); me->sp[0] = element_number; } /* Call out to the layout engine */ HTextImp_beginElement(me->text, element_number, present, value); }
int showlist(DocInfo *newdoc, BOOLEAN titles) { int cnt; int refs, hidden_links; static char tempfile[LY_MAXPATH]; static BOOLEAN last_titles = TRUE; FILE *fp0; char *Address = NULL, *Title = NULL, *cp = NULL; char *LinkTitle = NULL; /* Rel stored as property of link, not of dest */ BOOLEAN intern_w_post = FALSE; const char *desc = "unknown field or link"; void *helper; refs = HText_sourceAnchors(HTMainText); hidden_links = HText_HiddenLinkCount(HTMainText); if (refs <= 0 && hidden_links > 0 && LYHiddenLinks != HIDDENLINKS_SEPARATE) { HTUserMsg(NO_VISIBLE_REFS_FROM_DOC); return (-1); } if (refs <= 0 && hidden_links <= 0) { HTUserMsg(NO_REFS_FROM_DOC); return (-1); } if ((fp0 = InternalPageFP(tempfile, titles == last_titles)) == 0) return (-1); LYLocalFileToURL(&(newdoc->address), tempfile); LYRegisterUIPage(newdoc->address, titles ? UIP_LIST_PAGE : UIP_ADDRLIST_PAGE); last_titles = titles; LYforce_HTML_mode = TRUE; /* force this file to be HTML */ LYforce_no_cache = TRUE; /* force this file to be new */ #ifdef EXP_ADDRLIST_PAGE if (titles != TRUE) BeginInternalPage(fp0, ADDRLIST_PAGE_TITLE, LIST_PAGE_HELP); else #endif BeginInternalPage(fp0, LIST_PAGE_TITLE, LIST_PAGE_HELP); StrAllocCopy(Address, HTLoadedDocumentURL()); LYEntify(&Address, FALSE); fprintf(fp0, "%s%s<p>\n", gettext("References in "), (non_empty(Address) ? Address : gettext("this document:"))); FREE(Address); if (refs > 0) { fprintf(fp0, "<%s compact>\n", ((keypad_mode == NUMBERS_AS_ARROWS) ? "ol" : "ul")); if (hidden_links > 0) fprintf(fp0, "<lh><em>%s</em>\n", gettext("Visible links:")); } if (hidden_links > 0) { if (LYHiddenLinks == HIDDENLINKS_IGNORE) hidden_links = 0; } helper = NULL; /* init */ for (cnt = 1; cnt <= refs; cnt++) { HTChildAnchor *child = HText_childNextNumber(cnt, &helper); HTAnchor *dest_intl = NULL; HTAnchor *dest; HTParentAnchor *parent; char *address; const char *title; if (child == 0) { /* * child should not be 0 unless form field numbering is on and cnt * is the number of a form input field. HText_FormDescNumber() * will set desc to a description of what type of input field this * is. We'll list it to ensure that the link numbers on the list * page match the numbering in the original document, but won't * create a forward link to the form. - FM && LE * * Changed to create a fake hidden link, to get the numbering right * in connection with always treating this file as * HIDDENLINKS_MERGE in GridText.c - kw */ if (fields_are_numbered()) { HText_FormDescNumber(cnt, &desc); fprintf(fp0, "<li><a id=%d href=\"#%d\">form field</a> = <em>%s</em>\n", cnt, cnt, desc); } continue; } #ifndef DONT_TRACK_INTERNAL_LINKS dest_intl = HTAnchor_followTypedLink(child, HTInternalLink); #endif dest = dest_intl ? dest_intl : HTAnchor_followLink(child); parent = HTAnchor_parent(dest); if (!intern_w_post && dest_intl && HTMainAnchor && HTMainAnchor->post_data && parent->post_data && BINEQ(HTMainAnchor->post_data, parent->post_data)) { /* * Set flag to note that we had at least one internal link, if the * document from which we are generating the list has associated * POST data; after an extra check that the link destination really * has the same POST data so that we can believe it is an internal * link. */ intern_w_post = TRUE; } address = HTAnchor_address(dest); title = titles ? HTAnchor_title(parent) : NULL; if (dest_intl) { HTSprintf0(&LinkTitle, "(internal)"); } else if (titles && child->type && dest == child->dest && !strncmp(HTAtom_name(child->type), "RelTitle: ", 10)) { HTSprintf0(&LinkTitle, "(%s)", HTAtom_name(child->type) + 10); } else { FREE(LinkTitle); } StrAllocCopy(Address, address); FREE(address); LYEntify(&Address, TRUE); if (non_empty(title)) { LYformTitle(&Title, title); LYEntify(&Title, TRUE); if (*Title) { cp = findPoundSelector(Address); } else { FREE(Title); } } fprintf(fp0, "<li><a href=\"%s\"%s>%s%s%s%s%s</a>\n", Address, dest_intl ? " TYPE=\"internal link\"" : "", NonNull(LinkTitle), ((HTAnchor *) parent != dest) && Title ? "in " : "", (char *) (Title ? Title : Address), (Title && cp) ? " - " : "", (Title && cp) ? (cp + 1) : ""); FREE(Address); FREE(Title); } FREE(LinkTitle); if (hidden_links > 0) { if (refs > 0) fprintf(fp0, "\n</%s>\n\n<p>\n", ((keypad_mode == NUMBERS_AS_ARROWS) ? "ol" : "ul")); fprintf(fp0, "<%s compact>\n", ((keypad_mode == NUMBERS_AS_ARROWS) ? "ol continue" : "ul")); fprintf(fp0, "<lh><em>%s</em>\n", gettext("Hidden links:")); } for (cnt = 0; cnt < hidden_links; cnt++) { StrAllocCopy(Address, HText_HiddenLinkAt(HTMainText, cnt)); LYEntify(&Address, FALSE); if (isEmpty(Address)) { FREE(Address); continue; } fprintf(fp0, "<li><a href=\"%s\">%s</a>\n", Address, Address); FREE(Address); } fprintf(fp0, "\n</%s>\n", ((keypad_mode == NUMBERS_AS_ARROWS) ? "ol" : "ul")); EndInternalPage(fp0); LYCloseTempFP(fp0); /* * Make necessary changes to newdoc before returning to caller. If the * intern_w_post flag is set, we keep the POST data in newdoc that have * been passed in. They should be the same as in the loaded document for * which we generated the list. In that case the file we have written will * be associated with the same POST data when it is loaded after we are * done here, so that following one of the links we have marked as * "internal link" can lead back to the underlying document with the right * address+post_data combination. - kw */ if (intern_w_post) { newdoc->internal_link = TRUE; } else { LYFreePostData(newdoc); newdoc->internal_link = FALSE; } newdoc->isHEAD = FALSE; newdoc->safe = FALSE; return (0); }