Ejemplo n.º 1
0
  /* Wrapper for xsltApplyStylesheet */
xmlDocPtr mxslt_doc_xml_apply_stylesheet(mxslt_doc_t * mxslt_doc, xsltStylesheetPtr style, 
					 xmlDocPtr doc, const char ** params) {
  xmlDocPtr retval;
  xsltTransformContextPtr userCtxt;

  userCtxt=xsltNewTransformContext(style, doc);
  if(userCtxt == NULL)
    return NULL;

  xsltSetCtxtParseOptions(userCtxt, MXSLT_XSLT_OPTIONS);

    /* XXX I don't like this much :| ... I consider this an hack */
  /* userCtxt->_private=(void *)mxslt_doc; */
  userCtxt->outputFile=mxslt_doc->localfile;

#ifndef MXSLT_DISABLE_EXTENSIONS
  xsltRegisterExtElement(userCtxt, (xmlChar *)"header-set",
                         (xmlChar *)MXSLT_NS_URI, mxslt_transform_header);
  xsltRegisterExtElement(userCtxt, (xmlChar *)"value-of",
                         (xmlChar *)MXSLT_NS_URI, mxslt_transform_value_of);

  xsltRegisterExtElement(userCtxt, (xmlChar *)"header-set",
                         (xmlChar *)MXSLT_OBSOLETE_NS_URI, mxslt_transform_header);
  xsltRegisterExtElement(userCtxt, (xmlChar *)"value-of",
                         (xmlChar *)MXSLT_OBSOLETE_NS_URI, mxslt_transform_value_of);
#endif

  retval=xsltApplyStylesheetUser(style, doc, params, NULL, NULL, userCtxt);

  xsltFreeTransformContext(userCtxt);

  return retval;
}
Ejemplo n.º 2
0
bool XSLTProcessor::transformToString(Node* sourceNode, String& mimeType, String& resultString, String& resultEncoding)
{
    RefPtr<Document> ownerDocument = sourceNode->document();

    setXSLTLoadCallBack(docLoaderFunc, this, ownerDocument->docLoader());
    xsltStylesheetPtr sheet = xsltStylesheetPointer(m_stylesheet, m_stylesheetRootNode.get());
    if (!sheet) {
        setXSLTLoadCallBack(0, 0, 0);
        return false;
    }
    m_stylesheet->clearDocuments();

    xmlChar* origMethod = sheet->method;
    if (!origMethod && mimeType == "text/html")
        sheet->method = (xmlChar*)"html";

    bool success = false;
    bool shouldFreeSourceDoc = false;
    if (xmlDocPtr sourceDoc = xmlDocPtrFromNode(sourceNode, shouldFreeSourceDoc)) {
        // The XML declaration would prevent parsing the result as a fragment, and it's not needed even for documents,
        // as the result of this function is always immediately parsed.
        sheet->omitXmlDeclaration = true;

        xsltTransformContextPtr transformContext = xsltNewTransformContext(sheet, sourceDoc);
        registerXSLTExtensions(transformContext);

        // <http://bugs.webkit.org/show_bug.cgi?id=16077>: XSLT processor <xsl:sort> algorithm only compares by code point.
        xsltSetCtxtSortFunc(transformContext, xsltUnicodeSortFunction);

        // This is a workaround for a bug in libxslt.
        // The bug has been fixed in version 1.1.13, so once we ship that this can be removed.
        if (!transformContext->globalVars)
           transformContext->globalVars = xmlHashCreate(20);

        const char** params = xsltParamArrayFromParameterMap(m_parameters);
        xsltQuoteUserParams(transformContext, params);
        xmlDocPtr resultDoc = xsltApplyStylesheetUser(sheet, sourceDoc, 0, 0, 0, transformContext);

        xsltFreeTransformContext(transformContext);
        freeXsltParamArray(params);

        if (shouldFreeSourceDoc)
            xmlFreeDoc(sourceDoc);

        if ((success = saveResultToString(resultDoc, sheet, resultString))) {
            mimeType = resultMIMEType(resultDoc, sheet);
            resultEncoding = (char*)resultDoc->encoding;
        }
        xmlFreeDoc(resultDoc);
    }

    sheet->method = origMethod;
    setXSLTLoadCallBack(0, 0, 0);
    xsltFreeStylesheet(sheet);
    m_stylesheet = 0;

    return success;
}
Ejemplo n.º 3
0
static void free_xslt_info( struct xslt_info *info )
{
    if (info->pattern)
        xsltFreeCompMatchList( info->pattern );
    if (info->sheet)
        xsltFreeStylesheet( info->sheet );
    if (info->ctxt)
        xsltFreeTransformContext( info->ctxt );
}
Ejemplo n.º 4
0
	xsltTransformContext_auto_ptr& operator=(const xsltTransformContext_auto_ptr& _Y) 
		{if (this != &_Y)
			{if (_Ptr != _Y.get())
				{if (_Owns && _Ptr)
					xsltFreeTransformContext(_Ptr);
				_Owns = _Y._Owns; }
			else if (_Y._Owns)
				_Owns = true;
			_Ptr = _Y.release(); }
		return (*this); }
