It's a rare treat to see low level programming in Common Lisp!!
+100 for Steve Losh!
11–20 of 21 posts
It's a rare treat to see low level programming in Common Lisp!!
+100 for Steve Losh!
Very interesting read! But could somebody explain why the following piece of code is needed? And why is it defined inline? (defun-inline (setf vref) (new-value chip x y) (setf (aref (chip-video chip) (+ (* +screen-width+ y) x)) new-value))
Very interesting read! But could somebody explain why the following piece of code is needed? And why is it defined inline? (defun-inline (setf vref) (new-value chip x y) (setf (aref (chip-video chip) (+ (* +screen-width+ y) x)) new-value))
Wouldn't a lookup table be much faster here? That multiply on every screen access can't help the speed.
(defun foo (chip y)
(declare (optimize speed)
(type chip chip)
(type int16 y))
(vref chip 0 y))
(disassemble 'foo)
; disassembly for FOO
; Size: 48 bytes. Origin: #x100EF5E39D
; 9D: 488B423D MOV RAX, [RDX+61] ; no-arg-parsing entry point
;; ---------------------- Look ma, no multiplication!
;; vvvvvvvvvvv
; A1: 48C1E706 SHL RDI, 6
; A5: B900100000 MOV ECX, 4096
; AA: 40F6C701 TEST DIL, 1
; AE: 7513 JNE L0
; B0: 4839F9 CMP RCX, RDI
; B3: 760E JBE L0
; B5: 488B54B801 MOV RDX, [RAX+RDI*4+1]
; BA: 488BE5 MOV RSP, RBP
; BD: F8 CLC
; BE: 5D POP RBP
; BF: C3 RET
; C0: 0F0B10 BREAK 16 ; Invalid argument count trap
; C3: L0: 0F0B0A BREAK 10 ; error trap
; C6: 06 BYTE #X06
; C7: 0C BYTE #X0C ; INVALID-ARRAY-INDEX-ERROR
; C8: 1B BYTE #X1B ; RAX
; C9: 9A BYTE #X9A ; RCX
; CA: FE9A03 BYTE #XFE, #X9A, #X03 ; RDIThis is one of the coolest things i've ever seen! It's a rare treat to see low level programming in Common Lisp!! +100 for Steve Losh!
https://github.com/kingcons/cl-6502/blob/master/README.md
And the corresponding book
Very interesting read! But could somebody explain why the following piece of code is needed? And why is it defined inline? (defun-inline (setf vref) (new-value chip x y) (setf (aref (chip-video chip) (+ (* +screen-width+ y) x)) new-value))
vref and (setf vref) define getter and setter functions for manipulating pixel arrays. Since these functions are used a lot, it makes sense to allow compiler to inline them for maximum speed. Normally function must be accessed trough the symbol and it can be redefined on the fly.
(defun-inline set-vref (new-value chip x y)
...)
And how would you actually call the original function to set a pixel? (I'm not very familiar with inlines, maybe that's my problem here.)Earlier quoted context omitted.
vref and (setf vref) define getter and setter functions for manipulating pixel arrays. Since these functions are used a lot, it makes sense to allow compiler to inline them for maximum speed. Normally function must be accessed trough the symbol and it can be redefined on the fly.
I understand what they do, and I appreciate that it helps performance to inline them. What I don't understand is the (setf vref) syntax. I thought that after a defun statement you had to have a symbol, not an S-expression? Something like so: (defun-inline set-vref (new-value chip x y) ...) And how would you actually call the original function to set a pixel? (I'm not very familiar with inlines, maybe that's my proble…
https://github.com/flambard/chip-8-dynarec
Perhaps my project will be completed after all.. :-)
Earlier quoted context omitted.
vref and (setf vref) define getter and setter functions for manipulating pixel arrays. Since these functions are used a lot, it makes sense to allow compiler to inline them for maximum speed. Normally function must be accessed trough the symbol and it can be redefined on the fly.
I understand what they do, and I appreciate that it helps performance to inline them. What I don't understand is the (setf vref) syntax. I thought that after a defun statement you had to have a symbol, not an S-expression? Something like so: (defun-inline set-vref (new-value chip x y) ...) And how would you actually call the original function to set a pixel? (I'm not very familiar with inlines, maybe that's my proble…
In this case you would use
(setf (vref chip x y) new-value)
to call the function (just like with AREF above). Using SETF has the advantage that you can define "modify macros" that read and write a place. For example, (incf (vref chip x y) delta)
would increment the place by DELTA. Or (rotatef (vref chip x1 y1)
(vref chip x2 y2))
would swap two pixels.So here, Steve Losh, one of the best Vimmers out there, is also an excellent Lisper! It would be interesting to hear his views on Emacs since he transitioned to Clojure. I am curious to know whether he uses Vim for Clojure/Lisp development.
I still use (Neo)Vim, using VLIME for Common Lisp interaction: https://github.com/l04m33/vlime It works great.