blob: e26308067a501521f7341441d3ddaa3775e39952 [file] [log] [blame]
Harald Weltec68af6a2017-04-30 21:21:52 +02001#ifndef _SERCOMM_H
2#define _SERCOMM_H
3
4#include <osmocom/core/msgb.h>
5
Harald Weltec68af6a2017-04-30 21:21:52 +02006/* a low sercomm_dlci means high priority. A high DLCI means low priority */
7enum sercomm_dlci {
8 SC_DLCI_HIGHEST = 0,
9 SC_DLCI_DEBUG = 4,
10 SC_DLCI_L1A_L23 = 5,
11 SC_DLCI_LOADER = 9,
12 SC_DLCI_CONSOLE = 10,
13 SC_DLCI_ECHO = 128,
14 _SC_DLCI_MAX
15};
16
Harald Welte13588362017-04-30 23:57:55 +020017struct osmo_sercomm_inst;
Harald Welteea3d3ba2017-05-02 21:24:48 +020018/*! \brief call-back function for per-DLC receive handler
19 * \param[in] sercomm instance on which msg was received
20 * \param[in] dlci DLC Identifier of received msg
21 * \param[in] msg received message that needs to be processed */
Harald Welte13588362017-04-30 23:57:55 +020022typedef void (*dlci_cb_t)(struct osmo_sercomm_inst *sercomm, uint8_t dlci, struct msgb *msg);
Harald Weltecc95f4b2017-04-30 21:39:33 +020023
Harald Welteea3d3ba2017-05-02 21:24:48 +020024/*! \brief one instance of a sercomm multiplex/demultiplex */
Harald Welte13588362017-04-30 23:57:55 +020025struct osmo_sercomm_inst {
Harald Welteea3d3ba2017-05-02 21:24:48 +020026 /*! \brief Has this instance been initialized? */
Harald Weltecc95f4b2017-04-30 21:39:33 +020027 int initialized;
Harald Welteea3d3ba2017-05-02 21:24:48 +020028 /*! \brief UART Identifier */
Harald Weltecc95f4b2017-04-30 21:39:33 +020029 int uart_id;
30
Harald Welteea3d3ba2017-05-02 21:24:48 +020031 /*! \brief transmit side */
Harald Weltecc95f4b2017-04-30 21:39:33 +020032 struct {
Harald Welteea3d3ba2017-05-02 21:24:48 +020033 /*! \brief per-DLC queue of pending transmit msgbs */
Harald Weltecc95f4b2017-04-30 21:39:33 +020034 struct llist_head dlci_queues[_SC_DLCI_MAX];
Harald Welteea3d3ba2017-05-02 21:24:48 +020035 /*! \brief msgb currently being transmitted */
Harald Weltecc95f4b2017-04-30 21:39:33 +020036 struct msgb *msg;
Harald Welteea3d3ba2017-05-02 21:24:48 +020037 /*! \brief transmit state */
Harald Weltecc95f4b2017-04-30 21:39:33 +020038 int state;
Harald Welteea3d3ba2017-05-02 21:24:48 +020039 /*! \brief next to-be-transmitted char in msg */
Harald Weltecc95f4b2017-04-30 21:39:33 +020040 uint8_t *next_char;
41 } tx;
42
Harald Welteea3d3ba2017-05-02 21:24:48 +020043 /*! \brief receive side */
Harald Weltecc95f4b2017-04-30 21:39:33 +020044 struct {
Harald Welteea3d3ba2017-05-02 21:24:48 +020045 /*! \brief per-DLC handler call-back functions */
Harald Weltecc95f4b2017-04-30 21:39:33 +020046 dlci_cb_t dlci_handler[_SC_DLCI_MAX];
Harald Welteea3d3ba2017-05-02 21:24:48 +020047 /*! \brief msgb allocation size for rx msgs */
Harald Weltef6adcd72017-05-01 00:19:13 +020048 unsigned int msg_size;
Harald Welteea3d3ba2017-05-02 21:24:48 +020049 /*! \brief currently received msgb */
Harald Weltecc95f4b2017-04-30 21:39:33 +020050 struct msgb *msg;
Harald Welteea3d3ba2017-05-02 21:24:48 +020051 /*! \brief receive state */
Harald Weltecc95f4b2017-04-30 21:39:33 +020052 int state;
Harald Welteea3d3ba2017-05-02 21:24:48 +020053 /*! \brief DLCI of currently received msgb */
Harald Weltecc95f4b2017-04-30 21:39:33 +020054 uint8_t dlci;
Harald Welteea3d3ba2017-05-02 21:24:48 +020055 /*! \brief CTRL of currently received msgb */
Harald Weltecc95f4b2017-04-30 21:39:33 +020056 uint8_t ctrl;
57 } rx;
58};
59
60
Harald Welte13588362017-04-30 23:57:55 +020061void osmo_sercomm_init(struct osmo_sercomm_inst *sercomm);
62int osmo_sercomm_initialized(struct osmo_sercomm_inst *sercomm);
Harald Weltec68af6a2017-04-30 21:21:52 +020063
64/* User Interface: Tx */
Harald Welte13588362017-04-30 23:57:55 +020065void osmo_sercomm_sendmsg(struct osmo_sercomm_inst *sercomm, uint8_t dlci, struct msgb *msg);
Harald Welte13588362017-04-30 23:57:55 +020066unsigned int osmo_sercomm_tx_queue_depth(struct osmo_sercomm_inst *sercomm, uint8_t dlci);
Harald Weltec68af6a2017-04-30 21:21:52 +020067
68/* User Interface: Rx */
Harald Welte13588362017-04-30 23:57:55 +020069int osmo_sercomm_register_rx_cb(struct osmo_sercomm_inst *sercomm, uint8_t dlci, dlci_cb_t cb);
Harald Weltec68af6a2017-04-30 21:21:52 +020070
Harald Welte799bef52017-05-15 17:16:48 +020071int osmo_sercomm_change_speed(struct osmo_sercomm_inst *sercomm, uint32_t bdrt);
72
Harald Weltec68af6a2017-04-30 21:21:52 +020073/* Driver Interface */
74
Harald Welte13588362017-04-30 23:57:55 +020075int osmo_sercomm_drv_pull(struct osmo_sercomm_inst *sercomm, uint8_t *ch);
Harald Welte13588362017-04-30 23:57:55 +020076int osmo_sercomm_drv_rx_char(struct osmo_sercomm_inst *sercomm, uint8_t ch);
Harald Weltec68af6a2017-04-30 21:21:52 +020077
Harald Welte799bef52017-05-15 17:16:48 +020078extern void sercomm_drv_lock(unsigned long *flags);
79extern void sercomm_drv_unlock(unsigned long *flags);
80extern void sercomm_drv_start_tx(struct osmo_sercomm_inst *sercomm);
81extern int sercomm_drv_baudrate_chg(struct osmo_sercomm_inst *sercomm, uint32_t bdrt);
82
Harald Welte13588362017-04-30 23:57:55 +020083static inline struct msgb *osmo_sercomm_alloc_msgb(unsigned int len)
Harald Weltec68af6a2017-04-30 21:21:52 +020084{
85 return msgb_alloc_headroom(len+4, 4, "sercomm_tx");
86}
87
88#endif /* _SERCOMM_H */