Ejemplo n.º 5
0
static gboolean
transform_free (YelpTransform *transform)
{
    gchar *chunk_id;

    /* If the queue isn't empty yet, try again later.  But because
     * threads scare me and I don't want runaway code, stop trying
     * after an insane number of attempts and just leak.
     */
    if (transform->idle_funcs > 0) {
	transform->free_attempts++;
	if (transform->free_attempts < 1000) {
	    return TRUE;
	} else {
	    g_warning ("Runaway free attempt detected.  Memory is about to leak.\n");
	    return FALSE;
	}
    }

    g_mutex_lock (transform->mutex);
    if (transform->input_xslt)
	transform->input_xslt->doc = NULL;
    if (transform->outputDoc)
	xmlFreeDoc (transform->outputDoc);
    if (transform->stylesheet)
	xsltFreeStylesheet (transform->stylesheet);
    if (transform->context)
	xsltFreeTransformContext (transform->context);

    g_strfreev (transform->params);

    /* FIXME: destroy data */
    while ((chunk_id = (gchar *) g_async_queue_try_pop (transform->queue)))
	g_free (chunk_id);
    g_async_queue_unref (transform->queue);
    g_mutex_unlock (transform->mutex);
    g_mutex_free (transform->mutex);

    if (transform->error)
	yelp_error_free (transform->error);

    g_free (transform);
    return FALSE;
}
Ejemplo n.º 6
0
static void
yelp_transform_dispose (GObject *object)
{
    YelpTransformPrivate *priv = GET_PRIV (object);

    debug_print (DB_FUNCTION, "entering\n");

    if (priv->queue) {
        gchar *chunk_id;
        while ((chunk_id = (gchar *) g_async_queue_try_pop (priv->queue)))
            g_free (chunk_id);
        g_async_queue_unref (priv->queue);
        priv->queue = NULL;
    }

    /* We do not free input or aux.  They belong to the caller, which
       must ensure they exist for the lifetime of the transform.  We
       have to set priv->aux_xslt->doc (which is priv->aux) to NULL
       before xsltFreeTransformContext.  Otherwise it will be freed,
       which we don't want.
     */
    if (priv->aux_xslt)
        priv->aux_xslt->doc = NULL;

    /* We free these in dispose to make absolutely certain that they're
       freed by the time any weak notify callbacks are called.  These
       may be used elsewhere to free resources like the input document.
     */
    if (priv->context) {
        xsltFreeTransformContext (priv->context);
        priv->context = NULL;
    }
    if (priv->stylesheet) {
        xsltFreeStylesheet (priv->stylesheet);
        priv->stylesheet = NULL;
    }
    if (priv->output) {
        xmlFreeDoc (priv->output);
        priv->output = NULL;
    }

    G_OBJECT_CLASS (yelp_transform_parent_class)->dispose (object);
}
Ejemplo n.º 7
0
// Processes input XML file (e.g., instance metadata) into output XML file or string (e.g., for libvirt)
// using XSL-T specification file (e.g., libvirt.xsl)
static int apply_xslt_stylesheet (const char * xsltStylesheetPath, const char * inputXmlPath, const char * outputXmlPath, char * outputXmlBuffer, int outputXmlBufferSize)
{
        int err = OK;

        INIT();
        xsltStylesheetPtr cur = xsltParseStylesheetFile ((const xmlChar *)xsltStylesheetPath);
        if (cur) {
                xmlDocPtr doc = xmlParseFile (inputXmlPath);
                if (doc) {
                        xsltTransformContextPtr ctxt = xsltNewTransformContext (cur, doc); // need context to get result
                        xsltSetCtxtParseOptions (ctxt, 0); // TODO: do we want any XSL-T parsing options?
                        xmlDocPtr res = xsltApplyStylesheetUser (cur, doc, NULL, NULL, NULL, ctxt); // applies XSLT to XML
                        int applied_ok = ctxt->state==XSLT_STATE_OK; // errors are communicated via ctxt->state
                        xsltFreeTransformContext (ctxt);
                        
                        if (res && applied_ok) {

                            // save to a file, if path was provied
                            if (outputXmlPath!=NULL) {
                                FILE * fp = fopen (outputXmlPath, "w");
                                if (fp) {
                                    int bytes = xsltSaveResultToFile (fp, res, cur);
                                    if (bytes==-1) {
                                        logprintfl (EUCAERROR, "ERROR: failed to save XML document to %s\n", outputXmlPath);
                                        err = ERROR;
                                    }
                                    fclose (fp);
                                } else {
                                    logprintfl (EUCAERROR, "ERROR: failed to create file %s\n", outputXmlPath);
                                    err = ERROR;
                                }                                
                            }

                            // convert to an ASCII buffer, if such was provided
                            if (err==OK && outputXmlBuffer!=NULL && outputXmlBufferSize > 0) {
                                xmlChar * buf;
                                int buf_size;
                                if (xsltSaveResultToString (&buf, &buf_size, res, cur)==0) { // success
                                    if (buf_size < outputXmlBufferSize) {
                                        bzero (outputXmlBuffer, outputXmlBufferSize);
                                        for (int i=0, j=0; i<buf_size; i++) {
                                            char c = (char) buf [i];
                                            if (c != '\n') // remove newlines
                                                outputXmlBuffer [j++] = c;
                                        }
                                    } else {
                                        logprintfl (EUCAERROR, "ERROR: XML string buffer is too small (%d > %d)\n", buf_size, outputXmlBufferSize);
                                        err = ERROR;
                                    }
                                    xmlFree (buf);
                                } else {
                                    logprintfl (EUCAERROR, "ERROR: failed to save XML document to a string\n");
                                    err = ERROR;
                                }
                            }
                        } else {
                            logprintfl (EUCAERROR, "ERROR: failed to apply stylesheet %s to %s\n", xsltStylesheetPath, inputXmlPath);
                            err = ERROR;
                        }
                        if (res!=NULL) xmlFreeDoc(res);
                        xmlFreeDoc(doc);
                } else {
                        logprintfl (EUCAERROR, "ERROR: failed to parse XML document %s\n", inputXmlPath);
                        err = ERROR;
                }
                xsltFreeStylesheet(cur);
        } else {
                logprintfl (EUCAERROR, "ERROR: failed to open and parse XSL-T stylesheet file %s\n", xsltStylesheetPath);
                err = ERROR;
        }

        return err;
}
Ejemplo n.º 8
0
static ngx_buf_t *
ngx_http_xslt_apply_stylesheet(ngx_http_request_t *r,
    ngx_http_xslt_filter_ctx_t *ctx)
{
    int                               len, rc, doc_type;
    u_char                           *type, *encoding;
    ngx_buf_t                        *b;
    ngx_uint_t                        i;
    xmlChar                          *buf;
    xmlDocPtr                         doc, res;
    ngx_http_xslt_sheet_t            *sheet;
    ngx_http_xslt_filter_loc_conf_t  *conf;

    conf = ngx_http_get_module_loc_conf(r, ngx_http_xslt_filter_module);
    sheet = conf->sheets.elts;
    doc = ctx->doc;

    /* preallocate array for 4 params */

    if (ngx_array_init(&ctx->params, r->pool, 4 * 2 + 1, sizeof(char *))
        != NGX_OK)
    {
        xmlFreeDoc(doc);
        return NULL;
    }

    for (i = 0; i < conf->sheets.nelts; i++) {

        ctx->transform = xsltNewTransformContext(sheet[i].stylesheet, doc);
        if (ctx->transform == NULL) {
            xmlFreeDoc(doc);
            return NULL;
        }

        if (conf->params
            && ngx_http_xslt_params(r, ctx, conf->params, 0) != NGX_OK)
        {
            xsltFreeTransformContext(ctx->transform);
            xmlFreeDoc(doc);
            return NULL;
        }

        if (ngx_http_xslt_params(r, ctx, &sheet[i].params, 1) != NGX_OK) {
            xsltFreeTransformContext(ctx->transform);
            xmlFreeDoc(doc);
            return NULL;
        }

        res = xsltApplyStylesheetUser(sheet[i].stylesheet, doc,
                                      ctx->params.elts, NULL, NULL,
                                      ctx->transform);

        xsltFreeTransformContext(ctx->transform);
        xmlFreeDoc(doc);

        if (res == NULL) {
            ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
                          "xsltApplyStylesheet() failed");
            return NULL;
        }

        doc = res;

        /* reset array elements */
        ctx->params.nelts = 0;
    }

    /* there must be at least one stylesheet */

    if (r == r->main) {
        type = ngx_http_xslt_content_type(sheet[i - 1].stylesheet);

    } else {
        type = NULL;
    }

    encoding = ngx_http_xslt_encoding(sheet[i - 1].stylesheet);
    doc_type = doc->type;

    ngx_log_debug3(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
                   "xslt filter type: %d t:%s e:%s",
                   doc_type, type ? type : (u_char *) "(null)",
                   encoding ? encoding : (u_char *) "(null)");

    rc = xsltSaveResultToString(&buf, &len, doc, sheet[i - 1].stylesheet);

    xmlFreeDoc(doc);

    if (rc != 0) {
        ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
                      "xsltSaveResultToString() failed");
        return NULL;
    }

    if (len == 0) {
        ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
                      "xsltSaveResultToString() returned zero-length result");
        return NULL;
    }

    b = ngx_pcalloc(r->pool, sizeof(ngx_buf_t));
    if (b == NULL) {
        ngx_free(buf);
        return NULL;
    }

    b->pos = buf;
    b->last = buf + len;
    b->memory = 1;

    if (encoding) {
        r->headers_out.charset.len = ngx_strlen(encoding);
        r->headers_out.charset.data = encoding;
    }

    if (r != r->main) {
        return b;
    }

    b->last_buf = 1;

    if (type) {
        len = ngx_strlen(type);

        r->headers_out.content_type_len = len;
        r->headers_out.content_type.len = len;
        r->headers_out.content_type.data = type;

    } else if (doc_type == XML_HTML_DOCUMENT_NODE) {

        r->headers_out.content_type_len = sizeof("text/html") - 1;
        ngx_str_set(&r->headers_out.content_type, "text/html");
    }

    r->headers_out.content_type_lowcase = NULL;

    return b;
}
Ejemplo n.º 9
0
	~xsltTransformContext_auto_ptr()
		{if (_Owns && _Ptr)
			xsltFreeTransformContext(_Ptr); }
