diff options
| author | oni-link <knil.ino@gmail.com> | 2016-09-02 01:51:23 +0200 | 
|---|---|---|
| committer | oni-link <knil.ino@gmail.com> | 2016-09-08 21:29:20 +0200 | 
| commit | 1c9d7270a85a185e3d0fabcc22344d1319012ef3 (patch) | |
| tree | 0a241c528664e883a906e2842322b432499f8c53 /src/nvim/eval.c | |
| parent | fe06e2a4a076d698e921411608d7a6cbe8877175 (diff) | |
| download | rneovim-1c9d7270a85a185e3d0fabcc22344d1319012ef3.tar.gz rneovim-1c9d7270a85a185e3d0fabcc22344d1319012ef3.tar.bz2 rneovim-1c9d7270a85a185e3d0fabcc22344d1319012ef3.zip  | |
eval.c: Garbage collection frees dictionary before job cleanup
Removing a job too early from the joblist gives garbage collection the
chance to also remove the job dictionary.
Can be triggered with ASAN while waiting 'updatetime'ms (~5 seconds)
before closing the terminal window opened with:
    nvim -u NONE +'call termopen("true",{})'
Diffstat (limited to 'src/nvim/eval.c')
| -rw-r--r-- | src/nvim/eval.c | 7 | 
1 files changed, 4 insertions, 3 deletions
diff --git a/src/nvim/eval.c b/src/nvim/eval.c index 211419f7a6..c373d3e8ef 100644 --- a/src/nvim/eval.c +++ b/src/nvim/eval.c @@ -21768,6 +21768,9 @@ static inline bool common_job_start(TerminalJobData *data, typval_T *rettv)      return false;    } +  data->id = next_chan_id++; +  pmap_put(uint64_t)(jobs, data->id, data); +    data->refcount++;    char *cmd = xstrdup(proc->argv[0]);    if (!process_spawn(proc)) { @@ -21782,7 +21785,6 @@ static inline bool common_job_start(TerminalJobData *data, typval_T *rettv)    }    xfree(cmd); -  data->id = next_chan_id++;    if (data->rpc) {      // the rpc channel takes over the in and out streams @@ -21799,7 +21801,6 @@ static inline bool common_job_start(TerminalJobData *data, typval_T *rettv)      rstream_init(proc->err, 0);      rstream_start(proc->err, on_job_stderr, data);    } -  pmap_put(uint64_t)(jobs, data->id, data);    rettv->vval.v_number = data->id;    return true;  } @@ -21821,6 +21822,7 @@ static inline void free_term_job_data_event(void **argv)      dict_unref(data->self);    }    queue_free(data->events); +  pmap_del(uint64_t)(jobs, data->id);    xfree(data);  } @@ -21927,7 +21929,6 @@ static void on_process_exit(Process *proc, int status, void *d)    process_job_event(data, data->on_exit, "exit", NULL, 0, status); -  pmap_del(uint64_t)(jobs, data->id);    term_job_data_decref(data);  }  | 
