Packages
membrane_rtmp_plugin
0.14.0
0.29.5
0.29.4
0.29.3
0.29.2
0.29.1
0.29.0
0.28.1
0.28.0
0.27.3
0.27.2
0.27.0
0.26.0
0.25.0
0.24.0
0.23.3
0.23.2
0.23.1
0.23.0
0.22.1
0.22.0
0.21.0
0.20.2
0.20.1
0.20.0
0.19.3
0.19.2
retired
0.19.1
0.19.0
0.18.0
0.17.3
0.17.2
0.17.1
0.17.0
0.16.0
0.15.0
0.14.0
0.13.2
0.13.1
0.13.0
0.12.1
0.12.0
0.11.3
0.11.2
0.11.1
0.11.0
0.10.0
0.9.1
0.9.0
0.8.1
0.8.0
0.7.0
0.6.1
0.6.0
0.5.0
0.4.1
0.4.0
0.3.0
0.2.1
0.2.0
0.1.1
0.1.0
RTMP Plugin for Membrane Multimedia Framework
Current section
Files
Jump to
Current section
Files
lib/membrane_rtmp_plugin/rtmp/source/ssl_server.ex
defmodule Membrane.RTMP.Source.SslServer do
@moduledoc """
A simple ssl server, which handles each new incoming connection.
The `socket_handler` function passed inside the options should take the socket returned by `:ssl.handshake/1`
and return `{:ok, pid}`, where the `pid` describes a process, which will be interacting with the socket.
`#{inspect(__MODULE__)}` will grant that process control over the socket via `:ssl.controlling_process/2`.
"""
use Task
@enforce_keys [
:port,
:listen_options,
:socket_handler
]
defstruct @enforce_keys ++ [:parent]
@typedoc """
Defines options for the SSL server.
The `listen_options` are passed to the `:ssl.listen/2` function.
The `socket_handler` is a function that takes socket returned by `:gen_tcp.accept/1` and returns the pid of a process,
which will be interacting with the socket. SslServer will grant that process control over the socket via `:ssl.controlling_process/2`.
"""
@type t :: %__MODULE__{
port: :inet.port_number(),
listen_options: [:inet.inet_backend() | :ssl.tls_server_option()],
socket_handler: (:ssl.sslsocket() -> {:ok, pid} | {:error, reason :: any()}),
parent: pid()
}
@spec start_link(t()) :: {:ok, pid}
def start_link(options) do
Task.start_link(__MODULE__, :run, [options])
end
@spec run(t()) :: nil
def run(options) do
{:ok, socket} = :ssl.listen(options.port, options.listen_options)
if options.parent, do: send(options.parent, {:ssl_server_started, socket})
accept_loop(socket, options.socket_handler)
end
defp accept_loop(socket, socket_handler) do
{:ok, ssl_socket} = :ssl.transport_accept(socket)
{:ok, ssl_socket} = :ssl.handshake(ssl_socket)
{:ok, pid} = socket_handler.(ssl_socket)
:ok = :ssl.controlling_process(ssl_socket, pid)
# send(pid, :granted_control)
accept_loop(socket, socket_handler)
end
end