1.1--- a/lisp/ffi/uring/uring.lisp Tue Mar 26 22:30:19 2024 -0400
1.2+++ b/lisp/ffi/uring/uring.lisp Wed Mar 27 21:45:07 2024 -0400
1.3@@ -14,19 +14,154 @@
1.4 (sqe-mmap nil :type mmapped-region)
1.5 (cq-mmap nil :type mmapped-region))
1.6
1.7-(defstruct io-parameters (params nil :type io-uring-params))
1.8+(defun parse-io-uring-params (params)
1.9+ "Parse IO-URING-PARAMS foreign struct, return an IO-PARAMS struct."
1.10+ (let ((res 0))
1.11+ (loop while params
1.12+ do (1+ res))
1.13+ res))
1.14+
1.15+(defstruct io-params
1.16+ (sq-entries 0 :type fixnum)
1.17+ (cq-entries 0 :type fixnum)
1.18+ (flags 0 :type fixnum)
1.19+ (sq-thread-cpu 0 :type fixnum)
1.20+ (sq-thread-idle 0 :type fixnum)
1.21+ (features 0 :type fixnum)
1.22+ (wq-fd 0 :type fixnum)
1.23+ ;; resv
1.24+ (sq-off (make-submission-queue-offsets) :type submission-queue-offsets) ;; offsets are 40bytes each
1.25+ (cq-off (make-completion-queue-offsets) :type completion-queue-offsets))
1.26+
1.27+(defmacro define-io-param-flag (name const)
1.28+ "Create a predicate method with NAME which checks for presence of flag
1.29+CONST in FLAGS slot of IO-PARAMS. A SETF expansion is also defined
1.30+which accepts a boolean value and automatically adjusts the slot.")
1.31+
1.32+(defmacro define-io-param-feature (name const)
1.33+ "Create a predicate method with NAME which checks for presence of flag
1.34+CONST in FEATURES slot of IO-PARAMS. A SETF expansion is also defined
1.35+which accepts a boolean value and automatically adjust the slot.")
1.36+
1.37+;; (define-io-param-flag setup-sqpoll-p ioring-setup-sqpoll)
1.38+;; (define-io-param-flag setup-iopoll-p ioring-setup-iopoll)
1.39+;; (define-io-param-flag setup-single-issuer-p ioring-setup-single-issuer)
1.40+;; (define-io-param-flag setup-iopoll-p ioring-setup-iopoll)
1.41+;; (define-io-param-feature feat-single-mmap-p ioring-feat-single-mmap)
1.42+;; (define-io-param-feature feat-nodrop-p ioring-feat-nodrop)
1.43+;; (define-io-param-feature feat-submit-stable-p ioring-feat-submit-stable)
1.44+;; (define-io-param-feature feat-rw-cur-pos-p ioring-feat-rw-cur-pos)
1.45+;; (define-io-param-feature feat-cur-personality-p ioring-feat-cur-personality)
1.46+;; (define-io-param-feature feat-fast-poll-p ioring-feat-fast-poll-p)
1.47+;; (define-io-param-feature feat-poll-32bits-p ioring-feat-poll-32bits-p)
1.48+;; (define-io-param-feature feat-sqpoll-nonfixed-p ioring-feat-sqpoll-nonfixed)
1.49+;; (define-io-param-feature feat-ext-arg-p ioring-feat-ext-arg)
1.50+;; (define-io-param-feature feat-native-workers-p ioring-feat-native-workers)
1.51+;; (define-io-param-feature feat-rsrc-tags-p ioring-feat-rsrc-tags)
1.52+;; (define-io-param-feature feat-cqe-skip-p ioring-feat-cqe-skip)
1.53+;; (define-io-param-feature feat-linked-file-p ioring-feat-linked-file)
1.54+
1.55+(defmethod build ((self io-params) &key &allow-other-keys)
1.56+ (with-slots (sq-entries cq-entries flags sq-thread-cpu sq-thread-idle features wq-fd sq-off cq-off) self
1.57+ (with-io-uring-params res ((sq-entries sq-entries) (cq-entries cq-entries) (flags flags)
1.58+ (sq-thread-cpu sq-thread-cpu) (sq-thread-idle sq-thread-idle) (features features)
1.59+ (wq-fd wq-fd) (sq-off sq-off) (cq-off cq-off))
1.60+ res)))
1.61+
1.62+(define-alien-type nil
1.63+ (struct io-uring
1.64+ (sq (struct io-uring-sq))
1.65+ (cq (struct io-uring-cq))
1.66+ (flags unsigned-int)
1.67+ (ring-fd int)
1.68+ (features unsigned-int)
1.69+ (enter-ring-fd int)
1.70+ (int-flags char)
1.71+ (pad (array char 3))
1.72+ (pad2 unsigned-int)))
1.73
1.74 ;; io-uring instance
1.75-(defstruct io-uring
1.76+(defstruct uring
1.77 (sq nil :type submission-queue)
1.78 (cq nil :type completion-queue)
1.79 (fd nil :type sb-posix:file-descriptor) ;; owned fd
1.80- (params nil :type io-parameters) ;; TODO io-params
1.81+ (params nil :type io-params)
1.82 (memory nil :type io-memory-map))
1.83
1.84-(defstruct io-uring-builder
1.85- (dontfork nil :type boolean)
1.86- (params nil :type io-uring-params))
1.87+(defvar *default-io-params* (make-io-params))
1.88+(defstruct uring-builder
1.89+ (params *default-io-params* :type io-params)
1.90+ (dontfork nil :type boolean))
1.91+
1.92+(defmethod build ((self uring-builder) &key (entries 256) &allow-other-keys))
1.93+
1.94+(defun setup-queue (fd p)
1.95+ "Setup a URING struct given a reference to a FILE-DESCRIPTOR and IO-PARAMS.")
1.96+
1.97+(defun make-queue (entries)
1.98+ "Create a new URING instance with default params. N is the size of the
1.99+queue, which must be a power of two."
1.100+ (build (make-uring-builder) :entries entries))
1.101+
1.102+(defmethod build-submitter ((self uring)))
1.103
1.104 ;;; Syscalls
1.105 ;; register, setup, enter
1.106+
1.107+(define-alien-routine io-uring-get-probe-ring (* io-uring-probe) (ring (* (struct io-uring))))
1.108+(define-alien-routine io-uring-get-probe (* io-uring-probe))
1.109+(define-alien-routine io-uring-free-probe void (* io-uring-probe))
1.110+;;...
1.111+
1.112+(defalien-int io-uring-queue-init (entries int) (ring (* (struct io-uring))) (flags unsigned))
1.113+
1.114+
1.115+;;...
1.116+
1.117+(defalien-int io-uring-submit (ring (* (struct io-uring))))
1.118+
1.119+(defalien-int io-uring-register
1.120+ (fd int)
1.121+ (opcode unsigned-int)
1.122+ (args (* t))
1.123+ (nr-args unsigned-int))
1.124+
1.125+;;...
1.126+(defalien-int io-uring-register-buffers
1.127+ (ring (* (struct io-uring)))
1.128+ (iovecs (* (struct iovec)))
1.129+ (nr-iovecs unsigned-int))
1.130+
1.131+;;...
1.132+
1.133+(defalien-int io-uring-enable-rings (ring (* (struct io-uring))))
1.134+(defalien-int io-uring-sqring-wait (ring (* (struct io-uring))))
1.135+
1.136+;;...
1.137+(defalien-int io-uring-setup
1.138+ (entries unsigned-int)
1.139+ (p (* (struct io-uring-params))))
1.140+
1.141+(defalien-int io-uring-enter
1.142+ (fd int)
1.143+ (to-submit unsigned-int)
1.144+ (min-complete unsigned-int)
1.145+ (flags unsigned-int)
1.146+ (arg (* t))
1.147+ (size unsigned-long))
1.148+
1.149+(define-alien-routine io-uring-setup-buf-ring (* (struct io-uring-buf-ring))
1.150+ (ring (* (struct io-uring)))
1.151+ (nentries unsigned-int)
1.152+ (bgid int)
1.153+ (flags unsigned-int)
1.154+ (ret (* int)))
1.155+(defalien-int io-uring-free-buf-ring
1.156+ (ring (* (struct io-uring)))
1.157+ (br (* (struct io-uring-buf-ring)))
1.158+ (nentries unsigned-int)
1.159+ (bgid int))
1.160+;;...
1.161+
1.162+;; peek-cqe wait-cqe get-sqe
1.163+;; io-uring-buf-ring-init