Paste number 327488: lam-par-lisp-poc

Paste number 327488: lam-par-lisp-poc
Pasted by: phf
When:8 years, 5 months ago
Share:Tweet this! | http://paste.lisp.org/+70OW
Channel:None
Paste contents:
Raw Source | XML | Display As

;;; lam-par-lisp-poc by phf

(defun randomness (size)
  (with-open-file (input #p"/dev/random" :element-type '(unsigned-byte 8))
    (let ((arr (make-array size :element-type (stream-element-type input))))
      (read-sequence arr input)
      arr)))

(defun hexify (bytearray)
  (let ((*print-base* 16))
    (format nil "~{~2,'0x~}" (coerce bytearray 'list))))

(defun mkpriv (payloadbits strengthbits)
  (loop for i from 1 upto payloadbits
        collect (cons (randomness (/ strengthbits 8))
                      (randomness (/ strengthbits 8)))))

(defun priv->pub (hashthunk privkey)
  (loop for (a . b) in privkey
        collect (cons (funcall hashthunk a)
                      (funcall hashthunk b))))

(defun priv->pub-sha256 (privkey)
  (priv->pub (lambda (a) (ironclad:digest-sequence :sha256 a))
            privkey))

;;Great boobies honeybun, my lower intestine is full of spam
(defun encode (privkey payload)
  (assert (= (length privkey) (* 8 (length payload))))
  (labels ((b (n)
             (multiple-value-bind (n b) (truncate n 8)
               (ldb (byte 1 b) (elt payload n)))))
    (loop for (a . b) in privkey
          for n from 0
          collect (if (zerop (b n))
                      a
                    b))))

(defun decode (hashthunk pubkey encoded)
  (let ((result (make-array (/ (length pubkey) 8)
                            :element-type '(unsigned-byte 8)
                            :initial-element 0)))
    (labels ((set-b (n v)
               (multiple-value-bind (n b) (truncate n 8)
                 (setf (ldb (byte 1 b) (elt result n)) v))))
      (loop for (a . b) in pubkey
            for bs in encoded
            for hash = (funcall hashthunk bs)
            for n from 0
            do (cond ((equalp hash a) (set-b n 0))
                     ((equalp hash b) (set-b n 1))
                     (t (error "invalid hash n=~a hash=~a a=~a b=~a"
                               n hash a b)))
            finally (return result)))))

(defun decode-sha256 (pubkey encoded)
  (decode (lambda (a) (ironclad:digest-sequence :sha256 a))
          pubkey encoded))


#+nil
(time
 (let* ((privkey (mkpriv 256 512))
        (pubkey (priv->pub-sha256 privkey))
        (message (ironclad:digest-sequence :sha256 (ironclad:ascii-string-to-byte-array "Attack at dawn!"))))
   (equalp message (decode-sha256 pubkey (encode privkey message)))))

;;; User time    =        0.863
;;; System time  =        0.290
;;; Elapsed time =        1.140
;;; Allocation   = 134157184 bytes
;;; 0 Page faults

This paste has no annotations.

Colorize as:
Show Line Numbers

Lisppaste pastes can be made by anyone at any time. Imagine a fearsomely comprehensive disclaimer of liability. Now fear, comprehensively.