/* * Copyright 2021 Google LLC * SPDX-License-Identifier: MIT */ #include "proxy_client.h" #include #include "server/render_protocol.h" #include "proxy_server.h" bool proxy_client_destroy_context(struct proxy_client *client, uint32_t ctx_id) { const struct render_client_op_destroy_context_request req = { .header.op = RENDER_CLIENT_OP_DESTROY_CONTEXT, .ctx_id = ctx_id, }; return proxy_socket_send_request(&client->socket, &req, sizeof(req)); } bool proxy_client_create_context(struct proxy_client *client, uint32_t ctx_id, size_t ctx_name_len, const char *ctx_name, int *out_ctx_fd) { struct render_client_op_create_context_request req = { .header.op = RENDER_CLIENT_OP_CREATE_CONTEXT, .ctx_id = ctx_id, }; const size_t len = MIN2(ctx_name_len, sizeof(req.ctx_name) - 1); memcpy(req.ctx_name, ctx_name, len); if (!proxy_socket_send_request(&client->socket, &req, sizeof(req))) return false; struct render_client_op_create_context_reply reply; int fd_count; int ctx_fd; if (!proxy_socket_receive_reply_with_fds(&client->socket, &reply, sizeof(reply), &ctx_fd, 1, &fd_count)) return false; if (reply.ok != fd_count) { if (fd_count) close(ctx_fd); return false; } else if (!reply.ok) { return false; } if (!proxy_socket_is_seqpacket(ctx_fd)) { close(ctx_fd); return false; } *out_ctx_fd = ctx_fd; return true; } bool proxy_client_reset(struct proxy_client *client) { const struct render_client_op_reset_request req = { .header.op = RENDER_CLIENT_OP_RESET, }; return proxy_socket_send_request(&client->socket, &req, sizeof(req)); } void proxy_client_destroy(struct proxy_client *client) { proxy_socket_fini(&client->socket); free(client); } static bool proxy_client_init(struct proxy_client *client, uint32_t flags) { const struct render_client_op_init_request req = { .header.op = RENDER_CLIENT_OP_INIT, .flags = flags, }; return proxy_socket_send_request(&client->socket, &req, sizeof(req)); } struct proxy_client * proxy_client_create(struct proxy_server *srv, uint32_t flags) { struct proxy_client *client = calloc(1, sizeof(*client)); if (!client) return NULL; const int client_fd = proxy_server_connect(srv); if (client_fd < 0) { free(client); return NULL; } proxy_socket_init(&client->socket, client_fd); if (!proxy_client_init(client, flags)) { proxy_socket_fini(&client->socket); free(client); return NULL; } return client; }