Skip to content

Instantly share code, notes, and snippets.

View marcoheisig's full-sized avatar

Marco Heisig marcoheisig

  • FAU Erlangen-Nürnberg
  • Germany
View GitHub Profile
@marcoheisig
marcoheisig / 2022-03-22-els-loopus-demo.lisp
Created March 29, 2022 14:56
A demo of the Loopus loop optimization framework, as presented at https://european-lisp-symposium.org/2022
(in-package #:cl-user)
(defun jacobi-a (dst src &optional (w 0.25d0))
(declare (type (simple-array double-float 2) dst src)
(type double-float w))
(loop for i from 1 below (1- (array-dimension dst 0)) do
(loop for j from 1 below (1- (array-dimension dst 1)) do
(setf (aref dst i j)
(* w
(+
@marcoheisig
marcoheisig / odd-bits.lisp
Created October 4, 2021 14:12
Extract the odd bits of an integer.
(defun odd-bits (x)
(declare (type (unsigned-byte 32) x))
(setf x (logand (ash x -1) #x55555555))
(setf x (logand (logior (ash x -1) x) #x33333333))
(setf x (logand (logior (ash x -2) x) #x0F0F0F0F))
(setf x (logand (logior (ash x -4) x) #x00FF00FF))
(setf x (logand (logior (ash x -8) x) #x0000FFFF))
x)
@marcoheisig
marcoheisig / alist-from-plist.lisp
Created February 17, 2021 12:02
A functional implementation of plist to alist conversion.
(defun alist-from-plist (plist)
(trivia:match plist
((list) '())
((list* (and key (type symbol)) value rest)
(list* (cons key value) (alist-from-plist rest)))
(_ (error "Not a plist:~%~S~%" plist))))
@marcoheisig
marcoheisig / init.el
Last active January 14, 2021 16:16
Use Clouseau as the default inspector in Emacs.
;;;; Note: You should also put something like (ql:quickload :clouseau) in your initialization file.
(defun clouseau-inspect (string)
(interactive
(list (slime-read-from-minibuffer
"Inspect value (evaluated): "
(slime-sexp-at-point))))
(let ((inspector 'cl-user::*clouseau-inspector*))
(slime-eval-async
`(cl:progn
@marcoheisig
marcoheisig / typed-cells.lisp
Last active June 20, 2020 06:34
A possible safe implementation of typed cells for SICL.
(defun make-function-cell (value)
(check-type value function)
(values
(lambda () value)
(lambda (new-value)
(check-type new-value function)
(setf value new-value))))
;; In order to make typed cells as fast as cons cells,
;; the compiler has to be able to inline the first value returned by
@marcoheisig
marcoheisig / assumptions.org
Last active February 18, 2021 01:03
A Mechanism for Safely Maintaining Assumptions in a Common Lisp Implementation

A Mechanism for Safely Maintaining Assumptions in a Common Lisp Implementation

Description

There are many occasions where a function can be optimized under certain assumptions about the system. But since most aspects of Common Lisp can be redefined almost arbitrarily, there are few assumptions that a compiler can generally make. (A notable exception is the behavior of definitions in the CL package, and of built-in objects.)

@marcoheisig
marcoheisig / quickload-all.lisp
Created April 19, 2020 10:26
Load all of Quicklisp, except systems that fail to load or systems that get stuck loading for longer than 20 seconds.
(defun quickload-all ()
(loop for system in (ql:provided-systems t) do
(ignore-errors
(trivial-timeout:with-timeout (20)
(ql:quickload (ql-dist:short-description system))))))
@marcoheisig
marcoheisig / fast-method-keyword-handling.lisp
Created February 24, 2020 15:07
The inline lambda created for a call to a generic function with keyword arguments and calls to call-next-method with arguments.
(lambda
(#:x-1 &key ((:y #:y-2) nil #:suppliedp-3) ((:z #:z-4) nil #:suppliedp-5))
(declare (ignorable #:x-1 #:y-2 #:suppliedp-3 #:z-4 #:suppliedp-5))
(let ((sealable-metaobjects::.gf. #'keyword-function))
(declare (ignorable sealable-metaobjects::.gf.))
(declare (sb-ext:disable-package-locks call-method))
(declare (sb-ext:disable-package-locks make-method))
(declare (sb-ext:disable-package-locks sb-pcl::check-applicable-keywords))
@marcoheisig
marcoheisig / sicl-debugger-performance.lisp
Last active January 22, 2020 17:40
What ist the cost of having one (correctly predicted) branch at the beginning of a function?
(in-package :cl-user)
(defmacro debug-defun (name lambda-list &body body)
(multiple-value-bind (forms decls doc)
(alexandria:parse-body body :documentation t)
`(progn
(declaim (notinline ,name))
(defun ,name (.debug-flag. ,@lambda-list)
,@(when doc (list doc))
,@decls
@marcoheisig
marcoheisig / list-iterators.lisp
Created January 7, 2020 12:22
Iterators can be surprisingly fast (on SBCL, when they are inlined)
(in-package #:cl-user)
(defpackage #:list-iterators
(:use #:cl))
(in-package #:list-iterators)
(declaim (inline make-read-iterator))
(defun make-read-iterator (list terminate)
(lambda ()