aboutsummaryrefslogtreecommitdiff
path: root/sys/contrib/dev/mediatek/mt76/util.h
diff options
context:
space:
mode:
Diffstat (limited to 'sys/contrib/dev/mediatek/mt76/util.h')
-rw-r--r--sys/contrib/dev/mediatek/mt76/util.h162
1 files changed, 162 insertions, 0 deletions
diff --git a/sys/contrib/dev/mediatek/mt76/util.h b/sys/contrib/dev/mediatek/mt76/util.h
new file mode 100644
index 000000000000..000d2e04336a
--- /dev/null
+++ b/sys/contrib/dev/mediatek/mt76/util.h
@@ -0,0 +1,162 @@
+/*-
+ * SPDX-License-Identifier: BSD-2-Clause
+ *
+ * Copyright (c) 2020,2022 Bjoern A. Zeeb <bz@FreeBSD.org>
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $FreeBSD$
+ */
+
+#ifndef _MT76_UTIL_H
+#define _MT76_UTIL_H
+
+#include <linux/kthread.h>
+
+struct mt76_worker
+{
+ void(*fn)(struct mt76_worker *);
+ struct task_struct *task;
+ unsigned long state;
+};
+
+enum mt76_worker_state {
+ MT76_WORKER_SCHEDULED,
+ MT76_WORKER_RUNNING,
+};
+
+#if 0
+bool __mt76_poll(struct mt76_dev *, u32, u32, u32, int);
+bool __mt76_poll_msec(struct mt76_dev *, u32, u32, u32, int);
+int mt76_get_min_avg_rssi(struct mt76_dev *, bool);
+#endif
+int mt76_wcid_alloc(u32 *, int);
+int __mt76_worker_fn(void *);
+
+/* wcid_phy_mask is [32] */
+static inline void
+mt76_wcid_mask_set(u32 *mask, u16 bit)
+{
+
+ mask[bit / 32] |= BIT(bit % 32);
+}
+
+static inline void
+mt76_wcid_mask_clear(u32 *mask, u16 bit)
+{
+
+ mask[bit / 32] &= ~BIT(bit % 32);
+}
+
+static inline bool
+mt76_wcid_mask_test(u32 *mask, u16 bit)
+{
+
+ return (mask[bit / 32] & BIT(bit % 32));
+}
+
+/* See, e.g., __mt76_worker_fn for some details. */
+static inline int
+mt76_worker_setup(struct ieee80211_hw *hw, struct mt76_worker *w,
+ void (*wfunc)(struct mt76_worker *), const char *name)
+{
+ int rc;
+
+ if (wfunc)
+ w->fn = wfunc;
+
+ w->task = kthread_run(__mt76_worker_fn, w,
+ "mt76-worker");
+
+ if (!IS_ERR(w->task))
+ return (0);
+
+ rc = PTR_ERR(w->task);
+ w->task = NULL;
+ return (rc);
+}
+
+static inline void
+mt76_worker_schedule(struct mt76_worker *w)
+{
+
+ if (w->task == NULL)
+ return;
+
+ if (!test_and_set_bit(MT76_WORKER_SCHEDULED, &w->state) ||
+ !test_bit(MT76_WORKER_RUNNING, &w->state))
+ wake_up_process(w->task);
+}
+
+static inline void
+mt76_worker_enable(struct mt76_worker *w)
+{
+
+ if (w->task == NULL)
+ return;
+
+ kthread_unpark(w->task);
+ mt76_worker_schedule(w);
+}
+
+static inline void
+mt76_worker_disable(struct mt76_worker *w)
+{
+
+ if (w->task == NULL)
+ return;
+
+ kthread_park(w->task);
+ WRITE_ONCE(w->state, 0);
+}
+
+static inline void
+mt76_worker_teardown(struct mt76_worker *w)
+{
+
+ if (w->task == NULL)
+ return;
+
+ kthread_stop(w->task);
+ w->task = NULL;
+}
+
+static inline void
+mt76_skb_set_moredata(struct sk_buff *skb, bool moredata)
+{
+ /*
+ * This would be net80211::IEEE80211_FC1_MORE_DATA
+ * Implement it as mostly LinuxKPI 802.11 to avoid
+ * further header pollution and possible conflicts.
+ */
+ struct ieee80211_hdr *hdr;
+ uint16_t val;
+
+ hdr = (struct ieee80211_hdr *)skb->data;
+ val = cpu_to_le16(IEEE80211_FC1_MORE_DATA << 8);
+ if (!moredata)
+ hdr->frame_control &= ~val;
+ else
+ hdr->frame_control |= val;
+}
+
+#endif /* _MT76_UTIL_H */