cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

ssh_packet_layer.h (6089B)


      1/* SPDX-License-Identifier: GPL-2.0+ */
      2/*
      3 * SSH packet transport layer.
      4 *
      5 * Copyright (C) 2019-2021 Maximilian Luz <luzmaximilian@gmail.com>
      6 */
      7
      8#ifndef _SURFACE_AGGREGATOR_SSH_PACKET_LAYER_H
      9#define _SURFACE_AGGREGATOR_SSH_PACKET_LAYER_H
     10
     11#include <linux/atomic.h>
     12#include <linux/kfifo.h>
     13#include <linux/ktime.h>
     14#include <linux/list.h>
     15#include <linux/serdev.h>
     16#include <linux/spinlock.h>
     17#include <linux/types.h>
     18#include <linux/wait.h>
     19#include <linux/workqueue.h>
     20
     21#include <linux/surface_aggregator/serial_hub.h>
     22#include "ssh_parser.h"
     23
     24/**
     25 * enum ssh_ptl_state_flags - State-flags for &struct ssh_ptl.
     26 *
     27 * @SSH_PTL_SF_SHUTDOWN_BIT:
     28 *	Indicates that the packet transport layer has been shut down or is
     29 *	being shut down and should not accept any new packets/data.
     30 */
     31enum ssh_ptl_state_flags {
     32	SSH_PTL_SF_SHUTDOWN_BIT,
     33};
     34
     35/**
     36 * struct ssh_ptl_ops - Callback operations for packet transport layer.
     37 * @data_received: Function called when a data-packet has been received. Both,
     38 *                 the packet layer on which the packet has been received and
     39 *                 the packet's payload data are provided to this function.
     40 */
     41struct ssh_ptl_ops {
     42	void (*data_received)(struct ssh_ptl *p, const struct ssam_span *data);
     43};
     44
     45/**
     46 * struct ssh_ptl - SSH packet transport layer.
     47 * @serdev:        Serial device providing the underlying data transport.
     48 * @state:         State(-flags) of the transport layer.
     49 * @queue:         Packet submission queue.
     50 * @queue.lock:    Lock for modifying the packet submission queue.
     51 * @queue.head:    List-head of the packet submission queue.
     52 * @pending:       Set/list of pending packets.
     53 * @pending.lock:  Lock for modifying the pending set.
     54 * @pending.head:  List-head of the pending set/list.
     55 * @pending.count: Number of currently pending packets.
     56 * @tx:            Transmitter subsystem.
     57 * @tx.running:    Flag indicating (desired) transmitter thread state.
     58 * @tx.thread:     Transmitter thread.
     59 * @tx.thread_cplt_tx:  Completion for transmitter thread waiting on transfer.
     60 * @tx.thread_cplt_pkt: Completion for transmitter thread waiting on packets.
     61 * @tx.packet_wq:  Waitqueue-head for packet transmit completion.
     62 * @rx:            Receiver subsystem.
     63 * @rx.thread:     Receiver thread.
     64 * @rx.wq:         Waitqueue-head for receiver thread.
     65 * @rx.fifo:       Buffer for receiving data/pushing data to receiver thread.
     66 * @rx.buf:        Buffer for evaluating data on receiver thread.
     67 * @rx.blocked:    List of recent/blocked sequence IDs to detect retransmission.
     68 * @rx.blocked.seqs:   Array of blocked sequence IDs.
     69 * @rx.blocked.offset: Offset indicating where a new ID should be inserted.
     70 * @rtx_timeout:   Retransmission timeout subsystem.
     71 * @rtx_timeout.lock:    Lock for modifying the retransmission timeout reaper.
     72 * @rtx_timeout.timeout: Timeout interval for retransmission.
     73 * @rtx_timeout.expires: Time specifying when the reaper work is next scheduled.
     74 * @rtx_timeout.reaper:  Work performing timeout checks and subsequent actions.
     75 * @ops:           Packet layer operations.
     76 */
     77struct ssh_ptl {
     78	struct serdev_device *serdev;
     79	unsigned long state;
     80
     81	struct {
     82		spinlock_t lock;
     83		struct list_head head;
     84	} queue;
     85
     86	struct {
     87		spinlock_t lock;
     88		struct list_head head;
     89		atomic_t count;
     90	} pending;
     91
     92	struct {
     93		atomic_t running;
     94		struct task_struct *thread;
     95		struct completion thread_cplt_tx;
     96		struct completion thread_cplt_pkt;
     97		struct wait_queue_head packet_wq;
     98	} tx;
     99
    100	struct {
    101		struct task_struct *thread;
    102		struct wait_queue_head wq;
    103		struct kfifo fifo;
    104		struct sshp_buf buf;
    105
    106		struct {
    107			u16 seqs[8];
    108			u16 offset;
    109		} blocked;
    110	} rx;
    111
    112	struct {
    113		spinlock_t lock;
    114		ktime_t timeout;
    115		ktime_t expires;
    116		struct delayed_work reaper;
    117	} rtx_timeout;
    118
    119	struct ssh_ptl_ops ops;
    120};
    121
    122#define __ssam_prcond(func, p, fmt, ...)		\
    123	do {						\
    124		typeof(p) __p = (p);			\
    125							\
    126		if (__p)				\
    127			func(__p, fmt, ##__VA_ARGS__);	\
    128	} while (0)
    129
    130#define ptl_dbg(p, fmt, ...)  dev_dbg(&(p)->serdev->dev, fmt, ##__VA_ARGS__)
    131#define ptl_info(p, fmt, ...) dev_info(&(p)->serdev->dev, fmt, ##__VA_ARGS__)
    132#define ptl_warn(p, fmt, ...) dev_warn(&(p)->serdev->dev, fmt, ##__VA_ARGS__)
    133#define ptl_err(p, fmt, ...)  dev_err(&(p)->serdev->dev, fmt, ##__VA_ARGS__)
    134#define ptl_dbg_cond(p, fmt, ...) __ssam_prcond(ptl_dbg, p, fmt, ##__VA_ARGS__)
    135
    136#define to_ssh_ptl(ptr, member) \
    137	container_of(ptr, struct ssh_ptl, member)
    138
    139int ssh_ptl_init(struct ssh_ptl *ptl, struct serdev_device *serdev,
    140		 struct ssh_ptl_ops *ops);
    141
    142void ssh_ptl_destroy(struct ssh_ptl *ptl);
    143
    144/**
    145 * ssh_ptl_get_device() - Get device associated with packet transport layer.
    146 * @ptl: The packet transport layer.
    147 *
    148 * Return: Returns the device on which the given packet transport layer builds
    149 * upon.
    150 */
    151static inline struct device *ssh_ptl_get_device(struct ssh_ptl *ptl)
    152{
    153	return ptl->serdev ? &ptl->serdev->dev : NULL;
    154}
    155
    156int ssh_ptl_tx_start(struct ssh_ptl *ptl);
    157int ssh_ptl_tx_stop(struct ssh_ptl *ptl);
    158int ssh_ptl_rx_start(struct ssh_ptl *ptl);
    159int ssh_ptl_rx_stop(struct ssh_ptl *ptl);
    160void ssh_ptl_shutdown(struct ssh_ptl *ptl);
    161
    162int ssh_ptl_submit(struct ssh_ptl *ptl, struct ssh_packet *p);
    163void ssh_ptl_cancel(struct ssh_packet *p);
    164
    165int ssh_ptl_rx_rcvbuf(struct ssh_ptl *ptl, const u8 *buf, size_t n);
    166
    167/**
    168 * ssh_ptl_tx_wakeup_transfer() - Wake up packet transmitter thread for
    169 * transfer.
    170 * @ptl: The packet transport layer.
    171 *
    172 * Wakes up the packet transmitter thread, notifying it that the underlying
    173 * transport has more space for data to be transmitted. If the packet
    174 * transport layer has been shut down, calls to this function will be ignored.
    175 */
    176static inline void ssh_ptl_tx_wakeup_transfer(struct ssh_ptl *ptl)
    177{
    178	if (test_bit(SSH_PTL_SF_SHUTDOWN_BIT, &ptl->state))
    179		return;
    180
    181	complete(&ptl->tx.thread_cplt_tx);
    182}
    183
    184void ssh_packet_init(struct ssh_packet *packet, unsigned long type,
    185		     u8 priority, const struct ssh_packet_ops *ops);
    186
    187int ssh_ctrl_packet_cache_init(void);
    188void ssh_ctrl_packet_cache_destroy(void);
    189
    190#endif /* _SURFACE_AGGREGATOR_SSH_PACKET_LAYER_H */