Support the +line syntax for clients as well.
Fix a crash on daemon quit as well.
This commit is contained in:
parent
c6a7924b80
commit
e8ee8c23d8
|
@ -22,8 +22,10 @@ void ClientManager::clear()
|
|||
// So that clients destructor find the client manager empty
|
||||
// so that local UI does not fork.
|
||||
ClientList clients = std::move(m_clients);
|
||||
clients.clear();
|
||||
m_client_trash.clear();
|
||||
m_free_windows.clear();
|
||||
m_window_trash.clear();
|
||||
}
|
||||
|
||||
String ClientManager::generate_name() const
|
||||
|
|
54
src/main.cc
54
src/main.cc
|
@ -454,12 +454,13 @@ void signal_handler(int signal)
|
|||
abort();
|
||||
}
|
||||
|
||||
int run_client(StringView session, StringView init_cmds, UIType ui_type)
|
||||
int run_client(StringView session, StringView init_cmds,
|
||||
Optional<BufferCoord> init_coord, UIType ui_type)
|
||||
{
|
||||
try
|
||||
{
|
||||
EventManager event_manager;
|
||||
RemoteClient client{session, make_ui(ui_type), get_env_vars(), init_cmds};
|
||||
RemoteClient client{session, make_ui(ui_type), get_env_vars(), init_cmds, init_coord};
|
||||
while (true)
|
||||
event_manager.handle_next_events(EventMode::Normal);
|
||||
}
|
||||
|
@ -473,7 +474,7 @@ int run_client(StringView session, StringView init_cmds, UIType ui_type)
|
|||
}
|
||||
|
||||
int run_server(StringView session,
|
||||
StringView init_cmds, BufferCoord init_coord,
|
||||
StringView init_cmds, Optional<BufferCoord> init_coord,
|
||||
bool ignore_kakrc, bool daemon, bool readonly, UIType ui_type,
|
||||
ConstArrayView<StringView> files)
|
||||
{
|
||||
|
@ -812,6 +813,28 @@ int main(int argc, char* argv[])
|
|||
(bool)parser.get_switch("q"));
|
||||
}
|
||||
|
||||
Vector<StringView> files;
|
||||
Optional<BufferCoord> init_coord;
|
||||
for (auto& name : parser)
|
||||
{
|
||||
if (not name.empty() and name[0_byte] == '+')
|
||||
{
|
||||
auto colon = find(name, ':');
|
||||
if (auto line = str_to_int_ifp({name.begin()+1, colon}))
|
||||
{
|
||||
init_coord = BufferCoord{
|
||||
*line - 1,
|
||||
colon != name.end() ?
|
||||
str_to_int_ifp({colon+1, name.end()}).value_or(1) - 1
|
||||
: 0
|
||||
};
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
files.emplace_back(name);
|
||||
}
|
||||
|
||||
if (auto server_session = parser.get_switch("c"))
|
||||
{
|
||||
for (auto opt : { "n", "s", "d", "ro" })
|
||||
|
@ -823,32 +846,13 @@ int main(int argc, char* argv[])
|
|||
}
|
||||
}
|
||||
String new_files;
|
||||
for (auto name : parser)
|
||||
for (auto name : files)
|
||||
new_files += format("edit '{}';", escape(real_path(name), "'", '\\'));
|
||||
|
||||
return run_client(*server_session, new_files + init_cmds, ui_type);
|
||||
return run_client(*server_session, new_files + init_cmds, init_coord, ui_type);
|
||||
}
|
||||
else
|
||||
{
|
||||
BufferCoord init_coord;
|
||||
Vector<StringView> files;
|
||||
for (auto& name : parser)
|
||||
{
|
||||
if (not name.empty() and name[0_byte] == '+')
|
||||
{
|
||||
auto colon = find(name, ':');
|
||||
if (auto line = str_to_int_ifp({name.begin()+1, colon}))
|
||||
{
|
||||
init_coord.line = *line - 1;
|
||||
if (colon != name.end())
|
||||
init_coord.column = str_to_int_ifp({colon+1, name.end()}).value_or(1) - 1;
|
||||
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
files.emplace_back(name);
|
||||
}
|
||||
|
||||
StringView session = parser.get_switch("s").value_or(StringView{});
|
||||
try
|
||||
|
@ -864,7 +868,7 @@ int main(int argc, char* argv[])
|
|||
raise(SIGTSTP);
|
||||
return run_client(convert.session,
|
||||
format("try %^buffer '{}'; select '{}'^; echo converted to client only mode",
|
||||
escape(convert.buffer_name, "'^", '\\'), convert.selections), ui_type);
|
||||
escape(convert.buffer_name, "'^", '\\'), convert.selections), {}, ui_type);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -8,6 +8,7 @@
|
|||
#include "event_manager.hh"
|
||||
#include "file.hh"
|
||||
#include "id_map.hh"
|
||||
#include "optional.hh"
|
||||
#include "user_interface.hh"
|
||||
|
||||
#include <sys/types.h>
|
||||
|
@ -102,6 +103,14 @@ public:
|
|||
}
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
void write(const Optional<T>& val)
|
||||
{
|
||||
write((bool)val);
|
||||
if (val)
|
||||
write(*val);
|
||||
}
|
||||
|
||||
void write(Color color)
|
||||
{
|
||||
write(color.color);
|
||||
|
@ -219,6 +228,14 @@ public:
|
|||
return res;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
Optional<T> read_optional()
|
||||
{
|
||||
if (not read<bool>())
|
||||
return {};
|
||||
return read<T>();
|
||||
}
|
||||
|
||||
void reset()
|
||||
{
|
||||
m_stream.resize(0);
|
||||
|
@ -511,7 +528,8 @@ bool check_session(StringView session)
|
|||
}
|
||||
|
||||
RemoteClient::RemoteClient(StringView session, std::unique_ptr<UserInterface>&& ui,
|
||||
const EnvVarMap& env_vars, StringView init_command)
|
||||
const EnvVarMap& env_vars, StringView init_command,
|
||||
Optional<BufferCoord> init_coord)
|
||||
: m_ui(std::move(ui))
|
||||
{
|
||||
int sock = connect_to(session);
|
||||
|
@ -519,6 +537,7 @@ RemoteClient::RemoteClient(StringView session, std::unique_ptr<UserInterface>&&
|
|||
{
|
||||
MsgWriter msg{m_send_buffer, MessageType::Connect};
|
||||
msg.write(init_command);
|
||||
msg.write(init_coord);
|
||||
msg.write(m_ui->dimensions());
|
||||
msg.write(env_vars);
|
||||
}
|
||||
|
@ -652,12 +671,13 @@ private:
|
|||
case MessageType::Connect:
|
||||
{
|
||||
auto init_cmds = m_reader.read<String>();
|
||||
auto init_coord = m_reader.read_optional<BufferCoord>();
|
||||
auto dimensions = m_reader.read<DisplayCoord>();
|
||||
auto env_vars = m_reader.read_idmap<String, MemoryDomain::EnvVars>();
|
||||
auto* ui = new RemoteUI{sock, dimensions};
|
||||
if (auto* client = ClientManager::instance().create_client(
|
||||
std::unique_ptr<UserInterface>(ui),
|
||||
std::move(env_vars), init_cmds, {}))
|
||||
std::move(env_vars), init_cmds, init_coord))
|
||||
ui->set_client(client);
|
||||
|
||||
Server::instance().remove_accepter(this);
|
||||
|
|
|
@ -22,6 +22,9 @@ struct disconnected : runtime_error
|
|||
class FDWatcher;
|
||||
class UserInterface;
|
||||
|
||||
template<typename T> struct Optional;
|
||||
struct BufferCoord;
|
||||
|
||||
using RemoteBuffer = Vector<char, MemoryDomain::Remote>;
|
||||
|
||||
// A remote client handle communication between a client running on the server
|
||||
|
@ -30,7 +33,8 @@ class RemoteClient
|
|||
{
|
||||
public:
|
||||
RemoteClient(StringView session, std::unique_ptr<UserInterface>&& ui,
|
||||
const EnvVarMap& env_vars, StringView init_command);
|
||||
const EnvVarMap& env_vars, StringView init_command,
|
||||
Optional<BufferCoord> init_coord);
|
||||
|
||||
private:
|
||||
std::unique_ptr<UserInterface> m_ui;
|
||||
|
|
Loading…
Reference in New Issue
Block a user