mirror of
https://github.com/neovim/neovim.git
synced 2025-09-15 15:58:17 +00:00
refactor(api): use arena for channel info and terminal info
This commit is contained in:
@@ -1046,7 +1046,7 @@ static Array translate_firstarg(UI *ui, Array args, Arena *arena)
|
|||||||
|
|
||||||
ADD_C(new_args, ARRAY_OBJ(translate_contents(ui, contents, arena)));
|
ADD_C(new_args, ARRAY_OBJ(translate_contents(ui, contents, arena)));
|
||||||
for (size_t i = 1; i < args.size; i++) {
|
for (size_t i = 1; i < args.size; i++) {
|
||||||
ADD(new_args, args.items[i]);
|
ADD_C(new_args, args.items[i]);
|
||||||
}
|
}
|
||||||
return new_args;
|
return new_args;
|
||||||
}
|
}
|
||||||
|
@@ -1633,7 +1633,7 @@ void nvim_set_client_info(uint64_t channel_id, String name, Dictionary version,
|
|||||||
/// the RPC channel), if provided by it via
|
/// the RPC channel), if provided by it via
|
||||||
/// |nvim_set_client_info()|.
|
/// |nvim_set_client_info()|.
|
||||||
///
|
///
|
||||||
Dictionary nvim_get_chan_info(uint64_t channel_id, Integer chan, Error *err)
|
Dictionary nvim_get_chan_info(uint64_t channel_id, Integer chan, Arena *arena, Error *err)
|
||||||
FUNC_API_SINCE(4)
|
FUNC_API_SINCE(4)
|
||||||
{
|
{
|
||||||
if (chan < 0) {
|
if (chan < 0) {
|
||||||
@@ -1644,17 +1644,17 @@ Dictionary nvim_get_chan_info(uint64_t channel_id, Integer chan, Error *err)
|
|||||||
assert(channel_id <= INT64_MAX);
|
assert(channel_id <= INT64_MAX);
|
||||||
chan = (Integer)channel_id;
|
chan = (Integer)channel_id;
|
||||||
}
|
}
|
||||||
return channel_info((uint64_t)chan);
|
return channel_info((uint64_t)chan, arena);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Get information about all open channels.
|
/// Get information about all open channels.
|
||||||
///
|
///
|
||||||
/// @returns Array of Dictionaries, each describing a channel with
|
/// @returns Array of Dictionaries, each describing a channel with
|
||||||
/// the format specified at |nvim_get_chan_info()|.
|
/// the format specified at |nvim_get_chan_info()|.
|
||||||
Array nvim_list_chans(void)
|
Array nvim_list_chans(Arena *arena)
|
||||||
FUNC_API_SINCE(4)
|
FUNC_API_SINCE(4)
|
||||||
{
|
{
|
||||||
return channel_all_info();
|
return channel_all_info(arena);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Calls many API methods atomically.
|
/// Calls many API methods atomically.
|
||||||
@@ -1891,7 +1891,7 @@ Array nvim_get_proc_children(Integer pid, Arena *arena, Error *err)
|
|||||||
// syscall failed (possibly because of kernel options), try shelling out.
|
// syscall failed (possibly because of kernel options), try shelling out.
|
||||||
DLOG("fallback to vim._os_proc_children()");
|
DLOG("fallback to vim._os_proc_children()");
|
||||||
MAXSIZE_TEMP_ARRAY(a, 1);
|
MAXSIZE_TEMP_ARRAY(a, 1);
|
||||||
ADD(a, INTEGER_OBJ(pid));
|
ADD_C(a, INTEGER_OBJ(pid));
|
||||||
Object o = NLUA_EXEC_STATIC("return vim._os_proc_children(...)", a, kRetObject, arena, err);
|
Object o = NLUA_EXEC_STATIC("return vim._os_proc_children(...)", a, kRetObject, arena, err);
|
||||||
if (o.type == kObjectTypeArray) {
|
if (o.type == kObjectTypeArray) {
|
||||||
rvobj = o.data.array;
|
rvobj = o.data.array;
|
||||||
@@ -1903,7 +1903,7 @@ Array nvim_get_proc_children(Integer pid, Arena *arena, Error *err)
|
|||||||
} else {
|
} else {
|
||||||
rvobj = arena_array(arena, proc_count);
|
rvobj = arena_array(arena, proc_count);
|
||||||
for (size_t i = 0; i < proc_count; i++) {
|
for (size_t i = 0; i < proc_count; i++) {
|
||||||
ADD(rvobj, INTEGER_OBJ(proc_list[i]));
|
ADD_C(rvobj, INTEGER_OBJ(proc_list[i]));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1925,7 +1925,7 @@ Object nvim_get_proc(Integer pid, Arena *arena, Error *err)
|
|||||||
});
|
});
|
||||||
|
|
||||||
#ifdef MSWIN
|
#ifdef MSWIN
|
||||||
rvobj = DICTIONARY_OBJ(os_proc_info((int)pid));
|
rvobj = DICTIONARY_OBJ(os_proc_info((int)pid, arena));
|
||||||
if (rvobj.data.dictionary.size == 0) { // Process not found.
|
if (rvobj.data.dictionary.size == 0) { // Process not found.
|
||||||
return NIL;
|
return NIL;
|
||||||
}
|
}
|
||||||
|
@@ -238,7 +238,8 @@ void channel_create_event(Channel *chan, const char *ext_source)
|
|||||||
}
|
}
|
||||||
|
|
||||||
assert(chan->id <= VARNUMBER_MAX);
|
assert(chan->id <= VARNUMBER_MAX);
|
||||||
Dictionary info = channel_info(chan->id);
|
Arena arena = ARENA_EMPTY;
|
||||||
|
Dictionary info = channel_info(chan->id, &arena);
|
||||||
typval_T tv = TV_INITIAL_VALUE;
|
typval_T tv = TV_INITIAL_VALUE;
|
||||||
// TODO(bfredl): do the conversion in one step. Also would be nice
|
// TODO(bfredl): do the conversion in one step. Also would be nice
|
||||||
// to pretty print top level dict in defined order
|
// to pretty print top level dict in defined order
|
||||||
@@ -247,7 +248,7 @@ void channel_create_event(Channel *chan, const char *ext_source)
|
|||||||
char *str = encode_tv2json(&tv, NULL);
|
char *str = encode_tv2json(&tv, NULL);
|
||||||
ILOG("new channel %" PRIu64 " (%s) : %s", chan->id, source, str);
|
ILOG("new channel %" PRIu64 " (%s) : %s", chan->id, source, str);
|
||||||
xfree(str);
|
xfree(str);
|
||||||
api_free_dictionary(info);
|
arena_mem_free(arena_finish(&arena));
|
||||||
|
|
||||||
#else
|
#else
|
||||||
(void)ext_source;
|
(void)ext_source;
|
||||||
@@ -876,7 +877,8 @@ static void set_info_event(void **argv)
|
|||||||
|
|
||||||
save_v_event_T save_v_event;
|
save_v_event_T save_v_event;
|
||||||
dict_T *dict = get_v_event(&save_v_event);
|
dict_T *dict = get_v_event(&save_v_event);
|
||||||
Dictionary info = channel_info(chan->id);
|
Arena arena = ARENA_EMPTY;
|
||||||
|
Dictionary info = channel_info(chan->id, &arena);
|
||||||
typval_T retval;
|
typval_T retval;
|
||||||
object_to_vim(DICTIONARY_OBJ(info), &retval, NULL);
|
object_to_vim(DICTIONARY_OBJ(info), &retval, NULL);
|
||||||
assert(retval.v_type == VAR_DICT);
|
assert(retval.v_type == VAR_DICT);
|
||||||
@@ -886,7 +888,7 @@ static void set_info_event(void **argv)
|
|||||||
apply_autocmds(event, NULL, NULL, false, curbuf);
|
apply_autocmds(event, NULL, NULL, false, curbuf);
|
||||||
|
|
||||||
restore_v_event(dict, &save_v_event);
|
restore_v_event(dict, &save_v_event);
|
||||||
api_free_dictionary(info);
|
arena_mem_free(arena_finish(&arena));
|
||||||
channel_decref(chan);
|
channel_decref(chan);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -898,15 +900,15 @@ bool channel_job_running(uint64_t id)
|
|||||||
&& !process_is_stopped(&chan->stream.proc));
|
&& !process_is_stopped(&chan->stream.proc));
|
||||||
}
|
}
|
||||||
|
|
||||||
Dictionary channel_info(uint64_t id)
|
Dictionary channel_info(uint64_t id, Arena *arena)
|
||||||
{
|
{
|
||||||
Channel *chan = find_channel(id);
|
Channel *chan = find_channel(id);
|
||||||
if (!chan) {
|
if (!chan) {
|
||||||
return (Dictionary)ARRAY_DICT_INIT;
|
return (Dictionary)ARRAY_DICT_INIT;
|
||||||
}
|
}
|
||||||
|
|
||||||
Dictionary info = ARRAY_DICT_INIT;
|
Dictionary info = arena_dict(arena, 8);
|
||||||
PUT(info, "id", INTEGER_OBJ((Integer)chan->id));
|
PUT_C(info, "id", INTEGER_OBJ((Integer)chan->id));
|
||||||
|
|
||||||
const char *stream_desc, *mode_desc;
|
const char *stream_desc, *mode_desc;
|
||||||
switch (chan->streamtype) {
|
switch (chan->streamtype) {
|
||||||
@@ -914,18 +916,20 @@ Dictionary channel_info(uint64_t id)
|
|||||||
stream_desc = "job";
|
stream_desc = "job";
|
||||||
if (chan->stream.proc.type == kProcessTypePty) {
|
if (chan->stream.proc.type == kProcessTypePty) {
|
||||||
const char *name = pty_process_tty_name(&chan->stream.pty);
|
const char *name = pty_process_tty_name(&chan->stream.pty);
|
||||||
PUT(info, "pty", CSTR_TO_OBJ(name));
|
PUT_C(info, "pty", CSTR_TO_ARENA_OBJ(arena, name));
|
||||||
}
|
}
|
||||||
|
|
||||||
char **p = chan->stream.proc.argv;
|
char **args = chan->stream.proc.argv;
|
||||||
Array argv = ARRAY_DICT_INIT;
|
Array argv = ARRAY_DICT_INIT;
|
||||||
if (p != NULL) {
|
if (args != NULL) {
|
||||||
while (*p != NULL) {
|
size_t n;
|
||||||
ADD(argv, CSTR_TO_OBJ(*p));
|
for (n = 0; args[n] != NULL; n++) {}
|
||||||
p++;
|
argv = arena_array(arena, n);
|
||||||
|
for (size_t i = 0; i < n; i++) {
|
||||||
|
ADD_C(argv, CSTR_AS_OBJ(args[i]));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
PUT(info, "argv", ARRAY_OBJ(argv));
|
PUT_C(info, "argv", ARRAY_OBJ(argv));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -938,25 +942,25 @@ Dictionary channel_info(uint64_t id)
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case kChannelStreamInternal:
|
case kChannelStreamInternal:
|
||||||
PUT(info, "internal", BOOLEAN_OBJ(true));
|
PUT_C(info, "internal", BOOLEAN_OBJ(true));
|
||||||
FALLTHROUGH;
|
FALLTHROUGH;
|
||||||
|
|
||||||
case kChannelStreamSocket:
|
case kChannelStreamSocket:
|
||||||
stream_desc = "socket";
|
stream_desc = "socket";
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
PUT(info, "stream", CSTR_TO_OBJ(stream_desc));
|
PUT_C(info, "stream", CSTR_AS_OBJ(stream_desc));
|
||||||
|
|
||||||
if (chan->is_rpc) {
|
if (chan->is_rpc) {
|
||||||
mode_desc = "rpc";
|
mode_desc = "rpc";
|
||||||
PUT(info, "client", DICTIONARY_OBJ(rpc_client_info(chan)));
|
PUT_C(info, "client", DICTIONARY_OBJ(chan->rpc.info));
|
||||||
} else if (chan->term) {
|
} else if (chan->term) {
|
||||||
mode_desc = "terminal";
|
mode_desc = "terminal";
|
||||||
PUT(info, "buffer", BUFFER_OBJ(terminal_buf(chan->term)));
|
PUT_C(info, "buffer", BUFFER_OBJ(terminal_buf(chan->term)));
|
||||||
} else {
|
} else {
|
||||||
mode_desc = "bytes";
|
mode_desc = "bytes";
|
||||||
}
|
}
|
||||||
PUT(info, "mode", CSTR_TO_OBJ(mode_desc));
|
PUT_C(info, "mode", CSTR_AS_OBJ(mode_desc));
|
||||||
|
|
||||||
return info;
|
return info;
|
||||||
}
|
}
|
||||||
@@ -969,21 +973,20 @@ static int int64_t_cmp(const void *pa, const void *pb)
|
|||||||
return a == b ? 0 : a > b ? 1 : -1;
|
return a == b ? 0 : a > b ? 1 : -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
Array channel_all_info(void)
|
Array channel_all_info(Arena *arena)
|
||||||
{
|
{
|
||||||
// order the items in the array by channel number, for Determinism™
|
// order the items in the array by channel number, for Determinism™
|
||||||
kvec_t(int64_t) ids = KV_INITIAL_VALUE;
|
kvec_t(int64_t) ids = KV_INITIAL_VALUE;
|
||||||
kv_resize(ids, map_size(&channels));
|
kv_fixsize_arena(arena, ids, map_size(&channels));
|
||||||
uint64_t id;
|
uint64_t id;
|
||||||
map_foreach_key(&channels, id, {
|
map_foreach_key(&channels, id, {
|
||||||
kv_push(ids, (int64_t)id);
|
kv_push(ids, (int64_t)id);
|
||||||
});
|
});
|
||||||
qsort(ids.items, ids.size, sizeof ids.items[0], int64_t_cmp);
|
qsort(ids.items, ids.size, sizeof ids.items[0], int64_t_cmp);
|
||||||
|
|
||||||
Array ret = ARRAY_DICT_INIT;
|
Array ret = arena_array(arena, ids.size);
|
||||||
for (size_t i = 0; i < ids.size; i++) {
|
for (size_t i = 0; i < ids.size; i++) {
|
||||||
ADD(ret, DICTIONARY_OBJ(channel_info((uint64_t)ids.items[i])));
|
ADD_C(ret, DICTIONARY_OBJ(channel_info((uint64_t)ids.items[i], arena)));
|
||||||
}
|
}
|
||||||
kv_destroy(ids);
|
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
@@ -947,10 +947,10 @@ static void remote_request(mparm_T *params, int remote_args, char *server_addr,
|
|||||||
|
|
||||||
Error err = ERROR_INIT;
|
Error err = ERROR_INIT;
|
||||||
MAXSIZE_TEMP_ARRAY(a, 4);
|
MAXSIZE_TEMP_ARRAY(a, 4);
|
||||||
ADD(a, INTEGER_OBJ((int)chan));
|
ADD_C(a, INTEGER_OBJ((int)chan));
|
||||||
ADD(a, CSTR_AS_OBJ(server_addr));
|
ADD_C(a, CSTR_AS_OBJ(server_addr));
|
||||||
ADD(a, CSTR_AS_OBJ(connect_error));
|
ADD_C(a, CSTR_AS_OBJ(connect_error));
|
||||||
ADD(a, ARRAY_OBJ(args));
|
ADD_C(a, ARRAY_OBJ(args));
|
||||||
String s = STATIC_CSTR_AS_STRING("return vim._cs_remote(...)");
|
String s = STATIC_CSTR_AS_STRING("return vim._cs_remote(...)");
|
||||||
Object o = nlua_exec(s, a, kRetObject, NULL, &err);
|
Object o = nlua_exec(s, a, kRetObject, NULL, &err);
|
||||||
kv_destroy(args);
|
kv_destroy(args);
|
||||||
|
@@ -682,12 +682,11 @@ static WBuffer *serialize_response(uint64_t channel_id, MsgpackRpcRequestHandler
|
|||||||
semsg("paste: %s", err->msg);
|
semsg("paste: %s", err->msg);
|
||||||
api_clear_error(err);
|
api_clear_error(err);
|
||||||
} else {
|
} else {
|
||||||
Array args = ARRAY_DICT_INIT;
|
MAXSIZE_TEMP_ARRAY(args, 2);
|
||||||
ADD(args, INTEGER_OBJ(err->type));
|
ADD_C(args, INTEGER_OBJ(err->type));
|
||||||
ADD(args, CSTR_TO_OBJ(err->msg));
|
ADD_C(args, CSTR_AS_OBJ(err->msg));
|
||||||
msgpack_rpc_serialize_request(0, cstr_as_string("nvim_error_event"),
|
msgpack_rpc_serialize_request(0, cstr_as_string("nvim_error_event"),
|
||||||
args, &pac);
|
args, &pac);
|
||||||
api_free_array(args);
|
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
msgpack_rpc_serialize_response(response_id, err, arg, &pac);
|
msgpack_rpc_serialize_response(response_id, err, arg, &pac);
|
||||||
|
@@ -230,7 +230,7 @@ int os_proc_children(int ppid, int **proc_list, size_t *proc_count)
|
|||||||
///
|
///
|
||||||
/// @param pid Process to inspect.
|
/// @param pid Process to inspect.
|
||||||
/// @return Map of process properties, empty on error.
|
/// @return Map of process properties, empty on error.
|
||||||
Dictionary os_proc_info(int pid)
|
Dictionary os_proc_info(int pid, Arena *arena)
|
||||||
{
|
{
|
||||||
Dictionary pinfo = ARRAY_DICT_INIT;
|
Dictionary pinfo = ARRAY_DICT_INIT;
|
||||||
PROCESSENTRY32 pe;
|
PROCESSENTRY32 pe;
|
||||||
@@ -258,9 +258,10 @@ Dictionary os_proc_info(int pid)
|
|||||||
CloseHandle(h);
|
CloseHandle(h);
|
||||||
|
|
||||||
if (pe.th32ProcessID == (DWORD)pid) {
|
if (pe.th32ProcessID == (DWORD)pid) {
|
||||||
PUT(pinfo, "pid", INTEGER_OBJ(pid));
|
pinfo = arena_dict(arena, 3);
|
||||||
PUT(pinfo, "ppid", INTEGER_OBJ((int)pe.th32ParentProcessID));
|
PUT_C(pinfo, "pid", INTEGER_OBJ(pid));
|
||||||
PUT(pinfo, "name", CSTR_TO_OBJ(pe.szExeFile));
|
PUT_C(pinfo, "ppid", INTEGER_OBJ((int)pe.th32ParentProcessID));
|
||||||
|
PUT_C(pinfo, "name", CSTR_TO_ARENA_OBJ(arena, pe.szExeFile));
|
||||||
}
|
}
|
||||||
|
|
||||||
return pinfo;
|
return pinfo;
|
||||||
|
@@ -1434,28 +1434,28 @@ static void show_verbose_terminfo(TUIData *tui)
|
|||||||
abort();
|
abort();
|
||||||
}
|
}
|
||||||
|
|
||||||
Array chunks = ARRAY_DICT_INIT;
|
MAXSIZE_TEMP_ARRAY(chunks, 3);
|
||||||
Array title = ARRAY_DICT_INIT;
|
MAXSIZE_TEMP_ARRAY(title, 2);
|
||||||
ADD(title, CSTR_TO_OBJ("\n\n--- Terminal info --- {{{\n"));
|
ADD_C(title, CSTR_AS_OBJ("\n\n--- Terminal info --- {{{\n"));
|
||||||
ADD(title, CSTR_TO_OBJ("Title"));
|
ADD_C(title, CSTR_AS_OBJ("Title"));
|
||||||
ADD(chunks, ARRAY_OBJ(title));
|
ADD_C(chunks, ARRAY_OBJ(title));
|
||||||
Array info = ARRAY_DICT_INIT;
|
MAXSIZE_TEMP_ARRAY(info, 2);
|
||||||
String str = terminfo_info_msg(ut, tui->term);
|
String str = terminfo_info_msg(ut, tui->term);
|
||||||
ADD(info, STRING_OBJ(str));
|
ADD_C(info, STRING_OBJ(str));
|
||||||
ADD(chunks, ARRAY_OBJ(info));
|
ADD_C(chunks, ARRAY_OBJ(info));
|
||||||
Array end_fold = ARRAY_DICT_INIT;
|
MAXSIZE_TEMP_ARRAY(end_fold, 2);
|
||||||
ADD(end_fold, CSTR_TO_OBJ("}}}\n"));
|
ADD_C(end_fold, CSTR_AS_OBJ("}}}\n"));
|
||||||
ADD(end_fold, CSTR_TO_OBJ("Title"));
|
ADD_C(end_fold, CSTR_AS_OBJ("Title"));
|
||||||
ADD(chunks, ARRAY_OBJ(end_fold));
|
ADD_C(chunks, ARRAY_OBJ(end_fold));
|
||||||
|
|
||||||
Array args = ARRAY_DICT_INIT;
|
MAXSIZE_TEMP_ARRAY(args, 3);
|
||||||
ADD(args, ARRAY_OBJ(chunks));
|
ADD_C(args, ARRAY_OBJ(chunks));
|
||||||
ADD(args, BOOLEAN_OBJ(true)); // history
|
ADD_C(args, BOOLEAN_OBJ(true)); // history
|
||||||
Dictionary opts = ARRAY_DICT_INIT;
|
MAXSIZE_TEMP_DICT(opts, 1);
|
||||||
PUT(opts, "verbose", BOOLEAN_OBJ(true));
|
PUT_C(opts, "verbose", BOOLEAN_OBJ(true));
|
||||||
ADD(args, DICTIONARY_OBJ(opts));
|
ADD_C(args, DICTIONARY_OBJ(opts));
|
||||||
rpc_send_event(ui_client_channel_id, "nvim_echo", args);
|
rpc_send_event(ui_client_channel_id, "nvim_echo", args);
|
||||||
api_free_array(args);
|
xfree(str.data);
|
||||||
}
|
}
|
||||||
|
|
||||||
void tui_suspend(TUIData *tui)
|
void tui_suspend(TUIData *tui)
|
||||||
|
Reference in New Issue
Block a user