summaryrefslogtreecommitdiff
path: root/src/eris-decode.lisp
diff options
context:
space:
mode:
authorPiotr Szarmanski2022-09-22 11:16:44 +0200
committerPiotr Szarmanski2022-09-22 11:16:44 +0200
commit4d82ef18a8bb18317be3e089f432f95b6e5dbd4a (patch)
treebfa28af036aeb0f3e41298867c449318675b5a07 /src/eris-decode.lisp
parentfdf5daa317c8a97ef8197200403db6f53a8f1777 (diff)
Implement stream-read-byte
Diffstat (limited to 'src/eris-decode.lisp')
-rw-r--r--src/eris-decode.lisp31
1 files changed, 24 insertions, 7 deletions
diff --git a/src/eris-decode.lisp b/src/eris-decode.lisp
index b7575ab..43f8db0 100644
--- a/src/eris-decode.lisp
+++ b/src/eris-decode.lisp
@@ -186,7 +186,7 @@ fetched from a trusted party.")
(setf (pos stream) new-pos
(data buffer) (data (car (last root)))
(pos buffer) (mod new-pos block-size))
- (if (= (- eof (mod eof block-size)) new-pos)
+ (if (< (- eof (mod eof block-size)) new-pos)
(unpad-buffer buffer)
(setf (eof buffer) block-size))))))
@@ -199,23 +199,25 @@ fetched from a trusted party.")
(defun eris-decode (read-capability fetch-function &key (cache-capacity 2048))
- "With a given fetch-function, return a stream that decodes the read-capability.
+ "Using the FETCH-FUNCTION, return a stream that decodes the READ-CAPABILITY.
Fetch-function must be a function with one argument, the reference octet, which
returns a (simple-array (unsigned-byte 8)) containing the block. The block will
be destructively modified, so you MUST provide a fresh array every time. If a
hash-table is used, a (copy-seq) needs to be done on the return value of
-gethash. "
+gethash.
+
+The keyword argument CACHE-CAPACITY indicates the amount of blocks stored in the
+cache."
(with-slots (level block-size root-reference-pair) read-capability
(let* ((get-block (cached-lambda (:cache-class 'lru-cache
:capacity cache-capacity
:table (make-hash-table :size (1+ cache-capacity) :test #'equalp))
(reference key &optional nonce)
(let* ((block (funcall fetch-function reference)))
+ (unless block (error 'missing-block :reference reference))
(hash-check block reference)
- (if block
- (decrypt-block block key nonce)
- (error 'missing-block :reference reference)))))
+ (decrypt-block block key nonce))))
(root (funcall get-block (reference root-reference-pair) (key root-reference-pair) (make-nonce level))))
;; "Implementations MUST verify the key appearing in the read capability
;; if level of encoded content is larger than 0."
@@ -282,10 +284,25 @@ the new position is beyond the end of file.."
(read-to-seq seq buffer :start start :end (if end end (length seq)) :stream stream)))
(defmethod stream-read-byte ((stream eris-decode-stream))
- nil)
+ (when (minusp (pos (buffer stream)))
+ ;; initializes the buffer
+ (reupdate-block stream (pos stream)))
+ (with-slots (position buffer block-size) stream
+ (with-slots (pos eof data) buffer
+ (cond
+ ((eql pos block-size)
+ (setf pos 0)
+ (advance-next-block stream)
+ (stream-read-byte stream))
+ ((eql pos eof)
+ :eof)
+ (t (prog1 (aref data pos)
+ (incf pos)
+ (incf position)))))))
(defmethod stream-element-type ((stream eris-decode-stream))
'(unsigned-byte 8))
(defun eris-file-length (stream)
+ "This is the equivalent of \"file-length\" for eris-decode-stream."
(eof stream))