Ejemplo n.º 10
0
static xmlDocPtr php_xsl_apply_stylesheet(zval *id, xsl_object *intern, xsltStylesheetPtr style, zval *docp) /* {{{ */
{
	xmlDocPtr newdocp = NULL;
	xmlDocPtr doc = NULL;
	xmlNodePtr node = NULL;
	xsltTransformContextPtr ctxt;
	php_libxml_node_object *object;
	char **params = NULL;
	int clone;
	zval *doXInclude, member, rv;
	zend_object_handlers *std_hnd;
	FILE *f;
	int secPrefsError = 0;
	int secPrefsValue;
	xsltSecurityPrefsPtr secPrefs = NULL;

	node = php_libxml_import_node(docp);

	if (node) {
		doc = node->doc;
	}
	if (doc == NULL) {
		php_error_docref(NULL, E_WARNING, "Invalid Document");
		return NULL;
	}

	if (style == NULL) {
		php_error_docref(NULL, E_WARNING, "No stylesheet associated to this object");
		return NULL;
	}

	if (intern->profiling) {
		if (php_check_open_basedir(intern->profiling)) {
			f = NULL;
		} else {
			f = VCWD_FOPEN(intern->profiling, "w");
		}
	} else {
		f = NULL;
	}

	if (intern->parameter) {
		params = php_xsl_xslt_make_params(intern->parameter, 0);
	}

	intern->doc = emalloc(sizeof(php_libxml_node_object));
	memset(intern->doc, 0, sizeof(php_libxml_node_object));

	if (intern->hasKeys == 1) {
		doc = xmlCopyDoc(doc, 1);
	} else {
		object = Z_LIBXML_NODE_P(docp);
		intern->doc->document = object->document;
	}

	php_libxml_increment_doc_ref(intern->doc, doc);

	ctxt = xsltNewTransformContext(style, doc);
	ctxt->_private = (void *) intern;

	std_hnd = zend_get_std_object_handlers();

	ZVAL_STRING(&member, "doXInclude");
	doXInclude = std_hnd->read_property(id, &member, BP_VAR_IS, NULL, &rv);
	if (Z_TYPE_P(doXInclude) != IS_NULL) {
		convert_to_long(doXInclude);
		ctxt->xinclude = Z_LVAL_P(doXInclude);
	}
	zval_ptr_dtor(&member);

	secPrefsValue = intern->securityPrefs;

	/* if securityPrefs is set to NONE, we don't have to do any checks, but otherwise... */
	if (secPrefsValue != XSL_SECPREF_NONE) {
		secPrefs = xsltNewSecurityPrefs();
		if (secPrefsValue & XSL_SECPREF_READ_FILE ) {
			if (0 != xsltSetSecurityPrefs(secPrefs, XSLT_SECPREF_READ_FILE, xsltSecurityForbid)) {
				secPrefsError = 1;
			}
		}
		if (secPrefsValue & XSL_SECPREF_WRITE_FILE ) {
			if (0 != xsltSetSecurityPrefs(secPrefs, XSLT_SECPREF_WRITE_FILE, xsltSecurityForbid)) {
				secPrefsError = 1;
			}
		}
		if (secPrefsValue & XSL_SECPREF_CREATE_DIRECTORY ) {
			if (0 != xsltSetSecurityPrefs(secPrefs, XSLT_SECPREF_CREATE_DIRECTORY, xsltSecurityForbid)) {
				secPrefsError = 1;
			}
		}
		if (secPrefsValue & XSL_SECPREF_READ_NETWORK) {
			if (0 != xsltSetSecurityPrefs(secPrefs, XSLT_SECPREF_READ_NETWORK, xsltSecurityForbid)) {
				secPrefsError = 1;
			}
		}
		if (secPrefsValue & XSL_SECPREF_WRITE_NETWORK) {
			if (0 != xsltSetSecurityPrefs(secPrefs, XSLT_SECPREF_WRITE_NETWORK, xsltSecurityForbid)) {
				secPrefsError = 1;
			}
		}

		if (0 != xsltSetCtxtSecurityPrefs(secPrefs, ctxt)) {
			secPrefsError = 1;
		}
	}

	if (secPrefsError == 1) {
		php_error_docref(NULL, E_WARNING, "Can't set libxslt security properties, not doing transformation for security reasons");
	} else {
		newdocp = xsltApplyStylesheetUser(style, doc, (const char**) params,  NULL, f, ctxt);
	}
	if (f) {
		fclose(f);
	}

	xsltFreeTransformContext(ctxt);
	if (secPrefs) {
		xsltFreeSecurityPrefs(secPrefs);
	}

	if (intern->node_list != NULL) {
		zend_hash_destroy(intern->node_list);
		FREE_HASHTABLE(intern->node_list);
		intern->node_list = NULL;
	}

	php_libxml_decrement_doc_ref(intern->doc);
	efree(intern->doc);
	intern->doc = NULL;

	if (params) {
		clone = 0;
		while(params[clone]) {
			efree(params[clone++]);
		}
		efree(params);
	}

	return newdocp;

}
Ejemplo n.º 11
0
xmlDocPtr c_XSLTProcessor::apply_stylesheet() {
  SYNC_VM_REGS_SCOPED();

  if (m_stylesheet == nullptr || m_doc == nullptr) {
    raise_error("Unable to apply stylesheet");
    return nullptr;
  }

  xsltTransformContextPtr ctxt = xsltNewTransformContext (m_stylesheet, m_doc);
  if (ctxt == nullptr) {
    raise_error("Unable to apply stylesheet");
    return nullptr;
  }

  ctxt->_private = this;

  xsltSecurityPrefsPtr prefs = nullptr;
  if (m_secprefs != k_XSL_SECPREF_NONE) {
    prefs = xsltNewSecurityPrefs();
    int error = 0;

    if (m_secprefs & k_XSL_SECPREF_READ_FILE) {
      if (xsltSetSecurityPrefs(prefs,
                               XSLT_SECPREF_READ_FILE,
                               xsltSecurityForbid) != 0) {
        error = 1;
      }
    }

    if (m_secprefs & k_XSL_SECPREF_WRITE_FILE) {
      if (xsltSetSecurityPrefs(prefs,
                               XSLT_SECPREF_WRITE_FILE,
                               xsltSecurityForbid) != 0) {
        error = 1;
      }
    }

    if (m_secprefs & k_XSL_SECPREF_CREATE_DIRECTORY) {
      if (xsltSetSecurityPrefs(prefs,
                               XSLT_SECPREF_CREATE_DIRECTORY,
                               xsltSecurityForbid) != 0) {
        error = 1;
      }
    }

    if (m_secprefs & k_XSL_SECPREF_READ_NETWORK) {
      if (xsltSetSecurityPrefs(prefs,
                               XSLT_SECPREF_READ_NETWORK,
                               xsltSecurityForbid) != 0) {
        error = 1;
      }
    }

    if (m_secprefs & k_XSL_SECPREF_WRITE_NETWORK) {
      if (xsltSetSecurityPrefs(prefs,
                               XSLT_SECPREF_WRITE_NETWORK,
                               xsltSecurityForbid) != 0) {
        error = 1;
      }
    }

    if (xsltSetCtxtSecurityPrefs(prefs, ctxt) != 0) {
      error = 1;
    }

    if (error == 1) {
      raise_error("Can't set libxslt security properties, not doing "
                  "transformation for security reasons");
      return nullptr;
    }
  }

  xsltRegisterExtFunction(ctxt,
    (const xmlChar*) "functionString",
    (const xmlChar*) "http://php.net/xsl",
    xslt_ext_function_string_php
  );

  xsltRegisterExtFunction(ctxt,
    (const xmlChar*) "function",
    (const xmlChar*) "http://php.net/xsl",
    xslt_ext_function_object_php
  );

  for (ArrayIter iter(m_params); iter; ++iter) {
    assert(iter.first().isString());
    assert(iter.second().isString());

    xmlChar *value = xslt_string_to_xpathexpr(iter.second().toString().c_str());
    if (value) {
      xsltEvalOneUserParam(ctxt,
        (const xmlChar*)iter.first().toString().c_str(),
        (const xmlChar*)value
      );

      xmlFree(value);
    }
  }

  FILE *profile = nullptr;
  if (m_profile) {
    profile = fopen(m_profile.data(), "w");
  }

  xmlDocPtr res = xsltApplyStylesheetUser(m_stylesheet,
                                          m_doc,
                                          nullptr,
                                          nullptr,
                                          profile,
                                          ctxt);

  if (profile) {
    fclose(profile);
  }

  xsltFreeTransformContext(ctxt);

  if (prefs) {
    xsltFreeSecurityPrefs(prefs);
  }

  return res;
}