libcoap_rs/event.rs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189
// SPDX-License-Identifier: BSD-2-Clause
/*
* Copyright © The libcoap-rs Contributors, all rights reserved.
* This file is part of the libcoap-rs project, see the README file for
* general information on this project and the NOTICE.md and LICENSE files
* for information regarding copyright ownership and terms of use.
*
* event.rs - Event handling traits and logic for the libcoap Rust wrapper.
*/
//! Event handling-related code
use std::fmt::Debug;
use libcoap_sys::{
coap_event_t, coap_event_t_COAP_EVENT_SERVER_SESSION_NEW, coap_event_t_COAP_EVENT_TCP_CONNECTED,
coap_session_get_context, coap_session_get_type, coap_session_t, coap_session_type_t_COAP_SESSION_TYPE_SERVER,
};
use crate::{
context::CoapContext,
session::{CoapServerSession, CoapSession},
};
/// Trait for CoAP event handlers.
///
/// Implementations of this trait can be provided to a [CoapContext] to handle various events relating
/// to sessions.
///
/// This is the equivalent to the [libcoap `coap_event_handler_t` type](https://libcoap.net/doc/reference/develop/group__events.html#ga5d57fba7df54eae6f8cb3a47a4cb3569).
pub trait CoapEventHandler: Debug {
/// Handle a DTLS connected event.
///
/// This event is triggered when a DTLS session switches to the connected state.
#[allow(unused_variables)]
fn handle_dtls_connected(&mut self, session: &mut CoapSession) {}
/// Handle a DTLS closed event.
///
/// This event is triggered when a DTLS session is closed.
#[allow(unused_variables)]
fn handle_dtls_closed(&mut self, session: &mut CoapSession) {}
/// Handle a DTLS renegotiation event.
///
/// This event is triggered when a DTLS renegotiation occurs.
#[allow(unused_variables)]
fn handle_dtls_renegotiate(&mut self, session: &mut CoapSession) {}
/// Handle a DTLS error event.
///
/// This event is triggered when a DTLS error occurs.
#[allow(unused_variables)]
fn handle_dtls_error(&mut self, session: &mut CoapSession) {}
/// Handle a TCP connected event.
///
/// This event is triggered when a new TCP connection is established.
#[allow(unused_variables)]
fn handle_tcp_connected(&mut self, session: &mut CoapSession) {}
/// Handle a TCP closed event.
///
/// This event is triggered when a new TCP connection is closed.
#[allow(unused_variables)]
fn handle_tcp_closed(&mut self, session: &mut CoapSession) {}
/// Handle a TCP failed event.
#[allow(unused_variables)]
fn handle_tcp_failed(&mut self, session: &mut CoapSession) {}
/// Handle a session connected event.
///
/// This event is triggered by CSM exchanges only when reliable protocols are used.
#[allow(unused_variables)]
fn handle_session_connected(&mut self, session: &mut CoapSession) {}
/// Handle a session closed event.
///
/// This event is triggered by CSM exchanges only when reliable protocols are used.
#[allow(unused_variables)]
fn handle_session_closed(&mut self, session: &mut CoapSession) {}
/// Handle a session failed event.
///
/// This event is triggered by CSM exchanges only when reliable protocols are used.
#[allow(unused_variables)]
fn handle_session_failed(&mut self, session: &mut CoapSession) {}
/// Handle a partially received message.
#[allow(unused_variables)]
fn handle_partial_block(&mut self, session: &mut CoapSession) {}
/// Handle a failure to transmit a block.
#[allow(unused_variables)]
fn handle_xmit_block_fail(&mut self, session: &mut CoapSession) {}
/// Handle the creation of a new server-side session.
///
/// This event is called inside the IO loop when a new server-side session is created.
#[allow(unused_variables)]
fn handle_server_session_new(&mut self, session: &mut CoapServerSession) {}
/// Handle the deletion of a server-side session.
///
/// This event is called inside of the IO loop when a server-side session is deleted.
/// This can happen for a number of reasons:
/// - The session has been idle for too long (see [CoapContext::session_timeout()] and
/// [CoapContext::set_session_timeout()])
/// - The maximum number of handshaking sessions is exceeded (see
/// [CoapContext::max_handshake_sessions()] and [CoapContext::set_max_handshake_sessions()])
/// - The maximum number of idle sessions is exceeded (see
/// [CoapContext::max_idle_sessions()] and [CoapContext::set_max_idle_sessions()])
#[allow(unused_variables)]
fn handle_server_session_del(&mut self, session: &mut CoapServerSession) {}
/// Handle the receival of a badly formatted packet.
///
/// Note that this only refers to packets that can't be parsed by libcoap, i.e. valid packets
/// that have some semantic issues and therefore can't be parsed into a request or response
/// object do not trigger this event.
#[allow(unused_variables)]
fn handle_bad_packet(&mut self, session: &mut CoapSession) {}
/// Handle a retransmission event.
#[allow(unused_variables)]
fn handle_msg_retransmitted(&mut self, session: &mut CoapSession) {}
/// Handle an OSCORE decryption failure event.
#[allow(unused_variables)]
fn handle_oscore_decryption_failure(&mut self, session: &mut CoapSession) {}
/// Handle an OSCORE not enabled event.
#[allow(unused_variables)]
fn handle_oscore_not_enabled(&mut self, session: &mut CoapSession) {}
/// Handle an OSCORE no protected payload provided event.
#[allow(unused_variables)]
fn handle_oscore_no_protected_payload(&mut self, session: &mut CoapSession) {}
/// Handle an OSCORE no security definition found event.
#[allow(unused_variables)]
fn handle_oscore_no_security(&mut self, session: &mut CoapSession) {}
/// Handle an OSCORE internal error.
#[allow(unused_variables)]
fn handle_oscore_internal_error(&mut self, session: &mut CoapSession) {}
/// Handle a decoding error when parsing OSCORE options.
#[allow(unused_variables)]
fn handle_oscore_decode_error(&mut self, session: &mut CoapSession) {}
/// Handle an oversized WebSocket packet event.
#[allow(unused_variables)]
fn handle_ws_packet_size(&mut self, session: &mut CoapSession) {}
/// Handle a WebSocket layer up event.
#[allow(unused_variables)]
fn handle_ws_connected(&mut self, session: &mut CoapSession) {}
/// Handle a WebSocket layer closed event.
#[allow(unused_variables)]
fn handle_ws_closed(&mut self, session: &mut CoapSession) {}
/// Handle a failure to perform a keepalive (no response to keepalive packet)
#[allow(unused_variables)]
fn handle_keepalive_failure(&mut self, session: &mut CoapSession) {}
}
// This should be fine as we don't provide this type to an FFI function, we only read from it.
#[allow(improper_ctypes_definitions)]
pub(crate) unsafe extern "C" fn event_handler_callback(raw_session: *mut coap_session_t, event: coap_event_t) -> i32 {
let raw_session_type = coap_session_get_type(raw_session);
let session: CoapSession = if event == coap_event_t_COAP_EVENT_SERVER_SESSION_NEW
|| (event == coap_event_t_COAP_EVENT_TCP_CONNECTED
&& raw_session_type == coap_session_type_t_COAP_SESSION_TYPE_SERVER)
{
CoapServerSession::initialize_raw(raw_session).into()
} else {
CoapSession::from_raw(raw_session)
};
// SAFETY: Pointer is always valid as long as there is no bug in libcoap.
let context = CoapContext::from_raw(coap_session_get_context(raw_session));
context.handle_event(session, event);
0
}