Пример #1
0
// Operations
BOOL CLinks::AddLinkRelationships (HTAnchor * source)
{
    ASSERT(source != NULL);
    if (!m_hWnd) return FALSE;
    HTParentAnchor * src = HTAnchor_parent(source);

    // Update the list control with three columns
    CListCtrl &ListCtrl = m_pLinkList->GetListCtrl();
    int iItem = ListCtrl.GetItemCount();
    int cnt;
    for (cnt=0; cnt<iItem; cnt++) {
        CString l_type = ListCtrl.GetItemText(cnt, 0);
        CString l_dir = ListCtrl.GetItemText(cnt, 1);
        CString l_dest = ListCtrl.GetItemText(cnt, 2);
        
        if (!l_type.IsEmpty() && !l_dir.IsEmpty() && !l_dest.IsEmpty()) {
            char * link_addr = HTParse(l_dest, "", PARSE_ALL);
            HTParentAnchor * dest = HTAnchor_parent(HTAnchor_findAddress(link_addr));
            
            /* Now add the new relation */
            if (l_dir == "forward") {
                HTLink_add((HTAnchor *) src, (HTAnchor *) dest,
                    (HTLinkType) HTAtom_caseFor(l_type),
                    METHOD_INVALID);
            } else if (l_dir == "reverse") {
                HTLink_add((HTAnchor *) dest, (HTAnchor *) src,
                    (HTLinkType) HTAtom_caseFor(l_type),
                    METHOD_INVALID);
            } else
                ASSERT(1);
        }
    }
    return TRUE;
}
Пример #2
0
/*	Create or find a child anchor with a possible link
**	--------------------------------------------------
**
**	Create new anchor with a given parent and possibly
**	a name, and possibly a link to a _relatively_ named anchor.
**	All parameters EXCEPT parent can be NULL
*/
PUBLIC HTChildAnchor * HTAnchor_findChildAndLink (HTParentAnchor *	parent,
						  const char *		tag,
						  const char *		href,
						  HTLinkType		ltype)
{
    HTChildAnchor * child = HTAnchor_findChild(parent, tag);
    if (child && href && *href) {
	char * relative_to = HTAnchor_expandedAddress((HTAnchor *) parent);
	char * parsed_address = HTParse(href, relative_to, PARSE_ALL);
	HTAnchor * dest = HTAnchor_findAddress(parsed_address);
	HTLink_add((HTAnchor *) child, dest, ltype, METHOD_INVALID);
	HT_FREE(parsed_address);
	HT_FREE(relative_to);
    }
    return child;
}
Пример #3
0
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);
}
Пример #4
0
/*
**	Redirection AFTER filter
**	------------------------
**	The redirection handler only handles redirections
**	on the GET or HEAD method (or any other safe method)
*/
PUBLIC int HTRedirectFilter (HTRequest * request, HTResponse * response,
			     void * param, int status)
{
    HTMethod method = HTRequest_method(request); 
    HTAnchor * new_anchor = HTResponse_redirection(response); 

    /* Check for destination */
    if (!new_anchor) {
	HTTRACE(PROT_TRACE, "Redirection. No destination\n");
	return HT_OK;
    }

    /*
    ** Only do automatic redirect on GET and HEAD. Ask for all
    ** other methods.
    */
    if (!HTMethod_isSafe(method)) {

	/*
	** If we got a 303 See Other then change the method to GET.
	** Otherwise ask the user whether we should continue.
	*/
	if (status == HT_SEE_OTHER) {
	    HTTRACE(PROT_TRACE, "Redirection. Changing method from %s to GET\n" _ 
			HTMethod_name(method));
	    HTRequest_setMethod(request, METHOD_GET);
	} else {
	    HTAlertCallback * prompt = HTAlert_find(HT_A_CONFIRM);
	    if (prompt) {
		if ((*prompt)(request, HT_A_CONFIRM, HT_MSG_REDIRECTION,
			      NULL, NULL, NULL) != YES)
		    return HT_OK;
	    }
	}
    } 

    /* Register the redirection as a link relationship */
    {
	HTLinkType ltype = status==HT_PERM_REDIRECT ? HT_LR_PERM_REDIRECT :
	    (status==HT_TEMP_REDIRECT || status==HT_FOUND) ? HT_LR_TEMP_REDIRECT :
	    status==HT_SEE_OTHER ? HT_LR_SEE_OTHER : NULL;
	if (ltype) {
	    HTLink_add((HTAnchor *) HTRequest_anchor(request), new_anchor, 
		       ltype, method);
	}
    }

    /* Delete any auth credendials as they get regenerated */
    HTRequest_deleteCredentialsAll(request);

    /*
    **  Start new request with the redirect anchor found in the headers.
    **	Note that we reuse the same request object which means that we must
    **  keep this around until the redirected request has terminated. It also
    **  allows us in an easy way to keep track of the number of redirections
    **	so that we can detect endless loops.
    */ 
    if (HTRequest_doRetry(request)) { 
	HTLoadAnchor(new_anchor, request);
    } else {
	HTRequest_addError(request, ERR_FATAL, NO, HTERR_MAX_REDIRECT,
			   NULL, 0, "HTRedirectFilter");
	return HT_OK;		/* Wanna fall through */
    }

    /*
    **  By returning HT_ERROR we make sure that this is the last handler to be
    **  called. We do this as we don't want any other filter to delete the 
    **  request object now when we have just started a new one ourselves
    */
    return HT_ERROR;
}