diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/pulse/context.c | 122 | ||||
| -rw-r--r-- | src/pulse/internal.h | 19 | 
2 files changed, 42 insertions, 99 deletions
diff --git a/src/pulse/context.c b/src/pulse/context.c index 63114e10..b8182884 100644 --- a/src/pulse/context.c +++ b/src/pulse/context.c @@ -70,6 +70,7 @@  #include <pulsecore/socket-util.h>  #include <pulsecore/creds.h>  #include <pulsecore/macro.h> +#include <pulsecore/proplist-util.h>  #include "internal.h" @@ -169,6 +170,7 @@ pa_context *pa_context_new_with_proplist(pa_mainloop_api *mainloop, const char *      c->autospawn_lock_fd = -1;      memset(&c->spawn_api, 0, sizeof(c->spawn_api));      c->do_autospawn = FALSE; +    c->do_shm = FALSE;  #ifndef MSG_NOSIGNAL  #ifdef SIGPIPE @@ -424,6 +426,7 @@ static void setup_complete_callback(pa_pdispatch *pd, uint32_t command, uint32_t      switch(c->state) {          case PA_CONTEXT_AUTHORIZING: {              pa_tagstruct *reply; +            pa_bool_t shm_on_remote;              if (pa_tagstruct_getu32(t, &c->version) < 0 ||                  !pa_tagstruct_eof(t)) { @@ -437,10 +440,22 @@ static void setup_complete_callback(pa_pdispatch *pd, uint32_t command, uint32_t                  goto finish;              } +            /* Starting with protocol version 13 the MSB of the version +               tag reflects if shm is available for this connection or +               not. */ +            if (c->version >= 13) { +                shm_on_remote = !!(c->version & 0x80000000U); +                c->version &= 0x7FFFFFFFU; +            } + +            pa_log_debug("Protocol version: remote %u, local %u", c->version, PA_PROTOCOL_VERSION); +              /* Enable shared memory support if possible */ -            if (c->version >= 10 && -                pa_mempool_is_shared(c->mempool) && -                c->is_local) { +            if (c->do_shm) +                if (c->version < 10 || (c->version >= 13 && !shm_on_remote)) +                    c->do_shm = FALSE; + +            if (c->do_shm) {                  /* Only enable SHM if both sides are owned by the same                   * user. This is a security measure because otherwise @@ -448,12 +463,14 @@ static void setup_complete_callback(pa_pdispatch *pd, uint32_t command, uint32_t  #ifdef HAVE_CREDS                  const pa_creds *creds; -                if ((creds = pa_pdispatch_creds(pd))) -                    if (getuid() == creds->uid) -                        pa_pstream_enable_shm(c->pstream, TRUE); +                if (!(creds = pa_pdispatch_creds(pd)) || getuid() != creds->uid) +                    c->do_shm = FALSE;  #endif              } +            pa_log_debug("Negotiated SHM: %s", pa_yes_no(c->do_shm)); +            pa_pstream_enable_shm(c->pstream, c->do_shm); +              reply = pa_tagstruct_command(c, PA_COMMAND_SET_CLIENT_NAME, &tag);              if (c->version >= 13) { @@ -512,7 +529,16 @@ static void setup_context(pa_context *c, pa_iochannel *io) {          pa_log_info("No cookie loaded. Attempting to connect without.");      t = pa_tagstruct_command(c, PA_COMMAND_AUTH, &tag); -    pa_tagstruct_putu32(t, PA_PROTOCOL_VERSION); + +    c->do_shm = +        pa_mempool_is_shared(c->mempool) && +        c->is_local; + +    pa_log_debug("SHM possible: %s", pa_yes_no(c->do_shm)); + +    /* Starting with protocol version 13 we use the MSB of the version +     * tag for informing the other side if we could do SHM or not */ +    pa_tagstruct_putu32(t, PA_PROTOCOL_VERSION | (c->do_shm ? 0x80000000U : 0));      pa_tagstruct_put_arbitrary(t, c->conf->cookie, sizeof(c->conf->cookie));  #ifdef HAVE_CREDS @@ -1202,85 +1228,3 @@ pa_operation *pa_context_proplist_remove(pa_context *c, const char *const keys[]      return o;  } - -void pa_init_proplist(pa_proplist *p) { -    int a, b; -#ifndef HAVE_DECL_ENVIRON -    extern char **environ; -#endif -    char **e; - -    pa_assert(p); - -    for (e = environ; *e; e++) { - -        if (pa_startswith(*e, "PULSE_PROP_")) { -            size_t kl = strcspn(*e+11, "="); -            char *k; - -            if ((*e)[11+kl] != '=') -                continue; - -            if (!pa_utf8_valid(*e+11+kl+1)) -                continue; - -            k = pa_xstrndup(*e+11, kl); - -            if (pa_proplist_contains(p, k)) { -                pa_xfree(k); -                continue; -            } - -            pa_proplist_sets(p, k, *e+11+kl+1); -            pa_xfree(k); -        } -    } - -    if (!pa_proplist_contains(p, PA_PROP_APPLICATION_PROCESS_ID)) { -        char t[32]; -        pa_snprintf(t, sizeof(t), "%lu", (unsigned long) getpid()); -        pa_proplist_sets(p, PA_PROP_APPLICATION_PROCESS_ID, t); -    } - -    if (!pa_proplist_contains(p, PA_PROP_APPLICATION_PROCESS_USER)) { -        char t[64]; -        if (pa_get_user_name(t, sizeof(t))) { -            char *c = pa_utf8_filter(t); -            pa_proplist_sets(p, PA_PROP_APPLICATION_PROCESS_USER, c); -            pa_xfree(c); -        } -    } - -    if (!pa_proplist_contains(p, PA_PROP_APPLICATION_PROCESS_HOST)) { -        char t[64]; -        if (pa_get_host_name(t, sizeof(t))) { -            char *c = pa_utf8_filter(t); -            pa_proplist_sets(p, PA_PROP_APPLICATION_PROCESS_HOST, c); -            pa_xfree(c); -        } -    } - -    a = pa_proplist_contains(p, PA_PROP_APPLICATION_PROCESS_BINARY); -    b = pa_proplist_contains(p, PA_PROP_APPLICATION_NAME); - -    if (!a || !b) { -        char t[PATH_MAX]; -        if (pa_get_binary_name(t, sizeof(t))) { -            char *c = pa_utf8_filter(t); - -            if (!a) -                pa_proplist_sets(p, PA_PROP_APPLICATION_PROCESS_BINARY, c); -            if (!b) -                pa_proplist_sets(p, PA_PROP_APPLICATION_NAME, c); - -            pa_xfree(c); -        } -    } - -    if (!pa_proplist_contains(p, PA_PROP_APPLICATION_LANGUAGE)) { -        const char *l; - -        if ((l = setlocale(LC_MESSAGES, NULL))) -            pa_proplist_sets(p, PA_PROP_APPLICATION_LANGUAGE, l); -    } -} diff --git a/src/pulse/internal.h b/src/pulse/internal.h index 9b288562..2a808d17 100644 --- a/src/pulse/internal.h +++ b/src/pulse/internal.h @@ -75,8 +75,9 @@ struct pa_context {      pa_mempool *mempool; -    pa_bool_t is_local; -    pa_bool_t do_autospawn; +    pa_bool_t is_local:1; +    pa_bool_t do_autospawn:1; +    pa_bool_t do_shm:1;      int autospawn_lock_fd;      pa_spawn_api spawn_api; @@ -117,8 +118,13 @@ struct pa_stream {      pa_proplist *proplist; +    pa_bool_t channel_valid:1; +    pa_bool_t suspended:1; +    pa_bool_t corked:1; +    pa_bool_t timing_info_valid:1; +    pa_bool_t auto_timing_update_requested:1; +      uint32_t channel; -    pa_bool_t channel_valid;      uint32_t syncid;      uint32_t stream_index; @@ -127,17 +133,13 @@ struct pa_stream {      uint32_t device_index;      char *device_name; -    pa_bool_t suspended;      pa_memchunk peek_memchunk;      void *peek_data;      pa_memblockq *record_memblockq; -    pa_bool_t corked; -      /* Store latest latency info */      pa_timing_info timing_info; -    pa_bool_t timing_info_valid;      /* Use to make sure that time advances monotonically */      pa_usec_t previous_time; @@ -152,7 +154,6 @@ struct pa_stream {      /* Latency interpolation stuff */      pa_time_event *auto_timing_update_event; -    pa_bool_t auto_timing_update_requested;      pa_smoother *smoother; @@ -234,6 +235,4 @@ pa_tagstruct *pa_tagstruct_command(pa_context *c, uint32_t command, uint32_t *ta  #define PA_CHECK_VALIDITY_RETURN_NULL(context, expression, error) PA_CHECK_VALIDITY_RETURN_ANY(context, expression, error, NULL) -void pa_init_proplist(pa_proplist *p); -  #endif  | 
