From 71c343bee55fceed2d3ecef401d9e96b1a070b6c Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Fri, 25 Jan 2019 00:27:38 +0000 Subject: [PATCH 01/11] Make sure draw_idle is stopped in all cases Previously, compton fails to stop draw_idle in some cases when sw_opti is enabled. sw_opti is a feature that limits the draw frequence to vblank frequence. It adds a delay to drawing when the screen is updated more frequently than the vblank frequence. However when the delay is not used (i.e. the screen is updated infrequent enough), compton will start drawing the frame directly without using the delay. And specically in this case, compton will fail to stop the draw_idle, causing a callback to be called once per loop of the mainloop, resulting in high CPU usage. Fixes #92 Signed-off-by: Yuxuan Shui --- src/compton.c | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/src/compton.c b/src/compton.c index d5dcc525..4a0cd007 100644 --- a/src/compton.c +++ b/src/compton.c @@ -2482,12 +2482,16 @@ static void delayed_draw_callback(EV_P_ ev_idle *w, int revents) { // This function is only used if we are using --swopti session_t *ps = session_ptr(w, draw_idle); - if (ev_is_active(&ps->delayed_draw_timer)) - return; + assert(ps->redraw_needed); + assert(!ev_is_active(&ps->delayed_draw_timer)); double delay = swopti_handle_timeout(ps); - if (delay < 1e-6) + if (delay < 1e-6) { + if (!ps->o.benchmark) { + ev_idle_stop(ps->loop, &ps->draw_idle); + } return _draw_callback(EV_A_ ps, revents); + } // This is a little bit hacky. When we get to this point in code, we need // to update the screen , but we will only be updating after a delay, So From a0966ff31f01096b824f91181dcd0866d4be1e4f Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Sat, 26 Jan 2019 23:07:59 +0000 Subject: [PATCH 02/11] Remove unused session_t argument from gl_has_extension Signed-off-by: Yuxuan Shui --- src/backend/gl/gl_common.h | 2 +- src/backend/gl/glx.c | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/backend/gl/gl_common.h b/src/backend/gl/gl_common.h index bf201061..6c1e60f4 100644 --- a/src/backend/gl/gl_common.h +++ b/src/backend/gl/gl_common.h @@ -118,7 +118,7 @@ static inline void gl_check_err_(const char *func, int line) { /** * Check if a GLX extension exists. */ -static inline bool gl_has_extension(session_t *ps, const char *ext) { +static inline bool gl_has_extension(const char *ext) { GLint nexts = 0; glGetIntegerv(GL_NUM_EXTENSIONS, &nexts); if (!nexts) { diff --git a/src/backend/gl/glx.c b/src/backend/gl/glx.c index ff06254a..cc126996 100644 --- a/src/backend/gl/glx.c +++ b/src/backend/gl/glx.c @@ -432,8 +432,8 @@ static void *glx_init(session_t *ps) { // Check GL_ARB_texture_non_power_of_two, requires a GLX context and // must precede FBConfig fetching - gd->cap.non_power_of_two_texture = gl_has_extension(ps, "GL_ARB_texture_non_" - "power_of_two"); + gd->cap.non_power_of_two_texture = gl_has_extension("GL_ARB_texture_non_" + "power_of_two"); gd->glXBindTexImage = (void *)glXGetProcAddress((const GLubyte *)"glXBindTexImage" "EXT"); From eff3f1dc2b7df35c43dc92527cb556fd5cf99be0 Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Sun, 27 Jan 2019 17:45:38 +0000 Subject: [PATCH 03/11] Don't pretend that we have glStringMarker Signed-off-by: Yuxuan Shui --- src/log.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/log.c b/src/log.c index 4c09c695..9f801106 100644 --- a/src/log.c +++ b/src/log.c @@ -344,7 +344,7 @@ struct log_target *glx_string_marker_logger_new(void) { #else struct log_target *glx_string_marker_logger_new(void) { - return null_logger_new(); + return NULL; } #endif From 09707d4b7abc24711fc8c5b7ce7e6541e6e36b3c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Antonin=20D=C3=A9cimo?= Date: Mon, 28 Jan 2019 10:58:14 +0100 Subject: [PATCH 04/11] Fix small misspellings --- Doxyfile | 2 +- bin/compton-trans | 2 +- meson_options.txt | 2 +- src/c2.c | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/Doxyfile b/Doxyfile index eddba846..741325c7 100644 --- a/Doxyfile +++ b/Doxyfile @@ -1674,7 +1674,7 @@ UML_LOOK = NO # the class node. If there are many fields or methods and many nodes the # graph may become too big to be useful. The UML_LIMIT_NUM_FIELDS # threshold limits the number of items for each type to make the size more -# managable. Set this to 0 for no limit. Note that the threshold may be +# manageable. Set this to 0 for no limit. Note that the threshold may be # exceeded by 50% before the limit is enforced. UML_LIMIT_NUM_FIELDS = 10 diff --git a/bin/compton-trans b/bin/compton-trans index db41cf18..af2d3309 100755 --- a/bin/compton-trans +++ b/bin/compton-trans @@ -50,7 +50,7 @@ for v in "$@"; do done # This takes into account the fact that getopts stops on -# any argument it doesn't recongize or errors on. This +# any argument it doesn't recognize or errors on. This # allows for things like `compton-trans -5` as well # as `compton-trans -c +5 -s` (contrived example). while test $# -gt 0; do diff --git a/meson_options.txt b/meson_options.txt index 1a15445d..c2dd63d4 100644 --- a/meson_options.txt +++ b/meson_options.txt @@ -6,7 +6,7 @@ option('regex', type: 'boolean', value: true, description: 'Enable regex support option('vsync_drm', type: 'boolean', value: false, description: 'Enable support for using drm for vsync') option('opengl', type: 'boolean', value: true, description: 'Enable features that require opengl (opengl backend, and opengl vsync methods)') -option('dbus', type: 'boolean', value: true, description: 'Enable suport for D-Bus remote control') +option('dbus', type: 'boolean', value: true, description: 'Enable support for D-Bus remote control') option('xrescheck', type: 'boolean', value: false, description: 'Enable X resource leak checker (for debug only)') diff --git a/src/c2.c b/src/c2.c index 3ea8a4be..7ae66c85 100644 --- a/src/c2.c +++ b/src/c2.c @@ -19,7 +19,7 @@ #ifdef CONFIG_REGEX_PCRE #include -// For compatiblity with Date: Tue, 29 Jan 2019 22:26:26 +0000 Subject: [PATCH 05/11] Remove a redundant glEnd in glx_dim_dst Signed-off-by: Yuxuan Shui --- src/backend/gl/gl_common.c | 2 -- src/opengl.c | 2 -- 2 files changed, 4 deletions(-) diff --git a/src/backend/gl/gl_common.c b/src/backend/gl/gl_common.c index 78101624..079b7884 100644 --- a/src/backend/gl/gl_common.c +++ b/src/backend/gl/gl_common.c @@ -306,8 +306,6 @@ bool gl_dim_reg(session_t *ps, int dx, int dy, int width, int height, float z, P_PAINTREG_END(); } - glEnd(); - glColor4f(0.0f, 0.0f, 0.0f, 0.0f); glDisable(GL_BLEND); diff --git a/src/opengl.c b/src/opengl.c index 3f63cd7e..982fe2b4 100644 --- a/src/opengl.c +++ b/src/opengl.c @@ -1224,8 +1224,6 @@ glx_dim_dst(session_t *ps, int dx, int dy, int width, int height, float z, P_PAINTREG_END(); } - glEnd(); - glColor4f(0.0f, 0.0f, 0.0f, 0.0f); glDisable(GL_BLEND); From f18e862845e3a69b8d844e44deacbbfb89c76926 Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Tue, 29 Jan 2019 23:18:44 +0000 Subject: [PATCH 06/11] Use glDrawBuffer instead of glDrawBuffers in glx_blur_dst glDrawBuffers doesn't take GL_BACK, which is what we are passing. And we are using only one buffer argument anyway, no need to use glDrawBuffers. Signed-off-by: Yuxuan Shui --- src/opengl.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/src/opengl.c b/src/opengl.c index 982fe2b4..eafd5223 100644 --- a/src/opengl.c +++ b/src/opengl.c @@ -1102,11 +1102,10 @@ glx_blur_dst(session_t *ps, int dx, int dy, int width, int height, float z, glBindTexture(tex_tgt, tex_scr); if (!last_pass) { - static const GLenum DRAWBUFS[2] = { GL_COLOR_ATTACHMENT0 }; glBindFramebuffer(GL_FRAMEBUFFER, fbo); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex_scr2, 0); - glDrawBuffers(1, DRAWBUFS); + glDrawBuffer(GL_COLOR_ATTACHMENT0); if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) { log_error("Framebuffer attachment failed."); @@ -1114,9 +1113,8 @@ glx_blur_dst(session_t *ps, int dx, int dy, int width, int height, float z, } } else { - static const GLenum DRAWBUFS[2] = { GL_BACK }; glBindFramebuffer(GL_FRAMEBUFFER, 0); - glDrawBuffers(1, DRAWBUFS); + glDrawBuffer(GL_BACK); if (have_scissors) glEnable(GL_SCISSOR_TEST); if (have_stencil) From 484fd14ec9337722e4b12048a43b42fe3f0b7cdf Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Tue, 29 Jan 2019 23:24:40 +0000 Subject: [PATCH 07/11] Remove mentions of dbe from the man page Signed-off-by: Yuxuan Shui --- man/compton.1.asciidoc | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/man/compton.1.asciidoc b/man/compton.1.asciidoc index 17e51f31..8a3a3f62 100644 --- a/man/compton.1.asciidoc +++ b/man/compton.1.asciidoc @@ -144,9 +144,6 @@ OPTIONS *--vsync-aggressive*:: Attempt to send painting request before VBlank and do XFlush() during VBlank. Reported to work pretty terribly. This switch may be lifted out at any moment. -*--dbe*:: - Enable DBE painting mode, intended to use with VSync to (hopefully) eliminate tearing. Reported to have no effect, though. - *--paint-on-overlay*:: Painting on X Composite overlay window instead of on root window. @@ -216,7 +213,7 @@ May also be one of the predefined kernels: `3x3box` (default), `5x5box`, `7x7box Exclude conditions for background blur. *--resize-damage* 'INTEGER':: - Resize damaged region by a specific number of pixels. A positive value enlarges it while a negative one shrinks it. If the value is positive, those additional pixels will not be actually painted to screen, only used in blur calculation, and such. (Due to technical limitations, with *--dbe* or *--glx-swap-method*, those pixels will still be incorrectly painted to screen.) Primarily used to fix the line corruption issues of blur, in which case you should use the blur radius value here (e.g. with a 3x3 kernel, you should use *--resize-damage* 1, with a 5x5 one you use *--resize-damage* 2, and so on). May or may not work with `--glx-no-stencil`. Shrinking doesn't function correctly. + Resize damaged region by a specific number of pixels. A positive value enlarges it while a negative one shrinks it. If the value is positive, those additional pixels will not be actually painted to screen, only used in blur calculation, and such. (Due to technical limitations, with *--glx-swap-method*, those pixels will still be incorrectly painted to screen.) Primarily used to fix the line corruption issues of blur, in which case you should use the blur radius value here (e.g. with a 3x3 kernel, you should use *--resize-damage* 1, with a 5x5 one you use *--resize-damage* 2, and so on). May or may not work with `--glx-no-stencil`. Shrinking doesn't function correctly. *--invert-color-include* 'CONDITION':: Specify a list of conditions of windows that should be painted with inverted color. Resource-hogging, and is not well tested. From 61d8e7825f0667a1d7ae266b775a3e7e64a1e31f Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Tue, 29 Jan 2019 23:36:34 +0000 Subject: [PATCH 08/11] `compton -h` should quit after printing help Signed-off-by: Yuxuan Shui --- src/options.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/src/options.c b/src/options.c index b58583b5..68ab4bd8 100644 --- a/src/options.c +++ b/src/options.c @@ -8,7 +8,7 @@ #include #include #include -#include // for xcb_render_fixed_t, XXX +#include // for xcb_render_fixed_t, XXX #include "common.h" #include "config.h" @@ -20,7 +20,7 @@ #pragma GCC diagnostic error "-Wunused-parameter" /** - * Print usage text and exit. + * Print usage text. */ static void usage(int ret) { #define WARNING_DISABLED " (DISABLED AT COMPILE TIME)" @@ -479,9 +479,13 @@ bool get_early_config(int argc, char *const *argv, char **config_file, bool *all // arguments optind = 1; *config_file = NULL; + *exit_code = 0; while (-1 != (o = getopt_long(argc, argv, shortopts, longopts, &longopt_idx))) { if (o == 256) { *config_file = strdup(optarg); + } else if (o == 'h') { + usage(0); + return true; } else if (o == 'd') { log_warn("-d will be ignored, please use the DISPLAY " "environment variable"); @@ -489,7 +493,6 @@ bool get_early_config(int argc, char *const *argv, char **config_file, bool *all *all_xerrors = true; } else if (o == 318) { printf("%s\n", COMPTON_VERSION); - *exit_code = 0; return true; } else if (o == 'S') { log_warn("-S will be ignored"); @@ -497,7 +500,6 @@ bool get_early_config(int argc, char *const *argv, char **config_file, bool *all log_warn("--no-name-pixmap will be ignored"); } else if (o == '?' || o == ':') { usage(1); - *exit_code = 1; return true; } } From 2eb8cf961ee12bad5b8e93333991f72c71dc4a29 Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Wed, 30 Jan 2019 00:12:12 +0000 Subject: [PATCH 09/11] Use strncpy for string_utils functions Also removed mstrjoin3 since it's not used. Signed-off-by: Yuxuan Shui --- src/opengl.c | 2 +- src/string_utils.c | 39 +++++++++++++++++++-------------------- 2 files changed, 20 insertions(+), 21 deletions(-) diff --git a/src/opengl.c b/src/opengl.c index eafd5223..84744782 100644 --- a/src/opengl.c +++ b/src/opengl.c @@ -561,7 +561,7 @@ glx_init_blur(session_t *ps) { const char *texture_func = (use_texture_rect ? "texture2DRect": "texture2D"); const char *shader_add = FRAG_SHADER_BLUR_ADD; - char *extension = strdup(""); + char *extension = NULL; if (use_texture_rect) mstrextend(&extension, "#extension GL_ARB_texture_rectangle : require\n"); if (ps->o.glx_use_gpushader4) { diff --git a/src/string_utils.c b/src/string_utils.c index 064db9c4..df0ac8dd 100644 --- a/src/string_utils.c +++ b/src/string_utils.c @@ -11,33 +11,32 @@ * Allocate the space and join two strings. */ char *mstrjoin(const char *src1, const char *src2) { - auto str = ccalloc(strlen(src1)+strlen(src2)+1, char); + auto len1 = strlen(src1); + auto len2 = strlen(src2); + auto len = len1 + len2 + 1; + auto str = ccalloc(len, char); - strcpy(str, src1); - strcat(str, src2); + strncpy(str, src1, len1); + strncpy(str + len1, src2, len2); + str[len - 1] = '\0'; - return str; -} - -/** - * Allocate the space and join two strings; - */ -char * -mstrjoin3(const char *src1, const char *src2, const char *src3) { - auto str = ccalloc(strlen(src1)+strlen(src2)+strlen(src3)+1, char); - - strcpy(str, src1); - strcat(str, src2); - strcat(str, src3); - - return str; + return str; } /** * Concatenate a string on heap with another string. */ void mstrextend(char **psrc1, const char *src2) { - *psrc1 = crealloc(*psrc1, (*psrc1 ? strlen(*psrc1) : 0)+strlen(src2)+1); + if (!*psrc1) { + *psrc1 = strdup(src2); + return; + } - strcat(*psrc1, src2); + auto len1 = strlen(*psrc1); + auto len2 = strlen(src2); + auto len = len1 + len2 + 1; + *psrc1 = crealloc(*psrc1, len); + + strncpy(*psrc1 + len1, src2, len2); + (*psrc1)[len - 1] = '\0'; } From 14cf5f455e89a125a042565576c16915d6dd0f23 Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Wed, 30 Jan 2019 00:27:14 +0000 Subject: [PATCH 10/11] Improve config file search order Previously the search order is: ~/.config/compton/compton.conf /etc/xdg/compton/compton.conf ~/.config/compton.conf /etc/xdg/compton.conf ... Now the search order is: ~/.config/compton/compton.conf ~/.config/compton.conf ~/.compton.conf /etc/xdg/compton/compton.conf ... In other word, compton will now search all possible user config file path first before searching for a system config file. Signed-off-by: Yuxuan Shui --- src/config_libconfig.c | 69 +++++++++++++++++++++++++++++------------- 1 file changed, 48 insertions(+), 21 deletions(-) diff --git a/src/config_libconfig.c b/src/config_libconfig.c index 9dd9ae84..03ee084f 100644 --- a/src/config_libconfig.c +++ b/src/config_libconfig.c @@ -37,6 +37,28 @@ lcfg_lookup_bool(const config_t *config, const char *path, bool *value) { return ret; } +/// Search for config file under a base directory +FILE * +open_config_file_at(const char *base, char **out_path) { + static const char *config_paths[] = { + "/compton.conf", + "/compton/compton.conf" + }; + for (size_t i = 0; i < ARR_SIZE(config_paths); i++) { + char *path = mstrjoin(base, config_paths[i]); + FILE *ret = fopen(path, "r"); + if (ret && out_path) { + *out_path = path; + } else { + free(path); + } + if (ret) { + return ret; + } + } + return NULL; +} + /** * Get a file stream of the configuration file to read. * @@ -44,10 +66,6 @@ lcfg_lookup_bool(const config_t *config, const char *path, bool *value) { */ FILE * open_config_file(const char *cpath, char **ppath) { - static const char *config_paths[] = { - "/compton.conf", - "/compton/compton.conf" - }; static const char config_filename_legacy[] = "/.compton.conf"; if (cpath) { @@ -57,31 +75,40 @@ open_config_file(const char *cpath, char **ppath) { return ret; } - for (size_t i = 0; i < ARR_SIZE(config_paths); i++) { - char *path = xdgConfigFind(config_paths[i], NULL); - FILE *ret = fopen(path, "r"); + // First search for config file in user config directory + auto config_home = xdgConfigHome(NULL); + auto ret = open_config_file_at(config_home, ppath); + free((void *)config_home); + if (ret) { + return ret; + } + + // Fall back to legacy config file in user home directory + const char *home = getenv("HOME"); + if (home && strlen(home)) { + auto path = mstrjoin(home, config_filename_legacy); + ret = fopen(path, "r"); if (ret && ppath) { - *ppath = strdup(path); + *ppath = path; + } else { + free(path); } - free(path); if (ret) { return ret; } } - // Fall back to legacy config file names - const char *home = getenv("HOME"); - if (home && strlen(home)) { - auto path = ccalloc(strlen(home)+strlen(config_filename_legacy)+1, char); - strcpy(path, home); - strcpy(path+strlen(home), config_filename_legacy); - FILE *ret = fopen(path, "r"); - if (ret && ppath) - *ppath = path; - else - free(path); - return ret; + // Fall back to config file in system config directory + auto config_dirs = xdgConfigDirectories(NULL); + for (int i = 0; config_dirs[i]; i++) { + ret = open_config_file_at(config_dirs[i], ppath); + if (ret) { + free((void *)config_dirs); + return ret; + } } + free((void *)config_dirs); + return NULL; } From ade018fb5d1bd13bb1e487dd85552c48d123022f Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Wed, 30 Jan 2019 20:53:34 +0000 Subject: [PATCH 11/11] Tweak the wording in man page Make it clearer how command line options and config file options are related. Signed-off-by: Yuxuan Shui --- man/compton.1.asciidoc | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/man/compton.1.asciidoc b/man/compton.1.asciidoc index 8a3a3f62..aa0b5fbd 100644 --- a/man/compton.1.asciidoc +++ b/man/compton.1.asciidoc @@ -354,7 +354,9 @@ CONFIGURATION FILES ------------------- compton could read from a configuration file if libconfig support is compiled in. If *--config* is not used, compton will seek for a configuration file in `$XDG_CONFIG_HOME/compton.conf` (`~/.config/compton.conf`, usually), then `~/.compton.conf`, then `compton.conf` under `$XDG_CONFIG_DIRS` (often `/etc/xdg/compton.conf`). -compton uses general libconfig configuration file format. A sample configuration file is available as `compton.sample.conf` in the source tree. Most commandline switches each could be replaced with an option in configuration file, thus documented above. Window-type-specific settings are exposed only in configuration file and has the following format: +compton uses general libconfig configuration file format. A sample configuration file is available as `compton.sample.conf` in the source tree. Most of commandline switches can be used as options in configuration file as well. For example, *--vsync* option documented above can be set in the configuration file using `vsync = `. Command line options will always overwrite the settings in the configuration file. + +Window-type-specific settings are exposed only in configuration file and has the following format: ------------ wintypes: