Prepare UDP "connection" handling

This commit is contained in:
Baptiste Wicht 2016-09-18 11:04:24 +02:00
parent e6d5dd2b71
commit 900b6d3e46
8 changed files with 39 additions and 14 deletions

View File

@ -113,7 +113,7 @@ std::expected<void> listen(socket_fd_t socket_fd, bool listen);
* \param socket_fd The file descriptor of the packet * \param socket_fd The file descriptor of the packet
* \return the allocated port on success and a negative error code otherwise * \return the allocated port on success and a negative error code otherwise
*/ */
std::expected<size_t> client_bind(socket_fd_t socket_fd); std::expected<size_t> client_bind(socket_fd_t socket_fd, network::ip::address address);
/*! /*!
* \brief Bind a socket stream as a client (bind a local random port) * \brief Bind a socket stream as a client (bind a local random port)

View File

@ -31,6 +31,9 @@ std::expected<network::ethernet::packet> kernel_prepare_packet(network::interfac
std::expected<network::ethernet::packet> user_prepare_packet(char* buffer, network::interface_descriptor& interface, const packet_descriptor* descriptor); std::expected<network::ethernet::packet> user_prepare_packet(char* buffer, network::interface_descriptor& interface, const packet_descriptor* descriptor);
std::expected<void> finalize_packet(network::interface_descriptor& interface, network::ethernet::packet& p); std::expected<void> finalize_packet(network::interface_descriptor& interface, network::ethernet::packet& p);
std::expected<void> client_bind(network::socket& socket, network::interface_descriptor& interface, size_t local_port, size_t server_port, network::ip::address server);
std::expected<void> client_unbind(network::socket& socket);
} // end of upd namespace } // end of upd namespace
} // end of network namespace } // end of network namespace

View File

@ -378,7 +378,7 @@ std::expected<void> network::listen(socket_fd_t socket_fd, bool listen){
return std::make_expected(); return std::make_expected();
} }
std::expected<size_t> network::client_bind(socket_fd_t socket_fd){ std::expected<size_t> network::client_bind(socket_fd_t socket_fd, network::ip::address address){
if(!scheduler::has_socket(socket_fd)){ if(!scheduler::has_socket(socket_fd)){
return std::make_unexpected<size_t>(std::ERROR_SOCKET_INVALID_FD); return std::make_unexpected<size_t>(std::ERROR_SOCKET_INVALID_FD);
} }
@ -389,9 +389,21 @@ std::expected<size_t> network::client_bind(socket_fd_t socket_fd){
return std::make_unexpected<size_t>(std::ERROR_SOCKET_INVALID_TYPE); return std::make_unexpected<size_t>(std::ERROR_SOCKET_INVALID_TYPE);
} }
socket.local_port = local_port++; auto selected_port = local_port++;
logging::logf(logging::log_level::TRACE, "network: %u datagram socket %u was assigned port %u\n", scheduler::get_pid(), socket_fd, socket.local_port); logging::logf(logging::log_level::TRACE, "network: %u datagram socket %u was assigned port %u\n", scheduler::get_pid(), socket_fd, selected_port);
//TODO extract the underlying protocol (UDP)
//TODO Get the port from a function
if(socket.protocol == socket_protocol::DNS){
auto connection = network::udp::client_bind(socket, select_interface(address), selected_port, 53, address);
if(!connection){
return std::make_unexpected<size_t>(connection.error());
}
} else {
return std::make_unexpected<size_t>(std::ERROR_SOCKET_INVALID_TYPE_PROTOCOL);
}
return std::make_expected<size_t>(socket.local_port); return std::make_expected<size_t>(socket.local_port);
} }
@ -409,7 +421,7 @@ std::expected<size_t> network::connect(socket_fd_t socket_fd, network::ip::addre
auto selected_port = local_port++; auto selected_port = local_port++;
logging::logf(logging::log_level::TRACE, "network: %u stream socket %u was assigned port %u\n", scheduler::get_pid(), socket_fd, socket.local_port); logging::logf(logging::log_level::TRACE, "network: %u stream socket %u was assigned port %u\n", scheduler::get_pid(), socket_fd, selected_port);
if(socket.protocol == socket_protocol::TCP){ if(socket.protocol == socket_protocol::TCP){
auto connection = network::tcp::connect(socket, select_interface(server), selected_port, port, server); auto connection = network::tcp::connect(socket, select_interface(server), selected_port, port, server);

View File

@ -108,3 +108,11 @@ std::expected<void> network::udp::finalize_packet(network::interface_descriptor&
// Give the packet to the IP layer for finalization // Give the packet to the IP layer for finalization
return network::ip::finalize_packet(interface, p); return network::ip::finalize_packet(interface, p);
} }
std::expected<void> network::udp::client_bind(network::socket& socket, network::interface_descriptor& interface, size_t local_port, size_t server_port, network::ip::address server){
}
std::expected<void> network::udp::client_unbind(network::socket& socket){
}

View File

@ -419,8 +419,9 @@ void sc_listen(interrupt::syscall_regs* regs){
void sc_client_bind(interrupt::syscall_regs* regs){ void sc_client_bind(interrupt::syscall_regs* regs){
auto socket_fd = regs->rbx; auto socket_fd = regs->rbx;
auto server_ip = regs->rcx;
auto status = network::client_bind(socket_fd); auto status = network::client_bind(socket_fd, server_ip);
regs->rax = expected_to_i64(status); regs->rax = expected_to_i64(status);
} }

View File

@ -41,7 +41,7 @@ void socket_close(size_t socket_fd);
std::expected<packet> prepare_packet(size_t socket_fd, void* desc); std::expected<packet> prepare_packet(size_t socket_fd, void* desc);
std::expected<void> finalize_packet(size_t socket_fd, const packet& p); std::expected<void> finalize_packet(size_t socket_fd, const packet& p);
std::expected<void> listen(size_t socket_fd, bool l); std::expected<void> listen(size_t socket_fd, bool l);
std::expected<size_t> client_bind(size_t socket_fd); std::expected<size_t> client_bind(size_t socket_fd, tlib::ip::address server);
std::expected<size_t> connect(size_t socket_fd, tlib::ip::address server, size_t port); std::expected<size_t> connect(size_t socket_fd, tlib::ip::address server, size_t port);
std::expected<void> disconnect(size_t socket_fd); std::expected<void> disconnect(size_t socket_fd);
std::expected<packet> wait_for_packet(size_t socket_fd); std::expected<packet> wait_for_packet(size_t socket_fd);
@ -88,8 +88,9 @@ struct socket {
/*! /*!
* \brief Bind the socket as a client * \brief Bind the socket as a client
* \param server The IP address
*/ */
void client_bind(); void client_bind(tlib::ip::address server);
void connect(tlib::ip::address server, size_t port); void connect(tlib::ip::address server, size_t port);
void disconnect(); void disconnect();

View File

@ -90,7 +90,7 @@ std::expected<void> tlib::dns::send_request(tlib::socket& sock, const std::strin
std::expected<std::string> tlib::dns::resolve(const std::string& domain, size_t timeout_ms, size_t retries){ std::expected<std::string> tlib::dns::resolve(const std::string& domain, size_t timeout_ms, size_t retries){
tlib::socket sock(tlib::socket_domain::AF_INET, tlib::socket_type::DGRAM, tlib::socket_protocol::DNS); tlib::socket sock(tlib::socket_domain::AF_INET, tlib::socket_type::DGRAM, tlib::socket_protocol::DNS);
sock.client_bind(); sock.client_bind(gateway_address());
sock.listen(true); sock.listen(true);
if (!sock) { if (!sock) {

View File

@ -109,11 +109,11 @@ std::expected<void> tlib::listen(size_t socket_fd, bool l) {
} }
} }
std::expected<size_t> tlib::client_bind(size_t socket_fd) { std::expected<size_t> tlib::client_bind(size_t socket_fd, tlib::ip::address server) {
int64_t code; int64_t code;
asm volatile("mov rax, 0x3007; mov rbx, %[socket]; int 50; mov %[code], rax" asm volatile("mov rax, 0x3007; mov rbx, %[socket]; mov rcx, %[ip]; int 50; mov %[code], rax"
: [code] "=m"(code) : [code] "=m"(code)
: [socket] "g"(socket_fd) : [socket] "g"(socket_fd), [ip] "g" (size_t(server.raw_address))
: "rax", "rbx", "rcx"); : "rax", "rbx", "rcx");
if (code < 0) { if (code < 0) {
@ -251,12 +251,12 @@ void tlib::socket::listen(bool l) {
} }
} }
void tlib::socket::client_bind() { void tlib::socket::client_bind(tlib::ip::address server) {
if (!good() || !open()) { if (!good() || !open()) {
return; return;
} }
auto status = tlib::client_bind(fd); auto status = tlib::client_bind(fd, server);
if (!status) { if (!status) {
error_code = status.error(); error_code = status.error();
} }