Some cleanup work
* Remove NO_C2 option * Split configuration related functions into their own file * Drop support for libconfig < 1.4 * Fix dependencies in Makefile
This commit is contained in:
parent
265dc67717
commit
fcef5e706d
|
@ -2,8 +2,6 @@
|
||||||
.deps
|
.deps
|
||||||
aclocal.m4
|
aclocal.m4
|
||||||
autom4te.cache
|
autom4te.cache
|
||||||
config.h
|
|
||||||
config.h.in
|
|
||||||
config.log
|
config.log
|
||||||
config.status
|
config.status
|
||||||
configure
|
configure
|
||||||
|
|
29
Makefile
29
Makefile
|
@ -13,10 +13,10 @@ PACKAGES = x11 xcomposite xfixes xdamage xrender xext xrandr
|
||||||
LIBS = -lm -lrt
|
LIBS = -lm -lrt
|
||||||
INCS =
|
INCS =
|
||||||
|
|
||||||
OBJS = compton.o
|
OBJS = compton.o config.o
|
||||||
|
|
||||||
# === Configuration flags ===
|
# === Configuration flags ===
|
||||||
CFG = -std=c99
|
CFG = -std=c99 -D_GNU_SOURCE
|
||||||
|
|
||||||
# ==== Xinerama ====
|
# ==== Xinerama ====
|
||||||
# Enables support for --xinerama-shadow-crop
|
# Enables support for --xinerama-shadow-crop
|
||||||
|
@ -30,10 +30,14 @@ endif
|
||||||
ifeq "$(NO_LIBCONFIG)" ""
|
ifeq "$(NO_LIBCONFIG)" ""
|
||||||
CFG += -DCONFIG_LIBCONFIG
|
CFG += -DCONFIG_LIBCONFIG
|
||||||
PACKAGES += libconfig
|
PACKAGES += libconfig
|
||||||
|
OBJS += config_libconfig.o
|
||||||
|
|
||||||
# libconfig-1.3* does not define LIBCONFIG_VER* macros, so we use
|
# libconfig-1.3* does not define LIBCONFIG_VER* macros, so we use
|
||||||
# pkg-config to determine its version here
|
# pkg-config to determine its version here
|
||||||
CFG += $(shell pkg-config --atleast-version=1.4 libconfig || echo '-DCONFIG_LIBCONFIG_LEGACY')
|
LIBCONFIG_VER = $(shell pkg-config --atleast-version=1.4 libconfig; echo $$?)
|
||||||
|
ifeq ($LIBCONFIG_VER, 1)
|
||||||
|
$(error "Your libconfig is too old, at least 1.4 is required")
|
||||||
|
endif
|
||||||
endif
|
endif
|
||||||
|
|
||||||
# ==== PCRE regular expression ====
|
# ==== PCRE regular expression ====
|
||||||
|
@ -90,12 +94,7 @@ ifeq "$(NO_XSYNC)" ""
|
||||||
CFG += -DCONFIG_XSYNC
|
CFG += -DCONFIG_XSYNC
|
||||||
endif
|
endif
|
||||||
|
|
||||||
# ==== C2 ====
|
OBJS += c2.o
|
||||||
# Enable window condition support
|
|
||||||
ifeq "$(NO_C2)" ""
|
|
||||||
CFG += -DCONFIG_C2
|
|
||||||
OBJS += c2.o
|
|
||||||
endif
|
|
||||||
|
|
||||||
# ==== X resource checker ====
|
# ==== X resource checker ====
|
||||||
# Enable X resource leakage checking (Pixmap only, presently)
|
# Enable X resource leakage checking (Pixmap only, presently)
|
||||||
|
@ -141,7 +140,15 @@ MANPAGES_HTML = $(addsuffix .html,$(MANPAGES))
|
||||||
src/.clang_complete: Makefile
|
src/.clang_complete: Makefile
|
||||||
@(for i in $(filter-out -O% -DNDEBUG, $(CFG) $(CPPFLAGS) $(CFLAGS) $(INCS)); do echo "$$i"; done) > $@
|
@(for i in $(filter-out -O% -DNDEBUG, $(CFG) $(CPPFLAGS) $(CFLAGS) $(INCS)); do echo "$$i"; done) > $@
|
||||||
|
|
||||||
%.o: src/%.c src/%.h src/common.h
|
.deps:
|
||||||
|
mkdir -p .deps
|
||||||
|
|
||||||
|
%.o: src/%.c .deps
|
||||||
|
$(eval DEP=$(addprefix .deps/,$(@:.o=.d)))
|
||||||
|
@set -e; rm -f $(DEP); \
|
||||||
|
$(CC) -M $(CPPFLAGS) $< > $@.$$$$; \
|
||||||
|
sed 's,\($*\)\.o[ :]*,\1.o $@ : ,g' < $@.$$$$ > $(DEP); \
|
||||||
|
rm -f $@.$$$$
|
||||||
$(CC) $(CFG) $(CPPFLAGS) $(CFLAGS) $(INCS) -c src/$*.c
|
$(CC) $(CFG) $(CPPFLAGS) $(CFLAGS) $(INCS) -c src/$*.c
|
||||||
|
|
||||||
compton: $(OBJS)
|
compton: $(OBJS)
|
||||||
|
@ -183,8 +190,10 @@ endif
|
||||||
|
|
||||||
clean:
|
clean:
|
||||||
@rm -f $(OBJS) compton $(MANPAGES) $(MANPAGES_HTML) .clang_complete
|
@rm -f $(OBJS) compton $(MANPAGES) $(MANPAGES_HTML) .clang_complete
|
||||||
|
@rm -rf .deps
|
||||||
|
|
||||||
version:
|
version:
|
||||||
@echo "$(COMPTON_VERSION)"
|
@echo "$(COMPTON_VERSION)"
|
||||||
|
|
||||||
.PHONY: uninstall clean docs version
|
.PHONY: uninstall clean docs version
|
||||||
|
include $(addprefix .deps/,$(sources:.c=.d))
|
||||||
|
|
33
src/common.h
33
src/common.h
|
@ -8,8 +8,7 @@
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef COMPTON_COMMON_H
|
#pragma once
|
||||||
#define COMPTON_COMMON_H
|
|
||||||
|
|
||||||
// === Options ===
|
// === Options ===
|
||||||
|
|
||||||
|
@ -42,8 +41,6 @@
|
||||||
// #define CONFIG_REGEX_PCRE_JIT 1
|
// #define CONFIG_REGEX_PCRE_JIT 1
|
||||||
// Whether to enable parsing of configuration files using libconfig.
|
// Whether to enable parsing of configuration files using libconfig.
|
||||||
// #define CONFIG_LIBCONFIG 1
|
// #define CONFIG_LIBCONFIG 1
|
||||||
// Whether we are using a legacy version of libconfig (1.3.x).
|
|
||||||
// #define CONFIG_LIBCONFIG_LEGACY 1
|
|
||||||
// Whether to enable DRM VSync support
|
// Whether to enable DRM VSync support
|
||||||
// #define CONFIG_VSYNC_DRM 1
|
// #define CONFIG_VSYNC_DRM 1
|
||||||
// Whether to enable OpenGL support
|
// Whether to enable OpenGL support
|
||||||
|
@ -54,17 +51,11 @@
|
||||||
// #define CONFIG_VSYNC_OPENGL_FBO 1
|
// #define CONFIG_VSYNC_OPENGL_FBO 1
|
||||||
// Whether to enable DBus support with libdbus.
|
// Whether to enable DBus support with libdbus.
|
||||||
// #define CONFIG_DBUS 1
|
// #define CONFIG_DBUS 1
|
||||||
// Whether to enable condition support.
|
|
||||||
// #define CONFIG_C2 1
|
|
||||||
// Whether to enable X Sync support.
|
// Whether to enable X Sync support.
|
||||||
// #define CONFIG_XSYNC 1
|
// #define CONFIG_XSYNC 1
|
||||||
// Whether to enable GLX Sync support.
|
// Whether to enable GLX Sync support.
|
||||||
// #define CONFIG_GLX_XSYNC 1
|
// #define CONFIG_GLX_XSYNC 1
|
||||||
|
|
||||||
#if !defined(CONFIG_C2) && defined(DEBUG_C2)
|
|
||||||
#error Cannot enable c2 debugging without c2 support.
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if (!defined(CONFIG_XSYNC) || !defined(CONFIG_VSYNC_OPENGL)) && defined(CONFIG_GLX_SYNC)
|
#if (!defined(CONFIG_XSYNC) || !defined(CONFIG_VSYNC_OPENGL)) && defined(CONFIG_GLX_SYNC)
|
||||||
#error Cannot enable GL sync without X Sync / OpenGL support.
|
#error Cannot enable GL sync without X Sync / OpenGL support.
|
||||||
#endif
|
#endif
|
||||||
|
@ -80,8 +71,6 @@
|
||||||
// === Includes ===
|
// === Includes ===
|
||||||
|
|
||||||
// For some special functions
|
// For some special functions
|
||||||
#define _GNU_SOURCE
|
|
||||||
|
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
|
@ -116,12 +105,6 @@
|
||||||
#define PictOpDifference 0x39
|
#define PictOpDifference 0x39
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// libconfig
|
|
||||||
#ifdef CONFIG_LIBCONFIG
|
|
||||||
#include <libgen.h>
|
|
||||||
#include <libconfig.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// libdbus
|
// libdbus
|
||||||
#ifdef CONFIG_DBUS
|
#ifdef CONFIG_DBUS
|
||||||
#include <dbus/dbus.h>
|
#include <dbus/dbus.h>
|
||||||
|
@ -2483,7 +2466,6 @@ opts_set_no_fading_openclose(session_t *ps, bool newval);
|
||||||
//!@}
|
//!@}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef CONFIG_C2
|
|
||||||
/** @name c2
|
/** @name c2
|
||||||
*/
|
*/
|
||||||
///@{
|
///@{
|
||||||
|
@ -2503,7 +2485,6 @@ c2_matchd(session_t *ps, win *w, const c2_lptr_t *condlst,
|
||||||
|
|
||||||
#define c2_match(ps, w, condlst, cache) c2_matchd((ps), (w), (condlst), \
|
#define c2_match(ps, w, condlst, cache) c2_matchd((ps), (w), (condlst), \
|
||||||
(cache), NULL)
|
(cache), NULL)
|
||||||
#endif
|
|
||||||
|
|
||||||
///@}
|
///@}
|
||||||
|
|
||||||
|
@ -2564,4 +2545,14 @@ hexdump(const char *data, int len) {
|
||||||
fflush(stdout);
|
fflush(stdout);
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
/**
|
||||||
|
* Set a <code>bool</code> array of all wintypes to true.
|
||||||
|
*/
|
||||||
|
static inline void
|
||||||
|
wintype_arr_enable(bool arr[]) {
|
||||||
|
wintype_t i;
|
||||||
|
|
||||||
|
for (i = 0; i < NUM_WINTYPES; ++i) {
|
||||||
|
arr[i] = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
700
src/compton.c
700
src/compton.c
|
@ -9,6 +9,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "compton.h"
|
#include "compton.h"
|
||||||
|
#include "config.h"
|
||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
|
|
||||||
// === Global constants ===
|
// === Global constants ===
|
||||||
|
@ -684,24 +685,6 @@ win_rounded_corners(session_t *ps, win *w) {
|
||||||
cxfree(rects);
|
cxfree(rects);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Add a pattern to a condition linked list.
|
|
||||||
*/
|
|
||||||
static bool
|
|
||||||
condlst_add(session_t *ps, c2_lptr_t **pcondlst, const char *pattern) {
|
|
||||||
if (!pattern)
|
|
||||||
return false;
|
|
||||||
|
|
||||||
#ifdef CONFIG_C2
|
|
||||||
if (!c2_parse(ps, pcondlst, pattern))
|
|
||||||
exit(1);
|
|
||||||
#else
|
|
||||||
printf_errfq(1, "(): Condition support not compiled in.");
|
|
||||||
#endif
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Determine the event mask for a window.
|
* Determine the event mask for a window.
|
||||||
*/
|
*/
|
||||||
|
@ -2615,7 +2598,6 @@ win_update_opacity_rule(session_t *ps, win *w) {
|
||||||
if (IsViewable != w->a.map_state)
|
if (IsViewable != w->a.map_state)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
#ifdef CONFIG_C2
|
|
||||||
opacity_t opacity = OPAQUE;
|
opacity_t opacity = OPAQUE;
|
||||||
bool is_set = false;
|
bool is_set = false;
|
||||||
void *val = NULL;
|
void *val = NULL;
|
||||||
|
@ -2633,7 +2615,6 @@ win_update_opacity_rule(session_t *ps, win *w) {
|
||||||
wid_rm_opacity_prop(ps, w->id);
|
wid_rm_opacity_prop(ps, w->id);
|
||||||
else
|
else
|
||||||
wid_set_opacity_prop(ps, w->id, opacity);
|
wid_set_opacity_prop(ps, w->id, opacity);
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -4997,683 +4978,6 @@ write_pid(session_t *ps) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Parse a long number.
|
|
||||||
*/
|
|
||||||
static inline bool
|
|
||||||
parse_long(const char *s, long *dest) {
|
|
||||||
const char *endptr = NULL;
|
|
||||||
long val = strtol(s, (char **) &endptr, 0);
|
|
||||||
if (!endptr || endptr == s) {
|
|
||||||
printf_errf("(\"%s\"): Invalid number.", s);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
while (isspace(*endptr))
|
|
||||||
++endptr;
|
|
||||||
if (*endptr) {
|
|
||||||
printf_errf("(\"%s\"): Trailing characters.", s);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
*dest = val;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Parse a floating-point number in matrix.
|
|
||||||
*/
|
|
||||||
static inline const char *
|
|
||||||
parse_matrix_readnum(const char *src, double *dest) {
|
|
||||||
char *pc = NULL;
|
|
||||||
double val = strtod(src, &pc);
|
|
||||||
if (!pc || pc == src) {
|
|
||||||
printf_errf("(\"%s\"): No number found.", src);
|
|
||||||
return src;
|
|
||||||
}
|
|
||||||
|
|
||||||
while (*pc && (isspace(*pc) || ',' == *pc))
|
|
||||||
++pc;
|
|
||||||
|
|
||||||
*dest = val;
|
|
||||||
|
|
||||||
return pc;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Parse a matrix.
|
|
||||||
*/
|
|
||||||
static inline XFixed *
|
|
||||||
parse_matrix(session_t *ps, const char *src, const char **endptr) {
|
|
||||||
int wid = 0, hei = 0;
|
|
||||||
const char *pc = NULL;
|
|
||||||
XFixed *matrix = NULL;
|
|
||||||
|
|
||||||
// Get matrix width and height
|
|
||||||
{
|
|
||||||
double val = 0.0;
|
|
||||||
if (src == (pc = parse_matrix_readnum(src, &val)))
|
|
||||||
goto parse_matrix_err;
|
|
||||||
src = pc;
|
|
||||||
wid = val;
|
|
||||||
if (src == (pc = parse_matrix_readnum(src, &val)))
|
|
||||||
goto parse_matrix_err;
|
|
||||||
src = pc;
|
|
||||||
hei = val;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Validate matrix width and height
|
|
||||||
if (wid <= 0 || hei <= 0) {
|
|
||||||
printf_errf("(): Invalid matrix width/height.");
|
|
||||||
goto parse_matrix_err;
|
|
||||||
}
|
|
||||||
if (!(wid % 2 && hei % 2)) {
|
|
||||||
printf_errf("(): Width/height not odd.");
|
|
||||||
goto parse_matrix_err;
|
|
||||||
}
|
|
||||||
if (wid > 16 || hei > 16)
|
|
||||||
printf_errf("(): Matrix width/height too large, may slow down"
|
|
||||||
"rendering, and/or consume lots of memory");
|
|
||||||
|
|
||||||
// Allocate memory
|
|
||||||
matrix = calloc(wid * hei + 2, sizeof(XFixed));
|
|
||||||
if (!matrix) {
|
|
||||||
printf_errf("(): Failed to allocate memory for matrix.");
|
|
||||||
goto parse_matrix_err;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Read elements
|
|
||||||
{
|
|
||||||
int skip = hei / 2 * wid + wid / 2;
|
|
||||||
bool hasneg = false;
|
|
||||||
for (int i = 0; i < wid * hei; ++i) {
|
|
||||||
// Ignore the center element
|
|
||||||
if (i == skip) {
|
|
||||||
matrix[2 + i] = XDoubleToFixed(0);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
double val = 0;
|
|
||||||
if (src == (pc = parse_matrix_readnum(src, &val)))
|
|
||||||
goto parse_matrix_err;
|
|
||||||
src = pc;
|
|
||||||
if (val < 0) hasneg = true;
|
|
||||||
matrix[2 + i] = XDoubleToFixed(val);
|
|
||||||
}
|
|
||||||
if (BKEND_XRENDER == ps->o.backend && hasneg)
|
|
||||||
printf_errf("(): A convolution kernel with negative values "
|
|
||||||
"may not work properly under X Render backend.");
|
|
||||||
}
|
|
||||||
|
|
||||||
// Detect trailing characters
|
|
||||||
for ( ;*pc && ';' != *pc; ++pc)
|
|
||||||
if (!isspace(*pc) && ',' != *pc) {
|
|
||||||
printf_errf("(): Trailing characters in matrix string.");
|
|
||||||
goto parse_matrix_err;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Jump over spaces after ';'
|
|
||||||
if (';' == *pc) {
|
|
||||||
++pc;
|
|
||||||
while (*pc && isspace(*pc))
|
|
||||||
++pc;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Require an end of string if endptr is not provided, otherwise
|
|
||||||
// copy end pointer to endptr
|
|
||||||
if (endptr)
|
|
||||||
*endptr = pc;
|
|
||||||
else if (*pc) {
|
|
||||||
printf_errf("(): Only one matrix expected.");
|
|
||||||
goto parse_matrix_err;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Fill in width and height
|
|
||||||
matrix[0] = XDoubleToFixed(wid);
|
|
||||||
matrix[1] = XDoubleToFixed(hei);
|
|
||||||
|
|
||||||
return matrix;
|
|
||||||
|
|
||||||
parse_matrix_err:
|
|
||||||
free(matrix);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Parse a convolution kernel.
|
|
||||||
*/
|
|
||||||
static inline XFixed *
|
|
||||||
parse_conv_kern(session_t *ps, const char *src, const char **endptr) {
|
|
||||||
return parse_matrix(ps, src, endptr);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Parse a list of convolution kernels.
|
|
||||||
*/
|
|
||||||
static bool
|
|
||||||
parse_conv_kern_lst(session_t *ps, const char *src, XFixed **dest, int max) {
|
|
||||||
static const struct {
|
|
||||||
const char *name;
|
|
||||||
const char *kern_str;
|
|
||||||
} CONV_KERN_PREDEF[] = {
|
|
||||||
{ "3x3box", "3,3,1,1,1,1,1,1,1,1," },
|
|
||||||
{ "5x5box", "5,5,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1," },
|
|
||||||
{ "7x7box", "7,7,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1," },
|
|
||||||
{ "3x3gaussian", "3,3,0.243117,0.493069,0.243117,0.493069,0.493069,0.243117,0.493069,0.243117," },
|
|
||||||
{ "5x5gaussian", "5,5,0.003493,0.029143,0.059106,0.029143,0.003493,0.029143,0.243117,0.493069,0.243117,0.029143,0.059106,0.493069,0.493069,0.059106,0.029143,0.243117,0.493069,0.243117,0.029143,0.003493,0.029143,0.059106,0.029143,0.003493," },
|
|
||||||
{ "7x7gaussian", "7,7,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.001723,0.059106,0.493069,0.493069,0.059106,0.001723,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003," },
|
|
||||||
{ "9x9gaussian", "9,9,0.000000,0.000000,0.000001,0.000006,0.000012,0.000006,0.000001,0.000000,0.000000,0.000000,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003,0.000000,0.000001,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000001,0.000006,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.000006,0.000012,0.001723,0.059106,0.493069,0.493069,0.059106,0.001723,0.000012,0.000006,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.000006,0.000001,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000001,0.000000,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003,0.000000,0.000000,0.000000,0.000001,0.000006,0.000012,0.000006,0.000001,0.000000,0.000000," },
|
|
||||||
{ "11x11gaussian", "11,11,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000001,0.000006,0.000012,0.000006,0.000001,0.000000,0.000000,0.000000,0.000000,0.000000,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003,0.000000,0.000000,0.000000,0.000001,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000001,0.000000,0.000000,0.000006,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.000006,0.000000,0.000000,0.000012,0.001723,0.059106,0.493069,0.493069,0.059106,0.001723,0.000012,0.000000,0.000000,0.000006,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.000006,0.000000,0.000000,0.000001,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000001,0.000000,0.000000,0.000000,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003,0.000000,0.000000,0.000000,0.000000,0.000000,0.000001,0.000006,0.000012,0.000006,0.000001,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000," },
|
|
||||||
};
|
|
||||||
for (int i = 0;
|
|
||||||
i < sizeof(CONV_KERN_PREDEF) / sizeof(CONV_KERN_PREDEF[0]); ++i)
|
|
||||||
if (!strcmp(CONV_KERN_PREDEF[i].name, src))
|
|
||||||
return parse_conv_kern_lst(ps, CONV_KERN_PREDEF[i].kern_str, dest, max);
|
|
||||||
|
|
||||||
int i = 0;
|
|
||||||
const char *pc = src;
|
|
||||||
|
|
||||||
// Free old kernels
|
|
||||||
for (i = 0; i < max; ++i) {
|
|
||||||
free(dest[i]);
|
|
||||||
dest[i] = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Continue parsing until the end of source string
|
|
||||||
i = 0;
|
|
||||||
while (pc && *pc && i < max - 1) {
|
|
||||||
if (!(dest[i++] = parse_conv_kern(ps, pc, &pc)))
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (*pc) {
|
|
||||||
printf_errf("(): Too many blur kernels!");
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Parse a X geometry.
|
|
||||||
*/
|
|
||||||
static inline bool
|
|
||||||
parse_geometry(session_t *ps, const char *src, geometry_t *dest) {
|
|
||||||
geometry_t geom = { .wid = -1, .hei = -1, .x = -1, .y = -1 };
|
|
||||||
long val = 0L;
|
|
||||||
char *endptr = NULL;
|
|
||||||
|
|
||||||
#define T_STRIPSPACE() do { \
|
|
||||||
while (*src && isspace(*src)) ++src; \
|
|
||||||
if (!*src) goto parse_geometry_end; \
|
|
||||||
} while(0)
|
|
||||||
|
|
||||||
T_STRIPSPACE();
|
|
||||||
|
|
||||||
// Parse width
|
|
||||||
// Must be base 10, because "0x0..." may appear
|
|
||||||
if (!('+' == *src || '-' == *src)) {
|
|
||||||
val = strtol(src, &endptr, 10);
|
|
||||||
if (endptr && src != endptr) {
|
|
||||||
geom.wid = val;
|
|
||||||
assert(geom.wid >= 0);
|
|
||||||
src = endptr;
|
|
||||||
}
|
|
||||||
T_STRIPSPACE();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Parse height
|
|
||||||
if ('x' == *src) {
|
|
||||||
++src;
|
|
||||||
val = strtol(src, &endptr, 10);
|
|
||||||
if (endptr && src != endptr) {
|
|
||||||
geom.hei = val;
|
|
||||||
if (geom.hei < 0) {
|
|
||||||
printf_errf("(\"%s\"): Invalid height.", src);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
src = endptr;
|
|
||||||
}
|
|
||||||
T_STRIPSPACE();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Parse x
|
|
||||||
if ('+' == *src || '-' == *src) {
|
|
||||||
val = strtol(src, &endptr, 10);
|
|
||||||
if (endptr && src != endptr) {
|
|
||||||
geom.x = val;
|
|
||||||
if ('-' == *src && geom.x <= 0)
|
|
||||||
geom.x -= 2;
|
|
||||||
src = endptr;
|
|
||||||
}
|
|
||||||
T_STRIPSPACE();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Parse y
|
|
||||||
if ('+' == *src || '-' == *src) {
|
|
||||||
val = strtol(src, &endptr, 10);
|
|
||||||
if (endptr && src != endptr) {
|
|
||||||
geom.y = val;
|
|
||||||
if ('-' == *src && geom.y <= 0)
|
|
||||||
geom.y -= 2;
|
|
||||||
src = endptr;
|
|
||||||
}
|
|
||||||
T_STRIPSPACE();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (*src) {
|
|
||||||
printf_errf("(\"%s\"): Trailing characters.", src);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
parse_geometry_end:
|
|
||||||
*dest = geom;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Parse a list of opacity rules.
|
|
||||||
*/
|
|
||||||
static inline bool
|
|
||||||
parse_rule_opacity(session_t *ps, const char *src) {
|
|
||||||
#ifdef CONFIG_C2
|
|
||||||
// Find opacity value
|
|
||||||
char *endptr = NULL;
|
|
||||||
long val = strtol(src, &endptr, 0);
|
|
||||||
if (!endptr || endptr == src) {
|
|
||||||
printf_errf("(\"%s\"): No opacity specified?", src);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
if (val > 100 || val < 0) {
|
|
||||||
printf_errf("(\"%s\"): Opacity %ld invalid.", src, val);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Skip over spaces
|
|
||||||
while (*endptr && isspace(*endptr))
|
|
||||||
++endptr;
|
|
||||||
if (':' != *endptr) {
|
|
||||||
printf_errf("(\"%s\"): Opacity terminator not found.", src);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
++endptr;
|
|
||||||
|
|
||||||
// Parse pattern
|
|
||||||
// I hope 1-100 is acceptable for (void *)
|
|
||||||
return c2_parsed(ps, &ps->o.opacity_rules, endptr, (void *) val);
|
|
||||||
#else
|
|
||||||
printf_errf("(\"%s\"): Condition support not compiled in.", src);
|
|
||||||
return false;
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
#ifdef CONFIG_LIBCONFIG
|
|
||||||
/**
|
|
||||||
* Get a file stream of the configuration file to read.
|
|
||||||
*
|
|
||||||
* Follows the XDG specification to search for the configuration file.
|
|
||||||
*/
|
|
||||||
static FILE *
|
|
||||||
open_config_file(char *cpath, char **ppath) {
|
|
||||||
const static char *config_filename = "/compton.conf";
|
|
||||||
const static char *config_filename_legacy = "/.compton.conf";
|
|
||||||
const static char *config_home_suffix = "/.config";
|
|
||||||
const static char *config_system_dir = "/etc/xdg";
|
|
||||||
|
|
||||||
char *dir = NULL, *home = NULL;
|
|
||||||
char *path = cpath;
|
|
||||||
FILE *f = NULL;
|
|
||||||
|
|
||||||
if (path) {
|
|
||||||
f = fopen(path, "r");
|
|
||||||
if (f && ppath)
|
|
||||||
*ppath = path;
|
|
||||||
return f;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check user configuration file in $XDG_CONFIG_HOME firstly
|
|
||||||
if (!((dir = getenv("XDG_CONFIG_HOME")) && strlen(dir))) {
|
|
||||||
if (!((home = getenv("HOME")) && strlen(home)))
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
path = mstrjoin3(home, config_home_suffix, config_filename);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
path = mstrjoin(dir, config_filename);
|
|
||||||
|
|
||||||
f = fopen(path, "r");
|
|
||||||
|
|
||||||
if (f && ppath)
|
|
||||||
*ppath = path;
|
|
||||||
else
|
|
||||||
free(path);
|
|
||||||
if (f)
|
|
||||||
return f;
|
|
||||||
|
|
||||||
// Then check user configuration file in $HOME
|
|
||||||
if ((home = getenv("HOME")) && strlen(home)) {
|
|
||||||
path = mstrjoin(home, config_filename_legacy);
|
|
||||||
f = fopen(path, "r");
|
|
||||||
if (f && ppath)
|
|
||||||
*ppath = path;
|
|
||||||
else
|
|
||||||
free(path);
|
|
||||||
if (f)
|
|
||||||
return f;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check system configuration file in $XDG_CONFIG_DIRS at last
|
|
||||||
if ((dir = getenv("XDG_CONFIG_DIRS")) && strlen(dir)) {
|
|
||||||
char *part = strtok(dir, ":");
|
|
||||||
while (part) {
|
|
||||||
path = mstrjoin(part, config_filename);
|
|
||||||
f = fopen(path, "r");
|
|
||||||
if (f && ppath)
|
|
||||||
*ppath = path;
|
|
||||||
else
|
|
||||||
free(path);
|
|
||||||
if (f)
|
|
||||||
return f;
|
|
||||||
part = strtok(NULL, ":");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
path = mstrjoin(config_system_dir, config_filename);
|
|
||||||
f = fopen(path, "r");
|
|
||||||
if (f && ppath)
|
|
||||||
*ppath = path;
|
|
||||||
else
|
|
||||||
free(path);
|
|
||||||
if (f)
|
|
||||||
return f;
|
|
||||||
}
|
|
||||||
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Parse a condition list in configuration file.
|
|
||||||
*/
|
|
||||||
static inline void
|
|
||||||
parse_cfg_condlst(session_t *ps, const config_t *pcfg, c2_lptr_t **pcondlst,
|
|
||||||
const char *name) {
|
|
||||||
config_setting_t *setting = config_lookup(pcfg, name);
|
|
||||||
if (setting) {
|
|
||||||
// Parse an array of options
|
|
||||||
if (config_setting_is_array(setting)) {
|
|
||||||
int i = config_setting_length(setting);
|
|
||||||
while (i--)
|
|
||||||
condlst_add(ps, pcondlst, config_setting_get_string_elem(setting, i));
|
|
||||||
}
|
|
||||||
// Treat it as a single pattern if it's a string
|
|
||||||
else if (CONFIG_TYPE_STRING == config_setting_type(setting)) {
|
|
||||||
condlst_add(ps, pcondlst, config_setting_get_string(setting));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Parse an opacity rule list in configuration file.
|
|
||||||
*/
|
|
||||||
static inline void
|
|
||||||
parse_cfg_condlst_opct(session_t *ps, const config_t *pcfg, const char *name) {
|
|
||||||
config_setting_t *setting = config_lookup(pcfg, name);
|
|
||||||
if (setting) {
|
|
||||||
// Parse an array of options
|
|
||||||
if (config_setting_is_array(setting)) {
|
|
||||||
int i = config_setting_length(setting);
|
|
||||||
while (i--)
|
|
||||||
if (!parse_rule_opacity(ps, config_setting_get_string_elem(setting,
|
|
||||||
i)))
|
|
||||||
exit(1);
|
|
||||||
}
|
|
||||||
// Treat it as a single pattern if it's a string
|
|
||||||
else if (CONFIG_TYPE_STRING == config_setting_type(setting)) {
|
|
||||||
parse_rule_opacity(ps, config_setting_get_string(setting));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Parse a configuration file from default location.
|
|
||||||
*/
|
|
||||||
static void
|
|
||||||
parse_config(session_t *ps, struct options_tmp *pcfgtmp) {
|
|
||||||
char *path = NULL;
|
|
||||||
FILE *f;
|
|
||||||
config_t cfg;
|
|
||||||
int ival = 0;
|
|
||||||
double dval = 0.0;
|
|
||||||
// libconfig manages string memory itself, so no need to manually free
|
|
||||||
// anything
|
|
||||||
const char *sval = NULL;
|
|
||||||
|
|
||||||
f = open_config_file(ps->o.config_file, &path);
|
|
||||||
if (!f) {
|
|
||||||
if (ps->o.config_file) {
|
|
||||||
printf_errfq(1, "(): Failed to read configuration file \"%s\".",
|
|
||||||
ps->o.config_file);
|
|
||||||
free(ps->o.config_file);
|
|
||||||
ps->o.config_file = NULL;
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
config_init(&cfg);
|
|
||||||
#ifndef CONFIG_LIBCONFIG_LEGACY
|
|
||||||
{
|
|
||||||
// dirname() could modify the original string, thus we must pass a
|
|
||||||
// copy
|
|
||||||
char *path2 = mstrcpy(path);
|
|
||||||
char *parent = dirname(path2);
|
|
||||||
|
|
||||||
if (parent)
|
|
||||||
config_set_include_dir(&cfg, parent);
|
|
||||||
|
|
||||||
free(path2);
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
{
|
|
||||||
int read_result = config_read(&cfg, f);
|
|
||||||
fclose(f);
|
|
||||||
f = NULL;
|
|
||||||
if (CONFIG_FALSE == read_result) {
|
|
||||||
printf("Error when reading configuration file \"%s\", line %d: %s\n",
|
|
||||||
path, config_error_line(&cfg), config_error_text(&cfg));
|
|
||||||
config_destroy(&cfg);
|
|
||||||
free(path);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
config_set_auto_convert(&cfg, 1);
|
|
||||||
|
|
||||||
if (path != ps->o.config_file) {
|
|
||||||
free(ps->o.config_file);
|
|
||||||
ps->o.config_file = path;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Get options from the configuration file. We don't do range checking
|
|
||||||
// right now. It will be done later
|
|
||||||
|
|
||||||
// -D (fade_delta)
|
|
||||||
if (lcfg_lookup_int(&cfg, "fade-delta", &ival))
|
|
||||||
ps->o.fade_delta = ival;
|
|
||||||
// -I (fade_in_step)
|
|
||||||
if (config_lookup_float(&cfg, "fade-in-step", &dval))
|
|
||||||
ps->o.fade_in_step = normalize_d(dval) * OPAQUE;
|
|
||||||
// -O (fade_out_step)
|
|
||||||
if (config_lookup_float(&cfg, "fade-out-step", &dval))
|
|
||||||
ps->o.fade_out_step = normalize_d(dval) * OPAQUE;
|
|
||||||
// -r (shadow_radius)
|
|
||||||
lcfg_lookup_int(&cfg, "shadow-radius", &ps->o.shadow_radius);
|
|
||||||
// -o (shadow_opacity)
|
|
||||||
config_lookup_float(&cfg, "shadow-opacity", &ps->o.shadow_opacity);
|
|
||||||
// -l (shadow_offset_x)
|
|
||||||
lcfg_lookup_int(&cfg, "shadow-offset-x", &ps->o.shadow_offset_x);
|
|
||||||
// -t (shadow_offset_y)
|
|
||||||
lcfg_lookup_int(&cfg, "shadow-offset-y", &ps->o.shadow_offset_y);
|
|
||||||
// -i (inactive_opacity)
|
|
||||||
if (config_lookup_float(&cfg, "inactive-opacity", &dval))
|
|
||||||
ps->o.inactive_opacity = normalize_d(dval) * OPAQUE;
|
|
||||||
// --active_opacity
|
|
||||||
if (config_lookup_float(&cfg, "active-opacity", &dval))
|
|
||||||
ps->o.active_opacity = normalize_d(dval) * OPAQUE;
|
|
||||||
// -e (frame_opacity)
|
|
||||||
config_lookup_float(&cfg, "frame-opacity", &ps->o.frame_opacity);
|
|
||||||
// -z (clear_shadow)
|
|
||||||
lcfg_lookup_bool(&cfg, "clear-shadow", &ps->o.clear_shadow);
|
|
||||||
// -c (shadow_enable)
|
|
||||||
if (config_lookup_bool(&cfg, "shadow", &ival) && ival)
|
|
||||||
wintype_arr_enable(ps->o.wintype_shadow);
|
|
||||||
// -C (no_dock_shadow)
|
|
||||||
lcfg_lookup_bool(&cfg, "no-dock-shadow", &pcfgtmp->no_dock_shadow);
|
|
||||||
// -G (no_dnd_shadow)
|
|
||||||
lcfg_lookup_bool(&cfg, "no-dnd-shadow", &pcfgtmp->no_dnd_shadow);
|
|
||||||
// -m (menu_opacity)
|
|
||||||
config_lookup_float(&cfg, "menu-opacity", &pcfgtmp->menu_opacity);
|
|
||||||
// -f (fading_enable)
|
|
||||||
if (config_lookup_bool(&cfg, "fading", &ival) && ival)
|
|
||||||
wintype_arr_enable(ps->o.wintype_fade);
|
|
||||||
// --no-fading-open-close
|
|
||||||
lcfg_lookup_bool(&cfg, "no-fading-openclose", &ps->o.no_fading_openclose);
|
|
||||||
// --no-fading-destroyed-argb
|
|
||||||
lcfg_lookup_bool(&cfg, "no-fading-destroyed-argb",
|
|
||||||
&ps->o.no_fading_destroyed_argb);
|
|
||||||
// --shadow-red
|
|
||||||
config_lookup_float(&cfg, "shadow-red", &ps->o.shadow_red);
|
|
||||||
// --shadow-green
|
|
||||||
config_lookup_float(&cfg, "shadow-green", &ps->o.shadow_green);
|
|
||||||
// --shadow-blue
|
|
||||||
config_lookup_float(&cfg, "shadow-blue", &ps->o.shadow_blue);
|
|
||||||
// --shadow-exclude-reg
|
|
||||||
if (config_lookup_string(&cfg, "shadow-exclude-reg", &sval)
|
|
||||||
&& !parse_geometry(ps, sval, &ps->o.shadow_exclude_reg_geom))
|
|
||||||
exit(1);
|
|
||||||
// --inactive-opacity-override
|
|
||||||
lcfg_lookup_bool(&cfg, "inactive-opacity-override",
|
|
||||||
&ps->o.inactive_opacity_override);
|
|
||||||
// --inactive-dim
|
|
||||||
config_lookup_float(&cfg, "inactive-dim", &ps->o.inactive_dim);
|
|
||||||
// --mark-wmwin-focused
|
|
||||||
lcfg_lookup_bool(&cfg, "mark-wmwin-focused", &ps->o.mark_wmwin_focused);
|
|
||||||
// --mark-ovredir-focused
|
|
||||||
lcfg_lookup_bool(&cfg, "mark-ovredir-focused",
|
|
||||||
&ps->o.mark_ovredir_focused);
|
|
||||||
// --shadow-ignore-shaped
|
|
||||||
lcfg_lookup_bool(&cfg, "shadow-ignore-shaped",
|
|
||||||
&ps->o.shadow_ignore_shaped);
|
|
||||||
// --detect-rounded-corners
|
|
||||||
lcfg_lookup_bool(&cfg, "detect-rounded-corners",
|
|
||||||
&ps->o.detect_rounded_corners);
|
|
||||||
// --xinerama-shadow-crop
|
|
||||||
lcfg_lookup_bool(&cfg, "xinerama-shadow-crop",
|
|
||||||
&ps->o.xinerama_shadow_crop);
|
|
||||||
// --detect-client-opacity
|
|
||||||
lcfg_lookup_bool(&cfg, "detect-client-opacity",
|
|
||||||
&ps->o.detect_client_opacity);
|
|
||||||
// --refresh-rate
|
|
||||||
lcfg_lookup_int(&cfg, "refresh-rate", &ps->o.refresh_rate);
|
|
||||||
// --vsync
|
|
||||||
if (config_lookup_string(&cfg, "vsync", &sval) && !parse_vsync(ps, sval))
|
|
||||||
exit(1);
|
|
||||||
// --backend
|
|
||||||
if (config_lookup_string(&cfg, "backend", &sval) && !parse_backend(ps, sval))
|
|
||||||
exit(1);
|
|
||||||
// --alpha-step
|
|
||||||
config_lookup_float(&cfg, "alpha-step", &ps->o.alpha_step);
|
|
||||||
// --dbe
|
|
||||||
lcfg_lookup_bool(&cfg, "dbe", &ps->o.dbe);
|
|
||||||
// --paint-on-overlay
|
|
||||||
lcfg_lookup_bool(&cfg, "paint-on-overlay", &ps->o.paint_on_overlay);
|
|
||||||
// --sw-opti
|
|
||||||
lcfg_lookup_bool(&cfg, "sw-opti", &ps->o.sw_opti);
|
|
||||||
// --use-ewmh-active-win
|
|
||||||
lcfg_lookup_bool(&cfg, "use-ewmh-active-win",
|
|
||||||
&ps->o.use_ewmh_active_win);
|
|
||||||
// --unredir-if-possible
|
|
||||||
lcfg_lookup_bool(&cfg, "unredir-if-possible",
|
|
||||||
&ps->o.unredir_if_possible);
|
|
||||||
// --unredir-if-possible-delay
|
|
||||||
if (lcfg_lookup_int(&cfg, "unredir-if-possible-delay", &ival))
|
|
||||||
ps->o.unredir_if_possible_delay = ival;
|
|
||||||
// --inactive-dim-fixed
|
|
||||||
lcfg_lookup_bool(&cfg, "inactive-dim-fixed", &ps->o.inactive_dim_fixed);
|
|
||||||
// --detect-transient
|
|
||||||
lcfg_lookup_bool(&cfg, "detect-transient", &ps->o.detect_transient);
|
|
||||||
// --detect-client-leader
|
|
||||||
lcfg_lookup_bool(&cfg, "detect-client-leader",
|
|
||||||
&ps->o.detect_client_leader);
|
|
||||||
// --shadow-exclude
|
|
||||||
parse_cfg_condlst(ps, &cfg, &ps->o.shadow_blacklist, "shadow-exclude");
|
|
||||||
// --fade-exclude
|
|
||||||
parse_cfg_condlst(ps, &cfg, &ps->o.fade_blacklist, "fade-exclude");
|
|
||||||
// --focus-exclude
|
|
||||||
parse_cfg_condlst(ps, &cfg, &ps->o.focus_blacklist, "focus-exclude");
|
|
||||||
// --invert-color-include
|
|
||||||
parse_cfg_condlst(ps, &cfg, &ps->o.invert_color_list, "invert-color-include");
|
|
||||||
// --blur-background-exclude
|
|
||||||
parse_cfg_condlst(ps, &cfg, &ps->o.blur_background_blacklist, "blur-background-exclude");
|
|
||||||
// --opacity-rule
|
|
||||||
parse_cfg_condlst_opct(ps, &cfg, "opacity-rule");
|
|
||||||
// --unredir-if-possible-exclude
|
|
||||||
parse_cfg_condlst(ps, &cfg, &ps->o.unredir_if_possible_blacklist, "unredir-if-possible-exclude");
|
|
||||||
// --blur-background
|
|
||||||
lcfg_lookup_bool(&cfg, "blur-background", &ps->o.blur_background);
|
|
||||||
// --blur-background-frame
|
|
||||||
lcfg_lookup_bool(&cfg, "blur-background-frame",
|
|
||||||
&ps->o.blur_background_frame);
|
|
||||||
// --blur-background-fixed
|
|
||||||
lcfg_lookup_bool(&cfg, "blur-background-fixed",
|
|
||||||
&ps->o.blur_background_fixed);
|
|
||||||
// --blur-kern
|
|
||||||
if (config_lookup_string(&cfg, "blur-kern", &sval)
|
|
||||||
&& !parse_conv_kern_lst(ps, sval, ps->o.blur_kerns, MAX_BLUR_PASS))
|
|
||||||
exit(1);
|
|
||||||
// --resize-damage
|
|
||||||
lcfg_lookup_int(&cfg, "resize-damage", &ps->o.resize_damage);
|
|
||||||
// --glx-no-stencil
|
|
||||||
lcfg_lookup_bool(&cfg, "glx-no-stencil", &ps->o.glx_no_stencil);
|
|
||||||
// --glx-copy-from-front
|
|
||||||
lcfg_lookup_bool(&cfg, "glx-copy-from-front", &ps->o.glx_copy_from_front);
|
|
||||||
// --glx-use-copysubbuffermesa
|
|
||||||
lcfg_lookup_bool(&cfg, "glx-use-copysubbuffermesa", &ps->o.glx_use_copysubbuffermesa);
|
|
||||||
// --glx-no-rebind-pixmap
|
|
||||||
lcfg_lookup_bool(&cfg, "glx-no-rebind-pixmap", &ps->o.glx_no_rebind_pixmap);
|
|
||||||
// --glx-swap-method
|
|
||||||
if (config_lookup_string(&cfg, "glx-swap-method", &sval)
|
|
||||||
&& !parse_glx_swap_method(ps, sval))
|
|
||||||
exit(1);
|
|
||||||
// --glx-use-gpushader4
|
|
||||||
lcfg_lookup_bool(&cfg, "glx-use-gpushader4", &ps->o.glx_use_gpushader4);
|
|
||||||
// --xrender-sync
|
|
||||||
lcfg_lookup_bool(&cfg, "xrender-sync", &ps->o.xrender_sync);
|
|
||||||
// --xrender-sync-fence
|
|
||||||
lcfg_lookup_bool(&cfg, "xrender-sync-fence", &ps->o.xrender_sync_fence);
|
|
||||||
// Wintype settings
|
|
||||||
{
|
|
||||||
wintype_t i;
|
|
||||||
|
|
||||||
for (i = 0; i < NUM_WINTYPES; ++i) {
|
|
||||||
char *str = mstrjoin("wintypes.", WINTYPES[i]);
|
|
||||||
config_setting_t *setting = config_lookup(&cfg, str);
|
|
||||||
free(str);
|
|
||||||
if (setting) {
|
|
||||||
if (config_setting_lookup_bool(setting, "shadow", &ival))
|
|
||||||
ps->o.wintype_shadow[i] = (bool) ival;
|
|
||||||
if (config_setting_lookup_bool(setting, "fade", &ival))
|
|
||||||
ps->o.wintype_fade[i] = (bool) ival;
|
|
||||||
if (config_setting_lookup_bool(setting, "focus", &ival))
|
|
||||||
ps->o.wintype_focus[i] = (bool) ival;
|
|
||||||
|
|
||||||
double fval;
|
|
||||||
if (config_setting_lookup_float(setting, "opacity", &fval))
|
|
||||||
ps->o.wintype_opacity[i] = normalize_d(fval);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
config_destroy(&cfg);
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Process arguments and configuration files.
|
* Process arguments and configuration files.
|
||||||
*/
|
*/
|
||||||
|
@ -7513,7 +6817,6 @@ session_destroy(session_t *ps) {
|
||||||
ps->alpha_picts = NULL;
|
ps->alpha_picts = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef CONFIG_C2
|
|
||||||
// Free blacklists
|
// Free blacklists
|
||||||
free_wincondlst(&ps->o.shadow_blacklist);
|
free_wincondlst(&ps->o.shadow_blacklist);
|
||||||
free_wincondlst(&ps->o.fade_blacklist);
|
free_wincondlst(&ps->o.fade_blacklist);
|
||||||
|
@ -7523,7 +6826,6 @@ session_destroy(session_t *ps) {
|
||||||
free_wincondlst(&ps->o.opacity_rules);
|
free_wincondlst(&ps->o.opacity_rules);
|
||||||
free_wincondlst(&ps->o.paint_blacklist);
|
free_wincondlst(&ps->o.paint_blacklist);
|
||||||
free_wincondlst(&ps->o.unredir_if_possible_blacklist);
|
free_wincondlst(&ps->o.unredir_if_possible_blacklist);
|
||||||
#endif
|
|
||||||
|
|
||||||
// Free tracked atom list
|
// Free tracked atom list
|
||||||
{
|
{
|
||||||
|
|
|
@ -69,18 +69,6 @@ sub_unslong(unsigned long a, unsigned long b) {
|
||||||
return (a > b) ? a - b : 0;
|
return (a > b) ? a - b : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Set a <code>bool</code> array of all wintypes to true.
|
|
||||||
*/
|
|
||||||
static inline void
|
|
||||||
wintype_arr_enable(bool arr[]) {
|
|
||||||
wintype_t i;
|
|
||||||
|
|
||||||
for (i = 0; i < NUM_WINTYPES; ++i) {
|
|
||||||
arr[i] = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set a <code>switch_t</code> array of all unset wintypes to true.
|
* Set a <code>switch_t</code> array of all unset wintypes to true.
|
||||||
*/
|
*/
|
||||||
|
@ -186,10 +174,8 @@ free_damage(session_t *ps, Damage *p) {
|
||||||
*/
|
*/
|
||||||
static inline void
|
static inline void
|
||||||
free_wincondlst(c2_lptr_t **pcondlst) {
|
free_wincondlst(c2_lptr_t **pcondlst) {
|
||||||
#ifdef CONFIG_C2
|
|
||||||
while ((*pcondlst = c2_free_lptr(*pcondlst)))
|
while ((*pcondlst = c2_free_lptr(*pcondlst)))
|
||||||
continue;
|
continue;
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -585,16 +571,9 @@ win_validate_pixmap(session_t *ps, win *w) {
|
||||||
*/
|
*/
|
||||||
static inline bool
|
static inline bool
|
||||||
win_match(session_t *ps, win *w, c2_lptr_t *condlst, const c2_lptr_t **cache) {
|
win_match(session_t *ps, win *w, c2_lptr_t *condlst, const c2_lptr_t **cache) {
|
||||||
#ifdef CONFIG_C2
|
|
||||||
return c2_match(ps, w, condlst, cache);
|
return c2_match(ps, w, condlst, cache);
|
||||||
#else
|
|
||||||
return false;
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool
|
|
||||||
condlst_add(session_t *ps, c2_lptr_t **pcondlst, const char *pattern);
|
|
||||||
|
|
||||||
static long
|
static long
|
||||||
determine_evmask(session_t *ps, Window wid, win_evmode_t mode);
|
determine_evmask(session_t *ps, Window wid, win_evmode_t mode);
|
||||||
|
|
||||||
|
@ -1174,54 +1153,6 @@ ev_handle(session_t *ps, XEvent *ev);
|
||||||
static bool
|
static bool
|
||||||
fork_after(session_t *ps);
|
fork_after(session_t *ps);
|
||||||
|
|
||||||
#ifdef CONFIG_LIBCONFIG
|
|
||||||
/**
|
|
||||||
* Wrapper of libconfig's <code>config_lookup_int</code>.
|
|
||||||
*
|
|
||||||
* To convert <code>int</code> value <code>config_lookup_bool</code>
|
|
||||||
* returns to <code>bool</code>.
|
|
||||||
*/
|
|
||||||
static inline void
|
|
||||||
lcfg_lookup_bool(const config_t *config, const char *path,
|
|
||||||
bool *value) {
|
|
||||||
int ival;
|
|
||||||
|
|
||||||
if (config_lookup_bool(config, path, &ival))
|
|
||||||
*value = ival;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Wrapper of libconfig's <code>config_lookup_int</code>.
|
|
||||||
*
|
|
||||||
* To deal with the different value types <code>config_lookup_int</code>
|
|
||||||
* returns in libconfig-1.3 and libconfig-1.4.
|
|
||||||
*/
|
|
||||||
static inline int
|
|
||||||
lcfg_lookup_int(const config_t *config, const char *path, int *value) {
|
|
||||||
#ifndef CONFIG_LIBCONFIG_LEGACY
|
|
||||||
return config_lookup_int(config, path, value);
|
|
||||||
#else
|
|
||||||
long lval;
|
|
||||||
int ret;
|
|
||||||
|
|
||||||
if ((ret = config_lookup_int(config, path, &lval)))
|
|
||||||
*value = lval;
|
|
||||||
|
|
||||||
return ret;
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
static FILE *
|
|
||||||
open_config_file(char *cpath, char **path);
|
|
||||||
|
|
||||||
static void
|
|
||||||
parse_cfg_condlst(session_t *ps, const config_t *pcfg, c2_lptr_t **pcondlst,
|
|
||||||
const char *name);
|
|
||||||
|
|
||||||
static void
|
|
||||||
parse_config(session_t *ps, struct options_tmp *pcfgtmp);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
get_cfg(session_t *ps, int argc, char *const *argv, bool first_pass);
|
get_cfg(session_t *ps, int argc, char *const *argv, bool first_pass);
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,320 @@
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <stdbool.h>
|
||||||
|
|
||||||
|
#include "common.h"
|
||||||
|
#include "config.h"
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse a long number.
|
||||||
|
*/
|
||||||
|
bool
|
||||||
|
parse_long(const char *s, long *dest) {
|
||||||
|
const char *endptr = NULL;
|
||||||
|
long val = strtol(s, (char **) &endptr, 0);
|
||||||
|
if (!endptr || endptr == s) {
|
||||||
|
printf_errf("(\"%s\"): Invalid number.", s);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
while (isspace(*endptr))
|
||||||
|
++endptr;
|
||||||
|
if (*endptr) {
|
||||||
|
printf_errf("(\"%s\"): Trailing characters.", s);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
*dest = val;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse a floating-point number in matrix.
|
||||||
|
*/
|
||||||
|
const char *
|
||||||
|
parse_matrix_readnum(const char *src, double *dest) {
|
||||||
|
char *pc = NULL;
|
||||||
|
double val = strtod(src, &pc);
|
||||||
|
if (!pc || pc == src) {
|
||||||
|
printf_errf("(\"%s\"): No number found.", src);
|
||||||
|
return src;
|
||||||
|
}
|
||||||
|
|
||||||
|
while (*pc && (isspace(*pc) || ',' == *pc))
|
||||||
|
++pc;
|
||||||
|
|
||||||
|
*dest = val;
|
||||||
|
|
||||||
|
return pc;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse a matrix.
|
||||||
|
*/
|
||||||
|
XFixed *
|
||||||
|
parse_matrix(session_t *ps, const char *src, const char **endptr) {
|
||||||
|
int wid = 0, hei = 0;
|
||||||
|
const char *pc = NULL;
|
||||||
|
XFixed *matrix = NULL;
|
||||||
|
|
||||||
|
// Get matrix width and height
|
||||||
|
{
|
||||||
|
double val = 0.0;
|
||||||
|
if (src == (pc = parse_matrix_readnum(src, &val)))
|
||||||
|
goto parse_matrix_err;
|
||||||
|
src = pc;
|
||||||
|
wid = val;
|
||||||
|
if (src == (pc = parse_matrix_readnum(src, &val)))
|
||||||
|
goto parse_matrix_err;
|
||||||
|
src = pc;
|
||||||
|
hei = val;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Validate matrix width and height
|
||||||
|
if (wid <= 0 || hei <= 0) {
|
||||||
|
printf_errf("(): Invalid matrix width/height.");
|
||||||
|
goto parse_matrix_err;
|
||||||
|
}
|
||||||
|
if (!(wid % 2 && hei % 2)) {
|
||||||
|
printf_errf("(): Width/height not odd.");
|
||||||
|
goto parse_matrix_err;
|
||||||
|
}
|
||||||
|
if (wid > 16 || hei > 16)
|
||||||
|
printf_errf("(): Matrix width/height too large, may slow down"
|
||||||
|
"rendering, and/or consume lots of memory");
|
||||||
|
|
||||||
|
// Allocate memory
|
||||||
|
matrix = calloc(wid * hei + 2, sizeof(XFixed));
|
||||||
|
if (!matrix) {
|
||||||
|
printf_errf("(): Failed to allocate memory for matrix.");
|
||||||
|
goto parse_matrix_err;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Read elements
|
||||||
|
{
|
||||||
|
int skip = hei / 2 * wid + wid / 2;
|
||||||
|
bool hasneg = false;
|
||||||
|
for (int i = 0; i < wid * hei; ++i) {
|
||||||
|
// Ignore the center element
|
||||||
|
if (i == skip) {
|
||||||
|
matrix[2 + i] = XDoubleToFixed(0);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
double val = 0;
|
||||||
|
if (src == (pc = parse_matrix_readnum(src, &val)))
|
||||||
|
goto parse_matrix_err;
|
||||||
|
src = pc;
|
||||||
|
if (val < 0) hasneg = true;
|
||||||
|
matrix[2 + i] = XDoubleToFixed(val);
|
||||||
|
}
|
||||||
|
if (BKEND_XRENDER == ps->o.backend && hasneg)
|
||||||
|
printf_errf("(): A convolution kernel with negative values "
|
||||||
|
"may not work properly under X Render backend.");
|
||||||
|
}
|
||||||
|
|
||||||
|
// Detect trailing characters
|
||||||
|
for ( ;*pc && ';' != *pc; ++pc)
|
||||||
|
if (!isspace(*pc) && ',' != *pc) {
|
||||||
|
printf_errf("(): Trailing characters in matrix string.");
|
||||||
|
goto parse_matrix_err;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Jump over spaces after ';'
|
||||||
|
if (';' == *pc) {
|
||||||
|
++pc;
|
||||||
|
while (*pc && isspace(*pc))
|
||||||
|
++pc;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Require an end of string if endptr is not provided, otherwise
|
||||||
|
// copy end pointer to endptr
|
||||||
|
if (endptr)
|
||||||
|
*endptr = pc;
|
||||||
|
else if (*pc) {
|
||||||
|
printf_errf("(): Only one matrix expected.");
|
||||||
|
goto parse_matrix_err;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fill in width and height
|
||||||
|
matrix[0] = XDoubleToFixed(wid);
|
||||||
|
matrix[1] = XDoubleToFixed(hei);
|
||||||
|
|
||||||
|
return matrix;
|
||||||
|
|
||||||
|
parse_matrix_err:
|
||||||
|
free(matrix);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse a convolution kernel.
|
||||||
|
*/
|
||||||
|
XFixed *
|
||||||
|
parse_conv_kern(session_t *ps, const char *src, const char **endptr) {
|
||||||
|
return parse_matrix(ps, src, endptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse a list of convolution kernels.
|
||||||
|
*/
|
||||||
|
bool
|
||||||
|
parse_conv_kern_lst(session_t *ps, const char *src, XFixed **dest, int max) {
|
||||||
|
static const struct {
|
||||||
|
const char *name;
|
||||||
|
const char *kern_str;
|
||||||
|
} CONV_KERN_PREDEF[] = {
|
||||||
|
{ "3x3box", "3,3,1,1,1,1,1,1,1,1," },
|
||||||
|
{ "5x5box", "5,5,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1," },
|
||||||
|
{ "7x7box", "7,7,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1," },
|
||||||
|
{ "3x3gaussian", "3,3,0.243117,0.493069,0.243117,0.493069,0.493069,0.243117,0.493069,0.243117," },
|
||||||
|
{ "5x5gaussian", "5,5,0.003493,0.029143,0.059106,0.029143,0.003493,0.029143,0.243117,0.493069,0.243117,0.029143,0.059106,0.493069,0.493069,0.059106,0.029143,0.243117,0.493069,0.243117,0.029143,0.003493,0.029143,0.059106,0.029143,0.003493," },
|
||||||
|
{ "7x7gaussian", "7,7,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.001723,0.059106,0.493069,0.493069,0.059106,0.001723,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003," },
|
||||||
|
{ "9x9gaussian", "9,9,0.000000,0.000000,0.000001,0.000006,0.000012,0.000006,0.000001,0.000000,0.000000,0.000000,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003,0.000000,0.000001,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000001,0.000006,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.000006,0.000012,0.001723,0.059106,0.493069,0.493069,0.059106,0.001723,0.000012,0.000006,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.000006,0.000001,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000001,0.000000,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003,0.000000,0.000000,0.000000,0.000001,0.000006,0.000012,0.000006,0.000001,0.000000,0.000000," },
|
||||||
|
{ "11x11gaussian", "11,11,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000001,0.000006,0.000012,0.000006,0.000001,0.000000,0.000000,0.000000,0.000000,0.000000,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003,0.000000,0.000000,0.000000,0.000001,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000001,0.000000,0.000000,0.000006,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.000006,0.000000,0.000000,0.000012,0.001723,0.059106,0.493069,0.493069,0.059106,0.001723,0.000012,0.000000,0.000000,0.000006,0.000849,0.029143,0.243117,0.493069,0.243117,0.029143,0.000849,0.000006,0.000000,0.000000,0.000001,0.000102,0.003493,0.029143,0.059106,0.029143,0.003493,0.000102,0.000001,0.000000,0.000000,0.000000,0.000003,0.000102,0.000849,0.001723,0.000849,0.000102,0.000003,0.000000,0.000000,0.000000,0.000000,0.000000,0.000001,0.000006,0.000012,0.000006,0.000001,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000,0.000000," },
|
||||||
|
};
|
||||||
|
for (int i = 0;
|
||||||
|
i < sizeof(CONV_KERN_PREDEF) / sizeof(CONV_KERN_PREDEF[0]); ++i)
|
||||||
|
if (!strcmp(CONV_KERN_PREDEF[i].name, src))
|
||||||
|
return parse_conv_kern_lst(ps, CONV_KERN_PREDEF[i].kern_str, dest, max);
|
||||||
|
|
||||||
|
int i = 0;
|
||||||
|
const char *pc = src;
|
||||||
|
|
||||||
|
// Free old kernels
|
||||||
|
for (i = 0; i < max; ++i) {
|
||||||
|
free(dest[i]);
|
||||||
|
dest[i] = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Continue parsing until the end of source string
|
||||||
|
i = 0;
|
||||||
|
while (pc && *pc && i < max - 1) {
|
||||||
|
if (!(dest[i++] = parse_conv_kern(ps, pc, &pc)))
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (*pc) {
|
||||||
|
printf_errf("(): Too many blur kernels!");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse a X geometry.
|
||||||
|
*/
|
||||||
|
bool
|
||||||
|
parse_geometry(session_t *ps, const char *src, geometry_t *dest) {
|
||||||
|
geometry_t geom = { .wid = -1, .hei = -1, .x = -1, .y = -1 };
|
||||||
|
long val = 0L;
|
||||||
|
char *endptr = NULL;
|
||||||
|
|
||||||
|
#define T_STRIPSPACE() do { \
|
||||||
|
while (*src && isspace(*src)) ++src; \
|
||||||
|
if (!*src) goto parse_geometry_end; \
|
||||||
|
} while(0)
|
||||||
|
|
||||||
|
T_STRIPSPACE();
|
||||||
|
|
||||||
|
// Parse width
|
||||||
|
// Must be base 10, because "0x0..." may appear
|
||||||
|
if (!('+' == *src || '-' == *src)) {
|
||||||
|
val = strtol(src, &endptr, 10);
|
||||||
|
if (endptr && src != endptr) {
|
||||||
|
geom.wid = val;
|
||||||
|
assert(geom.wid >= 0);
|
||||||
|
src = endptr;
|
||||||
|
}
|
||||||
|
T_STRIPSPACE();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Parse height
|
||||||
|
if ('x' == *src) {
|
||||||
|
++src;
|
||||||
|
val = strtol(src, &endptr, 10);
|
||||||
|
if (endptr && src != endptr) {
|
||||||
|
geom.hei = val;
|
||||||
|
if (geom.hei < 0) {
|
||||||
|
printf_errf("(\"%s\"): Invalid height.", src);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
src = endptr;
|
||||||
|
}
|
||||||
|
T_STRIPSPACE();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Parse x
|
||||||
|
if ('+' == *src || '-' == *src) {
|
||||||
|
val = strtol(src, &endptr, 10);
|
||||||
|
if (endptr && src != endptr) {
|
||||||
|
geom.x = val;
|
||||||
|
if ('-' == *src && geom.x <= 0)
|
||||||
|
geom.x -= 2;
|
||||||
|
src = endptr;
|
||||||
|
}
|
||||||
|
T_STRIPSPACE();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Parse y
|
||||||
|
if ('+' == *src || '-' == *src) {
|
||||||
|
val = strtol(src, &endptr, 10);
|
||||||
|
if (endptr && src != endptr) {
|
||||||
|
geom.y = val;
|
||||||
|
if ('-' == *src && geom.y <= 0)
|
||||||
|
geom.y -= 2;
|
||||||
|
src = endptr;
|
||||||
|
}
|
||||||
|
T_STRIPSPACE();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (*src) {
|
||||||
|
printf_errf("(\"%s\"): Trailing characters.", src);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
parse_geometry_end:
|
||||||
|
*dest = geom;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse a list of opacity rules.
|
||||||
|
*/
|
||||||
|
bool parse_rule_opacity(session_t *ps, const char *src) {
|
||||||
|
// Find opacity value
|
||||||
|
char *endptr = NULL;
|
||||||
|
long val = strtol(src, &endptr, 0);
|
||||||
|
if (!endptr || endptr == src) {
|
||||||
|
printf_errf("(\"%s\"): No opacity specified?", src);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (val > 100 || val < 0) {
|
||||||
|
printf_errf("(\"%s\"): Opacity %ld invalid.", src, val);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Skip over spaces
|
||||||
|
while (*endptr && isspace(*endptr))
|
||||||
|
++endptr;
|
||||||
|
if (':' != *endptr) {
|
||||||
|
printf_errf("(\"%s\"): Opacity terminator not found.", src);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
++endptr;
|
||||||
|
|
||||||
|
// Parse pattern
|
||||||
|
// I hope 1-100 is acceptable for (void *)
|
||||||
|
return c2_parsed(ps, &ps->o.opacity_rules, endptr, (void *) val);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add a pattern to a condition linked list.
|
||||||
|
*/
|
||||||
|
bool
|
||||||
|
condlst_add(session_t *ps, c2_lptr_t **pcondlst, const char *pattern) {
|
||||||
|
if (!pattern)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if (!c2_parse(ps, pcondlst, pattern))
|
||||||
|
exit(1);
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
|
@ -0,0 +1,32 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <stdbool.h>
|
||||||
|
|
||||||
|
#include <libconfig.h>
|
||||||
|
|
||||||
|
#include "common.h"
|
||||||
|
|
||||||
|
bool parse_long(const char *, long *);
|
||||||
|
const char *parse_matrix_readnum(const char *, double *);
|
||||||
|
XFixed *parse_matrix(session_t *, const char *, const char **);
|
||||||
|
XFixed *parse_conv_kern(session_t *, const char *, const char **);
|
||||||
|
bool parse_conv_kern_lst(session_t *, const char *, XFixed **, int);
|
||||||
|
bool parse_geometry(session_t *, const char *, geometry_t *);
|
||||||
|
bool parse_rule_opacity(session_t *, const char *);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add a pattern to a condition linked list.
|
||||||
|
*/
|
||||||
|
bool condlst_add(session_t *, c2_lptr_t **, const char *);
|
||||||
|
|
||||||
|
#ifdef CONFIG_LIBCONFIG
|
||||||
|
FILE *
|
||||||
|
open_config_file(char *cpath, char **path);
|
||||||
|
|
||||||
|
void
|
||||||
|
parse_cfg_condlst(session_t *ps, const config_t *pcfg, c2_lptr_t **pcondlst,
|
||||||
|
const char *name);
|
||||||
|
|
||||||
|
void
|
||||||
|
parse_config(session_t *ps, struct options_tmp *pcfgtmp);
|
||||||
|
#endif
|
|
@ -0,0 +1,398 @@
|
||||||
|
#include <unistd.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
#include <libgen.h>
|
||||||
|
#include <libconfig.h>
|
||||||
|
|
||||||
|
#include "common.h"
|
||||||
|
#include "config.h"
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Wrapper of libconfig's <code>config_lookup_int</code>.
|
||||||
|
*
|
||||||
|
* To convert <code>int</code> value <code>config_lookup_bool</code>
|
||||||
|
* returns to <code>bool</code>.
|
||||||
|
*/
|
||||||
|
static inline void
|
||||||
|
lcfg_lookup_bool(const config_t *config, const char *path,
|
||||||
|
bool *value) {
|
||||||
|
int ival;
|
||||||
|
|
||||||
|
if (config_lookup_bool(config, path, &ival))
|
||||||
|
*value = ival;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Wrapper of libconfig's <code>config_lookup_int</code>.
|
||||||
|
*
|
||||||
|
* To deal with the different value types <code>config_lookup_int</code>
|
||||||
|
* returns in libconfig-1.3 and libconfig-1.4.
|
||||||
|
*/
|
||||||
|
static inline int
|
||||||
|
lcfg_lookup_int(const config_t *config, const char *path, int *value) {
|
||||||
|
return config_lookup_int(config, path, value);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get a file stream of the configuration file to read.
|
||||||
|
*
|
||||||
|
* Follows the XDG specification to search for the configuration file.
|
||||||
|
*/
|
||||||
|
FILE *
|
||||||
|
open_config_file(char *cpath, char **ppath) {
|
||||||
|
const static char *config_filename = "/compton.conf";
|
||||||
|
const static char *config_filename_legacy = "/.compton.conf";
|
||||||
|
const static char *config_home_suffix = "/.config";
|
||||||
|
const static char *config_system_dir = "/etc/xdg";
|
||||||
|
|
||||||
|
char *dir = NULL, *home = NULL;
|
||||||
|
char *path = cpath;
|
||||||
|
FILE *f = NULL;
|
||||||
|
|
||||||
|
if (path) {
|
||||||
|
f = fopen(path, "r");
|
||||||
|
if (f && ppath)
|
||||||
|
*ppath = path;
|
||||||
|
return f;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check user configuration file in $XDG_CONFIG_HOME firstly
|
||||||
|
if (!((dir = getenv("XDG_CONFIG_HOME")) && strlen(dir))) {
|
||||||
|
if (!((home = getenv("HOME")) && strlen(home)))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
path = mstrjoin3(home, config_home_suffix, config_filename);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
path = mstrjoin(dir, config_filename);
|
||||||
|
|
||||||
|
f = fopen(path, "r");
|
||||||
|
|
||||||
|
if (f && ppath)
|
||||||
|
*ppath = path;
|
||||||
|
else
|
||||||
|
free(path);
|
||||||
|
if (f)
|
||||||
|
return f;
|
||||||
|
|
||||||
|
// Then check user configuration file in $HOME
|
||||||
|
if ((home = getenv("HOME")) && strlen(home)) {
|
||||||
|
path = mstrjoin(home, config_filename_legacy);
|
||||||
|
f = fopen(path, "r");
|
||||||
|
if (f && ppath)
|
||||||
|
*ppath = path;
|
||||||
|
else
|
||||||
|
free(path);
|
||||||
|
if (f)
|
||||||
|
return f;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check system configuration file in $XDG_CONFIG_DIRS at last
|
||||||
|
if ((dir = getenv("XDG_CONFIG_DIRS")) && strlen(dir)) {
|
||||||
|
char *part = strtok(dir, ":");
|
||||||
|
while (part) {
|
||||||
|
path = mstrjoin(part, config_filename);
|
||||||
|
f = fopen(path, "r");
|
||||||
|
if (f && ppath)
|
||||||
|
*ppath = path;
|
||||||
|
else
|
||||||
|
free(path);
|
||||||
|
if (f)
|
||||||
|
return f;
|
||||||
|
part = strtok(NULL, ":");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
path = mstrjoin(config_system_dir, config_filename);
|
||||||
|
f = fopen(path, "r");
|
||||||
|
if (f && ppath)
|
||||||
|
*ppath = path;
|
||||||
|
else
|
||||||
|
free(path);
|
||||||
|
if (f)
|
||||||
|
return f;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse a condition list in configuration file.
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
parse_cfg_condlst(session_t *ps, const config_t *pcfg, c2_lptr_t **pcondlst,
|
||||||
|
const char *name) {
|
||||||
|
config_setting_t *setting = config_lookup(pcfg, name);
|
||||||
|
if (setting) {
|
||||||
|
// Parse an array of options
|
||||||
|
if (config_setting_is_array(setting)) {
|
||||||
|
int i = config_setting_length(setting);
|
||||||
|
while (i--)
|
||||||
|
condlst_add(ps, pcondlst, config_setting_get_string_elem(setting, i));
|
||||||
|
}
|
||||||
|
// Treat it as a single pattern if it's a string
|
||||||
|
else if (CONFIG_TYPE_STRING == config_setting_type(setting)) {
|
||||||
|
condlst_add(ps, pcondlst, config_setting_get_string(setting));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse an opacity rule list in configuration file.
|
||||||
|
*/
|
||||||
|
static inline void
|
||||||
|
parse_cfg_condlst_opct(session_t *ps, const config_t *pcfg, const char *name) {
|
||||||
|
config_setting_t *setting = config_lookup(pcfg, name);
|
||||||
|
if (setting) {
|
||||||
|
// Parse an array of options
|
||||||
|
if (config_setting_is_array(setting)) {
|
||||||
|
int i = config_setting_length(setting);
|
||||||
|
while (i--)
|
||||||
|
if (!parse_rule_opacity(ps, config_setting_get_string_elem(setting,
|
||||||
|
i)))
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
// Treat it as a single pattern if it's a string
|
||||||
|
else if (CONFIG_TYPE_STRING == config_setting_type(setting)) {
|
||||||
|
parse_rule_opacity(ps, config_setting_get_string(setting));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse a configuration file from default location.
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
parse_config(session_t *ps, struct options_tmp *pcfgtmp) {
|
||||||
|
char *path = NULL;
|
||||||
|
FILE *f;
|
||||||
|
config_t cfg;
|
||||||
|
int ival = 0;
|
||||||
|
double dval = 0.0;
|
||||||
|
// libconfig manages string memory itself, so no need to manually free
|
||||||
|
// anything
|
||||||
|
const char *sval = NULL;
|
||||||
|
|
||||||
|
f = open_config_file(ps->o.config_file, &path);
|
||||||
|
if (!f) {
|
||||||
|
if (ps->o.config_file) {
|
||||||
|
printf_errfq(1, "(): Failed to read configuration file \"%s\".",
|
||||||
|
ps->o.config_file);
|
||||||
|
free(ps->o.config_file);
|
||||||
|
ps->o.config_file = NULL;
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
config_init(&cfg);
|
||||||
|
{
|
||||||
|
// dirname() could modify the original string, thus we must pass a
|
||||||
|
// copy
|
||||||
|
char *path2 = mstrcpy(path);
|
||||||
|
char *parent = dirname(path2);
|
||||||
|
|
||||||
|
if (parent)
|
||||||
|
config_set_include_dir(&cfg, parent);
|
||||||
|
|
||||||
|
free(path2);
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
int read_result = config_read(&cfg, f);
|
||||||
|
fclose(f);
|
||||||
|
f = NULL;
|
||||||
|
if (CONFIG_FALSE == read_result) {
|
||||||
|
printf("Error when reading configuration file \"%s\", line %d: %s\n",
|
||||||
|
path, config_error_line(&cfg), config_error_text(&cfg));
|
||||||
|
config_destroy(&cfg);
|
||||||
|
free(path);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
config_set_auto_convert(&cfg, 1);
|
||||||
|
|
||||||
|
if (path != ps->o.config_file) {
|
||||||
|
free(ps->o.config_file);
|
||||||
|
ps->o.config_file = path;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get options from the configuration file. We don't do range checking
|
||||||
|
// right now. It will be done later
|
||||||
|
|
||||||
|
// -D (fade_delta)
|
||||||
|
if (lcfg_lookup_int(&cfg, "fade-delta", &ival))
|
||||||
|
ps->o.fade_delta = ival;
|
||||||
|
// -I (fade_in_step)
|
||||||
|
if (config_lookup_float(&cfg, "fade-in-step", &dval))
|
||||||
|
ps->o.fade_in_step = normalize_d(dval) * OPAQUE;
|
||||||
|
// -O (fade_out_step)
|
||||||
|
if (config_lookup_float(&cfg, "fade-out-step", &dval))
|
||||||
|
ps->o.fade_out_step = normalize_d(dval) * OPAQUE;
|
||||||
|
// -r (shadow_radius)
|
||||||
|
lcfg_lookup_int(&cfg, "shadow-radius", &ps->o.shadow_radius);
|
||||||
|
// -o (shadow_opacity)
|
||||||
|
config_lookup_float(&cfg, "shadow-opacity", &ps->o.shadow_opacity);
|
||||||
|
// -l (shadow_offset_x)
|
||||||
|
lcfg_lookup_int(&cfg, "shadow-offset-x", &ps->o.shadow_offset_x);
|
||||||
|
// -t (shadow_offset_y)
|
||||||
|
lcfg_lookup_int(&cfg, "shadow-offset-y", &ps->o.shadow_offset_y);
|
||||||
|
// -i (inactive_opacity)
|
||||||
|
if (config_lookup_float(&cfg, "inactive-opacity", &dval))
|
||||||
|
ps->o.inactive_opacity = normalize_d(dval) * OPAQUE;
|
||||||
|
// --active_opacity
|
||||||
|
if (config_lookup_float(&cfg, "active-opacity", &dval))
|
||||||
|
ps->o.active_opacity = normalize_d(dval) * OPAQUE;
|
||||||
|
// -e (frame_opacity)
|
||||||
|
config_lookup_float(&cfg, "frame-opacity", &ps->o.frame_opacity);
|
||||||
|
// -z (clear_shadow)
|
||||||
|
lcfg_lookup_bool(&cfg, "clear-shadow", &ps->o.clear_shadow);
|
||||||
|
// -c (shadow_enable)
|
||||||
|
if (config_lookup_bool(&cfg, "shadow", &ival) && ival)
|
||||||
|
wintype_arr_enable(ps->o.wintype_shadow);
|
||||||
|
// -C (no_dock_shadow)
|
||||||
|
lcfg_lookup_bool(&cfg, "no-dock-shadow", &pcfgtmp->no_dock_shadow);
|
||||||
|
// -G (no_dnd_shadow)
|
||||||
|
lcfg_lookup_bool(&cfg, "no-dnd-shadow", &pcfgtmp->no_dnd_shadow);
|
||||||
|
// -m (menu_opacity)
|
||||||
|
config_lookup_float(&cfg, "menu-opacity", &pcfgtmp->menu_opacity);
|
||||||
|
// -f (fading_enable)
|
||||||
|
if (config_lookup_bool(&cfg, "fading", &ival) && ival)
|
||||||
|
wintype_arr_enable(ps->o.wintype_fade);
|
||||||
|
// --no-fading-open-close
|
||||||
|
lcfg_lookup_bool(&cfg, "no-fading-openclose", &ps->o.no_fading_openclose);
|
||||||
|
// --no-fading-destroyed-argb
|
||||||
|
lcfg_lookup_bool(&cfg, "no-fading-destroyed-argb",
|
||||||
|
&ps->o.no_fading_destroyed_argb);
|
||||||
|
// --shadow-red
|
||||||
|
config_lookup_float(&cfg, "shadow-red", &ps->o.shadow_red);
|
||||||
|
// --shadow-green
|
||||||
|
config_lookup_float(&cfg, "shadow-green", &ps->o.shadow_green);
|
||||||
|
// --shadow-blue
|
||||||
|
config_lookup_float(&cfg, "shadow-blue", &ps->o.shadow_blue);
|
||||||
|
// --shadow-exclude-reg
|
||||||
|
if (config_lookup_string(&cfg, "shadow-exclude-reg", &sval)
|
||||||
|
&& !parse_geometry(ps, sval, &ps->o.shadow_exclude_reg_geom))
|
||||||
|
exit(1);
|
||||||
|
// --inactive-opacity-override
|
||||||
|
lcfg_lookup_bool(&cfg, "inactive-opacity-override",
|
||||||
|
&ps->o.inactive_opacity_override);
|
||||||
|
// --inactive-dim
|
||||||
|
config_lookup_float(&cfg, "inactive-dim", &ps->o.inactive_dim);
|
||||||
|
// --mark-wmwin-focused
|
||||||
|
lcfg_lookup_bool(&cfg, "mark-wmwin-focused", &ps->o.mark_wmwin_focused);
|
||||||
|
// --mark-ovredir-focused
|
||||||
|
lcfg_lookup_bool(&cfg, "mark-ovredir-focused",
|
||||||
|
&ps->o.mark_ovredir_focused);
|
||||||
|
// --shadow-ignore-shaped
|
||||||
|
lcfg_lookup_bool(&cfg, "shadow-ignore-shaped",
|
||||||
|
&ps->o.shadow_ignore_shaped);
|
||||||
|
// --detect-rounded-corners
|
||||||
|
lcfg_lookup_bool(&cfg, "detect-rounded-corners",
|
||||||
|
&ps->o.detect_rounded_corners);
|
||||||
|
// --xinerama-shadow-crop
|
||||||
|
lcfg_lookup_bool(&cfg, "xinerama-shadow-crop",
|
||||||
|
&ps->o.xinerama_shadow_crop);
|
||||||
|
// --detect-client-opacity
|
||||||
|
lcfg_lookup_bool(&cfg, "detect-client-opacity",
|
||||||
|
&ps->o.detect_client_opacity);
|
||||||
|
// --refresh-rate
|
||||||
|
lcfg_lookup_int(&cfg, "refresh-rate", &ps->o.refresh_rate);
|
||||||
|
// --vsync
|
||||||
|
if (config_lookup_string(&cfg, "vsync", &sval) && !parse_vsync(ps, sval))
|
||||||
|
exit(1);
|
||||||
|
// --backend
|
||||||
|
if (config_lookup_string(&cfg, "backend", &sval) && !parse_backend(ps, sval))
|
||||||
|
exit(1);
|
||||||
|
// --alpha-step
|
||||||
|
config_lookup_float(&cfg, "alpha-step", &ps->o.alpha_step);
|
||||||
|
// --dbe
|
||||||
|
lcfg_lookup_bool(&cfg, "dbe", &ps->o.dbe);
|
||||||
|
// --paint-on-overlay
|
||||||
|
lcfg_lookup_bool(&cfg, "paint-on-overlay", &ps->o.paint_on_overlay);
|
||||||
|
// --sw-opti
|
||||||
|
lcfg_lookup_bool(&cfg, "sw-opti", &ps->o.sw_opti);
|
||||||
|
// --use-ewmh-active-win
|
||||||
|
lcfg_lookup_bool(&cfg, "use-ewmh-active-win",
|
||||||
|
&ps->o.use_ewmh_active_win);
|
||||||
|
// --unredir-if-possible
|
||||||
|
lcfg_lookup_bool(&cfg, "unredir-if-possible",
|
||||||
|
&ps->o.unredir_if_possible);
|
||||||
|
// --unredir-if-possible-delay
|
||||||
|
if (lcfg_lookup_int(&cfg, "unredir-if-possible-delay", &ival))
|
||||||
|
ps->o.unredir_if_possible_delay = ival;
|
||||||
|
// --inactive-dim-fixed
|
||||||
|
lcfg_lookup_bool(&cfg, "inactive-dim-fixed", &ps->o.inactive_dim_fixed);
|
||||||
|
// --detect-transient
|
||||||
|
lcfg_lookup_bool(&cfg, "detect-transient", &ps->o.detect_transient);
|
||||||
|
// --detect-client-leader
|
||||||
|
lcfg_lookup_bool(&cfg, "detect-client-leader",
|
||||||
|
&ps->o.detect_client_leader);
|
||||||
|
// --shadow-exclude
|
||||||
|
parse_cfg_condlst(ps, &cfg, &ps->o.shadow_blacklist, "shadow-exclude");
|
||||||
|
// --fade-exclude
|
||||||
|
parse_cfg_condlst(ps, &cfg, &ps->o.fade_blacklist, "fade-exclude");
|
||||||
|
// --focus-exclude
|
||||||
|
parse_cfg_condlst(ps, &cfg, &ps->o.focus_blacklist, "focus-exclude");
|
||||||
|
// --invert-color-include
|
||||||
|
parse_cfg_condlst(ps, &cfg, &ps->o.invert_color_list, "invert-color-include");
|
||||||
|
// --blur-background-exclude
|
||||||
|
parse_cfg_condlst(ps, &cfg, &ps->o.blur_background_blacklist, "blur-background-exclude");
|
||||||
|
// --opacity-rule
|
||||||
|
parse_cfg_condlst_opct(ps, &cfg, "opacity-rule");
|
||||||
|
// --unredir-if-possible-exclude
|
||||||
|
parse_cfg_condlst(ps, &cfg, &ps->o.unredir_if_possible_blacklist, "unredir-if-possible-exclude");
|
||||||
|
// --blur-background
|
||||||
|
lcfg_lookup_bool(&cfg, "blur-background", &ps->o.blur_background);
|
||||||
|
// --blur-background-frame
|
||||||
|
lcfg_lookup_bool(&cfg, "blur-background-frame",
|
||||||
|
&ps->o.blur_background_frame);
|
||||||
|
// --blur-background-fixed
|
||||||
|
lcfg_lookup_bool(&cfg, "blur-background-fixed",
|
||||||
|
&ps->o.blur_background_fixed);
|
||||||
|
// --blur-kern
|
||||||
|
if (config_lookup_string(&cfg, "blur-kern", &sval)
|
||||||
|
&& !parse_conv_kern_lst(ps, sval, ps->o.blur_kerns, MAX_BLUR_PASS))
|
||||||
|
exit(1);
|
||||||
|
// --resize-damage
|
||||||
|
lcfg_lookup_int(&cfg, "resize-damage", &ps->o.resize_damage);
|
||||||
|
// --glx-no-stencil
|
||||||
|
lcfg_lookup_bool(&cfg, "glx-no-stencil", &ps->o.glx_no_stencil);
|
||||||
|
// --glx-copy-from-front
|
||||||
|
lcfg_lookup_bool(&cfg, "glx-copy-from-front", &ps->o.glx_copy_from_front);
|
||||||
|
// --glx-use-copysubbuffermesa
|
||||||
|
lcfg_lookup_bool(&cfg, "glx-use-copysubbuffermesa", &ps->o.glx_use_copysubbuffermesa);
|
||||||
|
// --glx-no-rebind-pixmap
|
||||||
|
lcfg_lookup_bool(&cfg, "glx-no-rebind-pixmap", &ps->o.glx_no_rebind_pixmap);
|
||||||
|
// --glx-swap-method
|
||||||
|
if (config_lookup_string(&cfg, "glx-swap-method", &sval)
|
||||||
|
&& !parse_glx_swap_method(ps, sval))
|
||||||
|
exit(1);
|
||||||
|
// --glx-use-gpushader4
|
||||||
|
lcfg_lookup_bool(&cfg, "glx-use-gpushader4", &ps->o.glx_use_gpushader4);
|
||||||
|
// --xrender-sync
|
||||||
|
lcfg_lookup_bool(&cfg, "xrender-sync", &ps->o.xrender_sync);
|
||||||
|
// --xrender-sync-fence
|
||||||
|
lcfg_lookup_bool(&cfg, "xrender-sync-fence", &ps->o.xrender_sync_fence);
|
||||||
|
// Wintype settings
|
||||||
|
|
||||||
|
for (wintype_t i = 0; i < NUM_WINTYPES; ++i) {
|
||||||
|
char *str = mstrjoin("wintypes.", WINTYPES[i]);
|
||||||
|
config_setting_t *setting = config_lookup(&cfg, str);
|
||||||
|
free(str);
|
||||||
|
if (setting) {
|
||||||
|
if (config_setting_lookup_bool(setting, "shadow", &ival))
|
||||||
|
ps->o.wintype_shadow[i] = (bool) ival;
|
||||||
|
if (config_setting_lookup_bool(setting, "fade", &ival))
|
||||||
|
ps->o.wintype_fade[i] = (bool) ival;
|
||||||
|
if (config_setting_lookup_bool(setting, "focus", &ival))
|
||||||
|
ps->o.wintype_focus[i] = (bool) ival;
|
||||||
|
|
||||||
|
double fval;
|
||||||
|
if (config_setting_lookup_float(setting, "opacity", &fval))
|
||||||
|
ps->o.wintype_opacity[i] = normalize_d(fval);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
config_destroy(&cfg);
|
||||||
|
}
|
|
@ -29,6 +29,7 @@ xr_glx_sync(session_t *ps, Drawable d, XSyncFence *pfence) {
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#ifdef DEBUG_GLX_DEBUG_CONTEXT
|
||||||
static inline GLXFBConfig
|
static inline GLXFBConfig
|
||||||
get_fbconfig_from_visualinfo(session_t *ps, const XVisualInfo *visualinfo) {
|
get_fbconfig_from_visualinfo(session_t *ps, const XVisualInfo *visualinfo) {
|
||||||
int nelements = 0;
|
int nelements = 0;
|
||||||
|
@ -44,7 +45,6 @@ get_fbconfig_from_visualinfo(session_t *ps, const XVisualInfo *visualinfo) {
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef DEBUG_GLX_DEBUG_CONTEXT
|
|
||||||
static void
|
static void
|
||||||
glx_debug_msg_callback(GLenum source, GLenum type,
|
glx_debug_msg_callback(GLenum source, GLenum type,
|
||||||
GLuint id, GLenum severity, GLsizei length, const GLchar *message,
|
GLuint id, GLenum severity, GLsizei length, const GLchar *message,
|
||||||
|
|
Loading…
Reference in New Issue