emacs-elpa-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[elpa] externals/xelb 04db92e5ab 6/6: Strict (un)marshal size checking


From: ELPA Syncer
Subject: [elpa] externals/xelb 04db92e5ab 6/6: Strict (un)marshal size checking
Date: Thu, 18 Jan 2024 12:59:14 -0500 (EST)

branch: externals/xelb
commit 04db92e5ab23becd359e906fc37f3aab18dc9ba8
Author: Steven Allen <steven@stebalien.com>
Commit: Steven Allen <steven@stebalien.com>

    Strict (un)marshal size checking
    
    * xcb-types.el (xcb:marshal xcb:-struct): Fail encoding if expected size
      is match the size of the encoded struct.
      (xcb:unmarshal xcb:-struct): Fail decoding if the expected size is
      less than the number of bytes read or more than the number of bytes
      available to read.
      (xcb:marshal xcb:-union): Fail encoding if the expected size is less
      than the size of the encoded union.
---
 xcb-types.el | 34 ++++++++++++++++++++++++++++------
 1 file changed, 28 insertions(+), 6 deletions(-)

diff --git a/xcb-types.el b/xcb-types.el
index 7a9521a799..8bd3a29934 100644
--- a/xcb-types.el
+++ b/xcb-types.el
@@ -519,6 +519,14 @@ Consider let-bind it rather than change its global 
value."))
                                                     (length result))))
           (when (eq type 'xcb:-switch) ;xcb:-switch always finishes a struct
             (throw 'break 'nil)))))
+    ;; If we specify a size, verify that it matches the actual size.
+    (when-let* ((size-exp (slot-value obj '~size))
+                (size (eval size-exp `((obj . ,obj)))))
+      (unless (length= result size)
+        (error "[XCB] Unexpected size for type %s: got %d, expected %d"
+               (type-of obj)
+               (length result)
+               size)))
     result))
 
 (cl-defmethod xcb:-marshal-field ((obj xcb:-struct) type value &optional pos)
@@ -640,11 +648,21 @@ The optional argument CTX is for <paramref>."
           (setq result (+ result (cadr tmp)))
           (when (eq type 'xcb:-switch) ;xcb:-switch always finishes a struct
             (throw 'break 'nil)))))
-    (if-let ((size (slot-value obj '~size)))
-        ;; Let the struct compute it's size if a length field is specified. 
This lets us skip
-        ;; unknown fields.
-        (eval (slot-value obj '~size) `((obj . ,obj)))
-      result)))
+    ;; Let the struct compute it's size if a length field is specified. This 
lets us skip unknown
+    ;; fields.
+    (when-let* ((size-exp (slot-value obj '~size))
+                (size (eval size-exp `((obj . ,obj)))))
+      ;; Make sure the stated size is reasonable.
+      (cond
+       ((< size result)
+        (error "[XCB] Object of type `%s' specified a size (%d) less than the 
number of bytes read (%d)"
+               (type-of obj) size result))
+       ((length< byte-array (- size result))
+        (error "[XCB] Object of type `%s' specified a size (%d) greater than 
the size of the input (%d)"
+               (type-of obj) size (+ result (length byte-array)))))
+      ;; Skip any additional bytes.
+      (setq result size))
+    result))
 
 (cl-defmethod xcb:-unmarshal-field ((obj xcb:-struct) type data offset
                                     initform &optional ctx total-length)
@@ -868,8 +886,12 @@ This result is converted from the first bounded slot."
                                       (slot-value obj name)))
         (when (> (length tmp) (length result))
           (setq result tmp))))
-    (when (> size (length result))
+    (cond
+     ((length< result size)
       (setq result (vconcat result (make-vector (- size (length result)) 0))))
+     ((length> result size)
+      (error "[XCB] Marshaled enum `%s' is larger than its declared size (%d > 
%d)"
+             (type-of obj) (length result) size)))
     result))
 ;;
 (cl-defmethod xcb:unmarshal ((obj xcb:-union) byte-array &optional ctx



reply via email to

[Prev in Thread] Current Thread [Next in Thread]