Commit f6204768 authored by Germán Poo-Caamaño's avatar Germán Poo-Caamaño

browser-plugin: Remove browser-plugin support

Epiphany deprecated support for NPAPI for 3.30, and when enabled
manually it will not download the PDF document from the network.
Therefore, it does not make sense to keep the browser-plugin
anymore.

Fixes #968
parent fbb0a963
Pipeline #34598 passed with stage
in 18 minutes and 26 seconds
......@@ -25,10 +25,6 @@ if ENABLE_PREVIEWER
SUBDIRS += previewer
endif
if ENABLE_BROWSER_PLUGIN
SUBDIRS += browser-plugin
endif
NULL =
pkgconfigdir = $(libdir)/pkgconfig
......
This diff is collapsed.
<?xml version="1.0" encoding="UTF-8"?>
<!--
Copyright © 2014 Igalia S.L.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
This program is distributed in the hope conf it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
-->
<gresources>
<gresource prefix="/org/gnome/evince/browser">
<file alias="ui/evince-browser.css" compressed="true">evince-browser.css</file>
<file alias="ui/thumbnail-frame.png" compressed="true">thumbnail-frame.png</file>
</gresource>
</gresources>
/*
* Copyright (C) 2014 Igalia S.L.
*
* Evince is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* Evince is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#ifndef EvBrowserPlugin_h
#define EvBrowserPlugin_h
#include <evince-document.h>
#include <evince-view.h>
#include "EvMemoryUtils.h"
#include "npapi.h"
#include "npruntime.h"
typedef union _XEvent XEvent;
struct EvBrowserPluginClass;
class EvBrowserPlugin: public NPObject {
public:
static EvBrowserPlugin* create(NPP);
static const char *nameString();
static const char *descriptionString();
// NPP API
NPError initialize(NPMIMEType, uint16_t mode, int16_t argc, char *argn[], char *argv[], NPSavedData *);
NPError setWindow(NPWindow *);
NPError newStream(NPMIMEType, NPStream *, NPBool seekable, uint16_t *stype);
NPError destroyStream(NPStream *, NPReason);
void streamAsFile(NPStream *, const char *fname);
int32_t writeReady(NPStream *);
int32_t write(NPStream *, int32_t offset, int32_t len, void *buffer);
void print(NPPrint *);
int16_t handleEvent(XEvent *);
void urlNotify(const char *url, NPReason, void *notifyData);
// Viewer API
EvDocumentModel *model() const { return m_model; }
unsigned currentPage() const;
unsigned pageCount() const;
double zoom() const;
void setZoom(double scale);
void goToPreviousPage();
void goToNextPage();
void goToPage(unsigned page);
void goToPage(const char *pageLabel);
void activateLink(EvLink *);
bool isContinuous() const;
void setContinuous(bool);
void toggleContinuous();
bool isDual() const;
void setDual(bool);
void toggleDual();
void zoomIn();
void zoomOut();
EvSizingMode sizingMode() const;
void setSizingMode(EvSizingMode);
void download() const;
void print() const;
bool toolbarVisible() const;
void setToolbarVisible(bool);
bool canDownload() const;
void setSearchModeEnabled(bool);
void search(EvJobFind *);
enum SearchDirection { Next, Previous };
void search(SearchDirection);
void clearSearch();
void restartSearch();
private:
EvBrowserPlugin(NPP);
virtual ~EvBrowserPlugin();
// Scripting interface
static NPObject *allocate(NPP, NPClass *);
static void deallocate(NPObject *);
static void invalidate(NPObject *);
static bool hasMethod(NPObject *, NPIdentifier name);
static bool invoke(NPObject *, NPIdentifier name, const NPVariant *args, uint32_t argCount, NPVariant *result);
static bool hasProperty(NPObject *, NPIdentifier name);
static bool getProperty(NPObject *, NPIdentifier name, NPVariant *);
static bool setProperty(NPObject *, NPIdentifier name, const NPVariant *);
NPP m_NPP;
GtkWidget *m_window;
EvDocumentModel *m_model;
EvView *m_view;
GtkWidget *m_toolbar;
unique_gptr<char> m_url;
static EvBrowserPluginClass s_pluginClass;
};
#endif // EvBrowserPlugin_h
/*
* Copyright (C) 2014 Igalia S.L.
*
* Evince is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* Evince is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#include "config.h"
#include "EvBrowserPlugin.h"
#include "EvMemoryUtils.h"
#include "npfunctions.h"
#include "npruntime.h"
#include <gdk/gdk.h>
#ifdef GDK_WINDOWING_WAYLAND
#include <gdk/gdkwayland.h>
#endif
static NPNetscapeFuncs *browser;
static unique_gptr<char> mimeDescription;
static EvBrowserPlugin *pluginForInstance(NPP instance)
{
if (!instance)
return nullptr;
return static_cast<EvBrowserPlugin *>(instance->pdata);
}
NPError NPP_New(NPMIMEType pluginType, NPP instance, uint16_t mode, int16_t argc, char *argn[], char *argv[], NPSavedData *savedData)
{
if (!instance)
return NPERR_INVALID_INSTANCE_ERROR;
return EvBrowserPlugin::create(instance)->initialize(pluginType, mode, argc, argn, argv, savedData);
}
NPError NPP_Destroy(NPP instance, NPSavedData **saveData)
{
EvBrowserPlugin *plugin = pluginForInstance(instance);
if (!plugin)
return NPERR_INVALID_INSTANCE_ERROR;
browser->releaseobject(static_cast<NPObject *>(plugin));
return NPERR_NO_ERROR;
}
NPError NPP_SetWindow(NPP instance, NPWindow *window)
{
EvBrowserPlugin *plugin = pluginForInstance(instance);
if (!plugin)
return NPERR_INVALID_INSTANCE_ERROR;
return plugin->setWindow(window);
}
NPError NPP_NewStream(NPP instance, NPMIMEType type, NPStream *stream, NPBool seekable, uint16_t *stype)
{
EvBrowserPlugin *plugin = pluginForInstance(instance);
if (!plugin)
return NPERR_INVALID_INSTANCE_ERROR;
return plugin->newStream(type, stream, seekable, stype);
}
NPError NPP_DestroyStream(NPP instance, NPStream *stream, NPReason reason)
{
EvBrowserPlugin *plugin = pluginForInstance(instance);
if (!plugin)
return NPERR_INVALID_INSTANCE_ERROR;
return plugin->destroyStream(stream, reason);
}
void NPP_StreamAsFile(NPP instance, NPStream *stream, const char *fname)
{
EvBrowserPlugin *plugin = pluginForInstance(instance);
if (!plugin)
return;
return plugin->streamAsFile(stream, fname);
}
int32_t NPP_WriteReady(NPP instance, NPStream *stream)
{
EvBrowserPlugin *plugin = pluginForInstance(instance);
if (!plugin)
return -1;
return plugin->writeReady(stream);
}
int32_t NPP_Write(NPP instance, NPStream *stream, int32_t offset, int32_t len, void *buffer)
{
EvBrowserPlugin *plugin = pluginForInstance(instance);
if (!plugin)
return -1;
return plugin->write(stream, offset, len, buffer);
}
void NPP_Print(NPP instance, NPPrint *platformPrint)
{
EvBrowserPlugin *plugin = pluginForInstance(instance);
if (!plugin)
return;
return plugin->print(platformPrint);
}
int16_t NPP_HandleEvent(NPP instance, void *event)
{
EvBrowserPlugin *plugin = pluginForInstance(instance);
if (!plugin)
return 0;
return plugin->handleEvent(static_cast<XEvent *>(event));
}
void NPP_URLNotify(NPP instance, const char *url, NPReason reason, void *notifyData)
{
EvBrowserPlugin *plugin = pluginForInstance(instance);
if (!plugin)
return;
return plugin->urlNotify(url, reason, notifyData);
}
NPError NPP_GetValue(NPP instance, NPPVariable variable, void *value)
{
switch (variable) {
case NPPVpluginNameString:
*((char **)value) = const_cast<char *>(EvBrowserPlugin::nameString());
return NPERR_NO_ERROR;
case NPPVpluginDescriptionString:
*((char **)value) = const_cast<char *>(EvBrowserPlugin::descriptionString());
return NPERR_NO_ERROR;
case NPPVpluginNeedsXEmbed:
*((NPBool *)value) = TRUE;
return NPERR_NO_ERROR;
case NPPVpluginScriptableNPObject: {
EvBrowserPlugin *plugin = pluginForInstance(instance);
if (!plugin)
return NPERR_INVALID_PLUGIN_ERROR;
browser->retainobject(static_cast<NPObject *>(plugin));
*((NPObject **)value) = plugin;
return NPERR_NO_ERROR;
}
default:
return NPERR_INVALID_PARAM;
}
return NPERR_GENERIC_ERROR;
}
NPError NPP_SetValue(NPP, NPNVariable, void *)
{
return NPERR_NO_ERROR;
}
static void initializePluginFuncs(NPPluginFuncs *pluginFuncs)
{
pluginFuncs->version = (NP_VERSION_MAJOR << 8) | NP_VERSION_MINOR;
pluginFuncs->size = sizeof(pluginFuncs);
pluginFuncs->newp = NPP_New;
pluginFuncs->destroy = NPP_Destroy;
pluginFuncs->setwindow = NPP_SetWindow;
pluginFuncs->newstream = NPP_NewStream;
pluginFuncs->destroystream = NPP_DestroyStream;
pluginFuncs->asfile = NPP_StreamAsFile;
pluginFuncs->writeready = NPP_WriteReady;
pluginFuncs->write = NPP_Write;
pluginFuncs->print = NPP_Print;
pluginFuncs->event = NPP_HandleEvent;
pluginFuncs->urlnotify = NPP_URLNotify;
pluginFuncs->getvalue = NPP_GetValue;
pluginFuncs->setvalue = NPP_SetValue;
}
NPError NP_Initialize(NPNetscapeFuncs *browserFuncs, NPPluginFuncs *pluginFuncs)
{
if (!browserFuncs || !pluginFuncs)
return NPERR_INVALID_FUNCTABLE_ERROR;
if ((browserFuncs->version >> 8) > NP_VERSION_MAJOR)
return NPERR_INCOMPATIBLE_VERSION_ERROR;
if (!ev_init())
return NPERR_GENERIC_ERROR;
gtk_init(nullptr, nullptr);
#ifdef GDK_WINDOWING_WAYLAND
if (GDK_IS_WAYLAND_DISPLAY(gdk_display_get_default()))
return NPERR_GENERIC_ERROR;
#endif
browser = browserFuncs;
initializePluginFuncs(pluginFuncs);
GBytes *resourceData = g_resources_lookup_data("/org/gnome/evince/browser/ui/evince-browser.css", G_RESOURCE_LOOKUP_FLAGS_NONE, nullptr);
if (resourceData) {
GtkCssProvider *cssProvider = gtk_css_provider_new();
gtk_css_provider_load_from_data(cssProvider, static_cast<const gchar *>(g_bytes_get_data(resourceData, nullptr)), g_bytes_get_size(resourceData), nullptr);
g_bytes_unref(resourceData);
gtk_style_context_add_provider_for_screen(gdk_screen_get_default(), GTK_STYLE_PROVIDER(cssProvider), GTK_STYLE_PROVIDER_PRIORITY_APPLICATION);
g_object_unref(cssProvider);
}
return NPERR_NO_ERROR;
}
NPError NP_Shutdown()
{
ev_shutdown();
return NPERR_NO_ERROR;
}
static const struct {
const char *mime;
const char *extensions;
} mimeExtensions[] = {
{ "application/postscript", "ps" },
{ "application/x-ext-ps", "ps" },
{ "application/x-bzpostscript", "ps.bz2" },
{ "application/x-gzpostscript", "ps.gz" },
{ "image/x-eps", "eps,epsi,epsf" },
{ "application/x-ext-eps", "eps,epsi,epsf" },
{ "image/x-bzeps", "eps.bz2,epsi.bz2,epsf.bz2" },
{ "image/x-gzeps", "eps.gz,epsi.gz,epsf.gz" },
{ "image/tiff", "tif,tiff" },
{ "application/pdf", "pdf" },
{ "application/x-ext-pdf", "pdf" },
{ "application/x-bzpdf", "pdf.bz2" },
{ "application/x-gzpdf", "pdf.gz" },
{ "application/x-xzpdf", "pdf.xz" },
{ "application/x-dvi", "dvi" },
{ "application/x-ext-dvi", "dvi" },
{ "application/x-bzdvi", "dvi.bz2" },
{ "application/x-gzdvi", "dvi.gz" },
{ "application/x-cbr", "cbr" },
{ "application/x-ext-cbr", "cbr" },
{ "application/x-cbz", "cbz" },
{ "application/x-ext-cbz", "cbz" },
{ "application/x-cb7", "cb7" },
{ "application/x-ext-cb7", "cb7" },
{ "application/x-cbt", "cbt" },
{ "application/x-ext-cbt", "cbt" },
{ "image/vnd.djvu", "djvu,djv" },
{ "image/vnd.djvu+multipage", "djvu,djv" },
{ "application/x-ext-djv", "djv" },
{ "application/x-ext-djvu", "djvu" },
{ "application/oxps", "xps,oxps" },
{ "application/vnd.ms-xpsdocument", "xps,oxps" }
};
const char *NP_GetMIMEDescription()
{
if (mimeDescription)
return mimeDescription.get();
if (!ev_init())
return nullptr;
#ifdef GDK_WINDOWING_WAYLAND
if (GDK_IS_WAYLAND_DISPLAY(gdk_display_get_default()))
return nullptr;
#endif
GString *mimeDescriptionStr = g_string_new(nullptr);
GList *typesInfo = ev_backends_manager_get_all_types_info();
for (GList *l = typesInfo; l; l = g_list_next(l)) {
EvTypeInfo *info = static_cast<EvTypeInfo *>(l->data);
for (unsigned i = 0; info->mime_types[i]; ++i) {
const char *extensions = [](const char *mime) -> const char * {
for (unsigned i = 0; i < G_N_ELEMENTS(mimeExtensions); ++i) {
if (g_ascii_strcasecmp(mimeExtensions[i].mime, mime) == 0)
return mimeExtensions[i].extensions;
}
return nullptr;
}(info->mime_types[i]);
if (!extensions)
continue;
g_string_append_printf(mimeDescriptionStr, "%s:%s:%s;",
info->mime_types[i],
extensions,
info->desc);
}
}
g_list_free(typesInfo);
mimeDescription.reset(g_string_free(mimeDescriptionStr, FALSE));
ev_shutdown();
return mimeDescription.get();
}
NPError NP_GetValue(void *, NPPVariable variable, void *value)
{
return NPP_GetValue(nullptr, variable, value);
}
NPObject *NPN_CreateObject(NPP instance, NPClass *npClass)
{
return browser->createobject(instance, npClass);
}
void NPN_GetStringIdentifiers(const NPUTF8 **names, int32_t nameCount, NPIdentifier *identifiers)
{
browser->getstringidentifiers(names, nameCount, identifiers);
}
NPError NPN_GetURL(NPP instance, const char* url, const char* target)
{
return browser->geturl(instance, url, target);
}
const char *NPN_UserAgent(NPP instance)
{
return browser->uagent(instance);
}
void *NPN_MemAlloc(uint32_t size)
{
return browser->memalloc(size);
}
void NPN_MemFree(void* ptr)
{
if (ptr)
browser->memfree(ptr);
}
static void __attribute__((constructor)) browserPluginConstructor()
{
ev_init();
}
static void __attribute__((destructor)) browserPluginDestructor()
{
ev_shutdown();
}
This diff is collapsed.
/*
* Copyright (C) 2014 Igalia S.L.
*
* Evince is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* Evince is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#ifndef EvBrowserPluginToolbar_h
#define EvBrowserPluginToolbar_h
#include "EvBrowserPlugin.h"
#include <gtk/gtk.h>
#include <evince-view.h>
G_BEGIN_DECLS
#define EV_TYPE_BROWSER_PLUGIN_TOOLBAR (ev_browser_plugin_toolbar_get_type())
#define EV_BROWSER_PLUGIN_TOOLBAR(object) (G_TYPE_CHECK_INSTANCE_CAST((object), EV_TYPE_BROWSER_PLUGIN_TOOLBAR, EvBrowserPluginToolbar))
#define EV_IS_BROWSER_PLUGIN_TOOLBAR(object) (G_TYPE_CHECK_INSTANCE_TYPE((object), EV_TYPE_BROWSER_PLUGIN_TOOLBAR))
#define EV_BROWSER_PLUGIN_TOOLBAR_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), EV_TYPE_BROWSER_PLUGIN_TOOLBAR, EvBrowserPluginToolbarClass))
#define EV_IS_BROWSER_PLUGIN_TOOLBAR_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), EV_TYPE_BROWSER_PLUGIN_TOOLBAR))
#define EV_BROWSER_PLUGIN_TOOLBAR_GET_CLASS(object) (G_TYPE_INSTANCE_GET_CLASS((object), EV_TYPE_BROWSER_PLUGIN_TOOLBAR, EvBrowserPluginToolbarClass))
typedef struct _EvBrowserPluginToolbar EvBrowserPluginToolbar;
typedef struct _EvBrowserPluginToolbarClass EvBrowserPluginToolbarClass;
typedef struct _EvBrowserPluginToolbarPrivate EvBrowserPluginToolbarPrivate;
struct _EvBrowserPluginToolbar {
GtkToolbar base_instance;
EvBrowserPluginToolbarPrivate *priv;
};
struct _EvBrowserPluginToolbarClass {
GtkToolbarClass base_class;
};
GType ev_browser_plugin_toolbar_get_type (void);
GtkWidget *ev_browser_plugin_toolbar_new (EvBrowserPlugin *plugin);
G_END_DECLS
#endif // EvBrowserPluginToolbar_h
/*
* Copyright (C) 2014 Igalia S.L.
*
* Evince is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* Evince is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#ifndef EvMemoryUtils_h
#define EvMemoryUtils_h
#include <glib.h>
#include <memory>
template<typename T>
struct unique_gptr_deleter {
void operator()(T* ptr) const { g_free(ptr); }
};
template<typename T>
using unique_gptr = std::unique_ptr<T, unique_gptr_deleter<T>>;
#endif // EvMemoryUtils_h
plugindir = $(BROWSER_PLUGIN_DIR)
plugin_LTLIBRARIES = libevbrowserplugin.la
npapi_sources = \
npapi/npapi.h \
npapi/npfunctions.h \
npapi/npruntime.h \
npapi/nptypes.h
libevbrowserplugin_la_SOURCES = \
$(npapi_sources) \
EvBrowserPluginMain.cpp \
EvBrowserPlugin.h \
EvBrowserPlugin.cpp \
EvBrowserPluginToolbar.h \
EvBrowserPluginToolbar.cpp \
EvMemoryUtils.h
nodist_libevbrowserplugin_la_SOURCES = \
EvBrowserPluginResources.c
libevbrowserplugin_la_CPPFLAGS = \
-I$(top_srcdir) \
-I$(top_srcdir)/browser-plugin/npapi \
-I$(top_srcdir)/libdocument \
-I$(top_srcdir)/libview \
-I$(top_srcdir)/libmisc \
-DGNOMELOCALEDIR=\"$(datadir)/locale\" \
-DEVINCE_COMPILATION \
-DXP_UNIX \
-DMOZ_X11 \
$(BROWSER_PLUGIN_CFLAGS) \
$(AM_CPPFLAGS)
libevbrowserplugin_la_CXXFLAGS = \
-std=c++11 \
-fno-exceptions \
-fno-strict-aliasing \
-fno-rtti \
$(AM_CXXFLAGS)
libevbrowserplugin_la_LDFLAGS = \
-avoid-version \
-export-symbols $(top_srcdir)/browser-plugin/plugin.symbols \
-module \
-no-undefined \
-Wl,-z,nodelete \
$(AM_LDFLAGS)
libevbrowserplugin_la_LIBADD = \
$(top_builddir)/libdocument/libevdocument3.la \
$(top_builddir)/libview/libevview3.la \
$(top_builddir)/libmisc/libevmisc.la \
$(BROWSER_PLUGIN_LIBS)
EvBrowserPluginResources.c: EvBrowserPlugin.gresource.xml Makefile $(shell $(GLIB_COMPILE_RESOURCES) --generate-dependencies --sourcedir=$(srcdir) --sourcedir=$(top_srcdir)/data $(srcdir)/EvBrowserPlugin.gresource.xml)
$(AM_V_GEN) XMLLINT=$(XMLLINT) $(GLIB_COMPILE_RESOURCES) --target=$@ --sourcedir=$(srcdir) --sourcedir=$(top_srcdir)/data --generate-source $<
EXTRA_DIST = \
EvBrowserPlugin.gresource.xml \
evince-browser.css \
plugin.symbols
CLEANFILES = \
EvBrowserPluginResources.c
-include $(top_srcdir)/git.mk
.content-view.document-page {
border-style: solid;
border-width: 3px 3px 6px 4px;
border-image: url("resource:///org/gnome/evince/browser/ui/thumbnail-frame.png") 3 3 6 4;
background-color: @theme_bg_color;
}
EvView {
background-color: @theme_bg_color;
}
EvView:selected {
background-color: @theme_selected_bg_color;
}
EvView.document-page {
background-color: white;
padding: 0;
}
sources = files(
'EvBrowserPlugin.cpp',
'EvBrowserPluginMain.cpp',
'EvBrowserPluginToolbar.cpp',
)
resource_data = files(
'../data/thumbnail-frame.png',
'evince-browser.css',
)
resource = 'EvBrowserPlugin'
sources += gnome.compile_resources(
resource + 'Resources',
resource + '.gresource.xml',
source_dir: data_dir,
dependencies: resource_data,
export: true,
)
incs = [
top_inc,
include_directories('npapi'),
]
cflags = [
'-DGNOMELOCALEDIR="@0@"'.format(ev_localedir),
'-DEVINCE_COMPILATION',
'-DMOZ_X11',
'-DXP_UNIX',
]