diff options
| author | Andrea Corallo | 2019-07-14 09:53:06 +0200 |
|---|---|---|
| committer | Andrea Corallo | 2020-01-01 11:33:53 +0100 |
| commit | 210a3c0b3ad2a944bfed4e87a5039a9e4e14329a (patch) | |
| tree | 6ad725e810da9b4be9e067f2b967d3ec7758ac37 | |
| parent | 4a0379bdb41a6044978d0b5ffb2a5ece1984e404 (diff) | |
| download | emacs-210a3c0b3ad2a944bfed4e87a5039a9e4e14329a.tar.gz emacs-210a3c0b3ad2a944bfed4e87a5039a9e4e14329a.zip | |
comp-op-case in place plus other rework
| -rw-r--r-- | lisp/emacs-lisp/comp.el | 246 |
1 files changed, 192 insertions, 54 deletions
diff --git a/lisp/emacs-lisp/comp.el b/lisp/emacs-lisp/comp.el index 5731a00b2d3..3c6ce6e5828 100644 --- a/lisp/emacs-lisp/comp.el +++ b/lisp/emacs-lisp/comp.el | |||
| @@ -54,6 +54,16 @@ | |||
| 54 | ;; allocating memory? (these are technically not side effect free) | 54 | ;; allocating memory? (these are technically not side effect free) |
| 55 | ) | 55 | ) |
| 56 | 56 | ||
| 57 | (eval-when-compile | ||
| 58 | (defconst comp-op-stack-info | ||
| 59 | (cl-loop with h = (make-hash-table) | ||
| 60 | for k across byte-code-vector | ||
| 61 | for v across byte-stack+-info | ||
| 62 | when k | ||
| 63 | do (puthash k v h) | ||
| 64 | finally return h) | ||
| 65 | "Hash table lap-op -> stack adjustment.")) | ||
| 66 | |||
| 57 | (cl-defstruct comp-args | 67 | (cl-defstruct comp-args |
| 58 | (min nil :type number | 68 | (min nil :type number |
| 59 | :documentation "Minimum number of arguments allowed") | 69 | :documentation "Minimum number of arguments allowed") |
| @@ -183,8 +193,19 @@ To be used when ncall-conv is nil.") | |||
| 183 | "Current stack pointer." | 193 | "Current stack pointer." |
| 184 | '(comp-limple-frame-sp comp-frame)) | 194 | '(comp-limple-frame-sp comp-frame)) |
| 185 | 195 | ||
| 196 | (defmacro comp-with-sp (sp &rest body) | ||
| 197 | "Execute BODY setting the stack pointer to SP. | ||
| 198 | Restore the original value afterwads." | ||
| 199 | (declare (debug (form body)) | ||
| 200 | (indent 1)) | ||
| 201 | `(let ((orig-sp (comp-sp))) | ||
| 202 | (setf (comp-sp) ,sp) | ||
| 203 | (progn ,@body) | ||
| 204 | (setf (comp-sp) orig-sp))) | ||
| 205 | |||
| 186 | (defmacro comp-slot-n (n) | 206 | (defmacro comp-slot-n (n) |
| 187 | "Slot N into the meta-stack." | 207 | "Slot N into the meta-stack." |
| 208 | (declare (debug (form))) | ||
| 188 | `(aref (comp-limple-frame-frame comp-frame) ,n)) | 209 | `(aref (comp-limple-frame-frame comp-frame) ,n)) |
| 189 | 210 | ||
| 190 | (defmacro comp-slot () | 211 | (defmacro comp-slot () |
| @@ -245,81 +266,198 @@ If the calle function is known to have a return type propagate it." | |||
| 245 | 266 | ||
| 246 | (defun comp-limplify-listn (n) | 267 | (defun comp-limplify-listn (n) |
| 247 | "Limplify list N." | 268 | "Limplify list N." |
| 248 | (comp-emit-set-call `(call Fcons ,(comp-slot) | 269 | (comp-with-sp (1- n) |
| 249 | ,(make-comp-mvar :const-vld t | ||
| 250 | :constant nil))) | ||
| 251 | (dotimes (_ (1- n)) | ||
| 252 | (comp-stack-adjust -1) | ||
| 253 | (comp-emit-set-call `(call Fcons | 270 | (comp-emit-set-call `(call Fcons |
| 254 | ,(comp-slot) | 271 | ,(comp-slot) |
| 255 | ,(comp-slot-n (1+ (comp-sp))))))) | 272 | ,(make-comp-mvar :const-vld t |
| 273 | :constant nil)))) | ||
| 274 | (cl-loop for sp from (+ (comp-sp) n -2) downto (comp-sp) | ||
| 275 | do (comp-with-sp sp | ||
| 276 | (comp-emit-set-call `(call Fcons | ||
| 277 | ,(comp-slot) | ||
| 278 | ,(comp-slot-next)))))) | ||
| 279 | |||
| 280 | (defmacro comp-op-case (&rest cases) | ||
| 281 | "Expand CASES to the corresponding pcase." | ||
| 282 | (declare (debug (body)) | ||
| 283 | (indent defun)) | ||
| 284 | `(pcase op | ||
| 285 | ,@(cl-loop for (op . body) in cases | ||
| 286 | for sp-delta = (gethash op comp-op-stack-info) | ||
| 287 | for op-name = (symbol-name op) | ||
| 288 | if body | ||
| 289 | collect `(',op | ||
| 290 | (comp-emit-annotation ,(concat "LAP op " op-name)) | ||
| 291 | (comp-stack-adjust ,(if sp-delta sp-delta 0)) | ||
| 292 | (progn ,@body)) | ||
| 293 | else | ||
| 294 | collect `(',op (error ,(concat "Unsupported LAP op " | ||
| 295 | op-name)))) | ||
| 296 | (_ (error "Unexpected LAP op %s" (symbol-name op))))) | ||
| 256 | 297 | ||
| 257 | (defun comp-limplify-lap-inst (inst) | 298 | (defun comp-limplify-lap-inst (inst) |
| 258 | "Limplify LAP instruction INST accumulating in `comp-limple'." | 299 | "Limplify LAP instruction INST accumulating in `comp-limple'." |
| 259 | (let ((op (car inst))) | 300 | (let ((op (car inst))) |
| 260 | (pcase op | 301 | (comp-op-case |
| 261 | ('byte-discard | 302 | (byte-stack-ref |
| 262 | (comp-stack-adjust -1)) | 303 | (comp-copy-slot-n (- (comp-sp) (cdr inst) 1))) |
| 263 | ('byte-dup | 304 | (byte-varref |
| 264 | (comp-stack-adjust 1) | ||
| 265 | (comp-copy-slot-n (1- (comp-sp)))) | ||
| 266 | ('byte-symbol-value | ||
| 267 | (comp-emit-set-call `(call Fsymbol_value ,(comp-slot)))) | ||
| 268 | ('byte-varref | ||
| 269 | (comp-stack-adjust 1) | ||
| 270 | (comp-emit-set-call `(call Fsymbol_value ,(make-comp-mvar | 305 | (comp-emit-set-call `(call Fsymbol_value ,(make-comp-mvar |
| 271 | :const-vld t | 306 | :const-vld t |
| 272 | :constant (cadr inst))))) | 307 | :constant (cadr inst))))) |
| 273 | ('byte-varset | 308 | (byte-varset |
| 274 | (comp-emit `(call set_internal | 309 | (comp-emit `(call set_internal |
| 275 | ,(make-comp-mvar :const-vld t | 310 | ,(make-comp-mvar :const-vld t |
| 276 | :constant (cadr inst)) | 311 | :constant (cadr inst)) |
| 277 | ,(comp-slot)))) | 312 | ,(comp-slot)))) |
| 278 | ('byte-constant | 313 | (byte-varbind) |
| 279 | (comp-stack-adjust 1) | 314 | (byte-call) |
| 280 | (comp-set-const (cadr inst))) | 315 | (byte-unbind) |
| 281 | ('byte-stack-ref | 316 | (byte-pophandler) |
| 282 | (comp-stack-adjust 1) | 317 | (byte-pushconditioncase) |
| 283 | (comp-copy-slot-n (- (comp-sp) (cdr inst) 1))) | 318 | (byte-pushcatch) |
| 284 | ('byte-plus | 319 | (byte-nth) |
| 285 | (comp-stack-adjust -1) | 320 | (byte-symbolp) |
| 286 | (comp-emit-set-call `(callref Fplus 2 ,(comp-sp)))) | 321 | (byte-consp) |
| 287 | ('byte-aref | 322 | (byte-stringp) |
| 288 | (comp-stack-adjust -1) | 323 | (byte-listp) |
| 324 | (byte-eq) | ||
| 325 | (byte-memq) | ||
| 326 | (byte-not) | ||
| 327 | (byte-car | ||
| 328 | (comp-emit-set-call `(call Fcar ,(comp-slot)))) | ||
| 329 | (byte-cdr | ||
| 330 | (comp-emit-set-call `(call Fcdr ,(comp-slot)))) | ||
| 331 | (byte-cons | ||
| 332 | (comp-emit-set-call `(call Fcons ,(comp-slot) ,(comp-slot-next)))) | ||
| 333 | (byte-list1 | ||
| 334 | (comp-limplify-listn 1)) | ||
| 335 | (byte-list2 | ||
| 336 | (comp-limplify-listn 2)) | ||
| 337 | (byte-list3 | ||
| 338 | (comp-limplify-listn 3)) | ||
| 339 | (byte-list4 | ||
| 340 | (comp-limplify-listn 4)) | ||
| 341 | (byte-length | ||
| 342 | (comp-emit-set-call `(call Flength ,(comp-slot)))) | ||
| 343 | (byte-aref | ||
| 289 | (comp-emit-set-call `(call Faref | 344 | (comp-emit-set-call `(call Faref |
| 290 | ,(comp-slot) | 345 | ,(comp-slot) |
| 291 | ,(comp-slot-next)))) | 346 | ,(comp-slot-next)))) |
| 292 | ('byte-aset | 347 | (byte-aset |
| 293 | (comp-stack-adjust -2) | ||
| 294 | (comp-emit-set-call `(call Faset | 348 | (comp-emit-set-call `(call Faset |
| 295 | ,(comp-slot) | 349 | ,(comp-slot) |
| 296 | ,(comp-slot-next) | 350 | ,(comp-slot-next) |
| 297 | ,(comp-slot-n (+ 2 (comp-sp)))))) | 351 | ,(comp-slot-n (+ 2 (comp-sp)))))) |
| 298 | ('byte-cons | 352 | (byte-symbol-value |
| 299 | (comp-stack-adjust -1) | 353 | (comp-emit-set-call `(call Fsymbol_value ,(comp-slot)))) |
| 300 | (comp-emit-set-call `(call Fcons ,(comp-slot) ,(comp-slot-next)))) | 354 | (byte-symbol-function) |
| 301 | ('byte-car | 355 | (byte-set) |
| 302 | (comp-emit-set-call `(call Fcar ,(comp-slot)))) | 356 | (byte-fset) |
| 303 | ('byte-cdr | 357 | (byte-get) |
| 304 | (comp-emit-set-call `(call Fcdr ,(comp-slot)))) | 358 | (byte-substring) |
| 305 | ('byte-car-safe | 359 | (byte-concat2) |
| 360 | (byte-concat3) | ||
| 361 | (byte-concat4) | ||
| 362 | (byte-sub1) | ||
| 363 | (byte-add1) | ||
| 364 | (byte-eqlsign) | ||
| 365 | (byte-gtr) | ||
| 366 | (byte-lss) | ||
| 367 | (byte-leq) | ||
| 368 | (byte-geq) | ||
| 369 | (byte-diff) | ||
| 370 | (byte-negate) | ||
| 371 | (byte-plus | ||
| 372 | (comp-emit-set-call `(callref Fplus 2 ,(comp-sp)))) | ||
| 373 | (byte-max) | ||
| 374 | (byte-min) | ||
| 375 | (byte-mult) | ||
| 376 | (byte-point) | ||
| 377 | (byte-goto-char) | ||
| 378 | (byte-insert) | ||
| 379 | (byte-point-max) | ||
| 380 | (byte-point-min) | ||
| 381 | (byte-char-after) | ||
| 382 | (byte-following-char) | ||
| 383 | (byte-preceding-char) | ||
| 384 | (byte-current-column) | ||
| 385 | (byte-indent-to) | ||
| 386 | (byte-scan-buffer-OBSOLETE) | ||
| 387 | (byte-eolp) | ||
| 388 | (byte-eobp) | ||
| 389 | (byte-bolp) | ||
| 390 | (byte-bobp) | ||
| 391 | (byte-current-buffer) | ||
| 392 | (byte-set-buffer) | ||
| 393 | (byte-save-current-buffer) | ||
| 394 | (byte-set-mark-OBSOLETE) | ||
| 395 | (byte-interactive-p-OBSOLETE) | ||
| 396 | (byte-forward-char) | ||
| 397 | (byte-forward-word) | ||
| 398 | (byte-skip-chars-forward) | ||
| 399 | (byte-skip-chars-backward) | ||
| 400 | (byte-forward-line) | ||
| 401 | (byte-char-syntax) | ||
| 402 | (byte-buffer-substring) | ||
| 403 | (byte-delete-region) | ||
| 404 | (byte-narrow-to-region) | ||
| 405 | (byte-widen) | ||
| 406 | (byte-end-of-line) | ||
| 407 | (byte-constant2) | ||
| 408 | (byte-goto) | ||
| 409 | (byte-goto-if-nil) | ||
| 410 | (byte-goto-if-not-nil) | ||
| 411 | (byte-goto-if-nil-else-pop) | ||
| 412 | (byte-goto-if-not-nil-else-pop) | ||
| 413 | (byte-return | ||
| 414 | (comp-emit (list 'return (comp-slot-next))) | ||
| 415 | `(return ,(comp-slot-next))) | ||
| 416 | (byte-discard t) | ||
| 417 | (byte-dup | ||
| 418 | (comp-copy-slot-n (1- (comp-sp)))) | ||
| 419 | (byte-save-excursion) | ||
| 420 | (byte-save-window-excursion-OBSOLETE) | ||
| 421 | (byte-save-restriction) | ||
| 422 | (byte-catch) | ||
| 423 | (byte-unwind-protect) | ||
| 424 | (byte-condition-case) | ||
| 425 | (byte-temp-output-buffer-setup-OBSOLETE) | ||
| 426 | (byte-temp-output-buffer-show-OBSOLETE) | ||
| 427 | (byte-unbind-all) | ||
| 428 | (byte-set-marker) | ||
| 429 | (byte-match-beginning) | ||
| 430 | (byte-match-end) | ||
| 431 | (byte-upcase) | ||
| 432 | (byte-downcase) | ||
| 433 | (byte-string=) | ||
| 434 | (byte-string<) | ||
| 435 | (byte-equal) | ||
| 436 | (byte-nthcdr) | ||
| 437 | (byte-elt) | ||
| 438 | (byte-member) | ||
| 439 | (byte-assq) | ||
| 440 | (byte-nreverse) | ||
| 441 | (byte-setcar) | ||
| 442 | (byte-setcdr) | ||
| 443 | (byte-car-safe | ||
| 306 | (comp-emit-set-call `(call Fcar_safe ,(comp-slot)))) | 444 | (comp-emit-set-call `(call Fcar_safe ,(comp-slot)))) |
| 307 | ('byte-cdr-safe | 445 | (byte-cdr-safe |
| 308 | (comp-emit-set-call `(call Fcdr_safe ,(comp-slot)))) | 446 | (comp-emit-set-call `(call Fcdr_safe ,(comp-slot)))) |
| 309 | ('byte-length | 447 | (byte-nconc) |
| 310 | (comp-emit-set-call `(call Flength ,(comp-slot)))) | 448 | (byte-quo) |
| 311 | ('byte-list1 | 449 | (byte-rem) |
| 312 | (comp-limplify-listn 1)) | 450 | (byte-numberp) |
| 313 | ('byte-list2 | 451 | (byte-integerp) |
| 314 | (comp-limplify-listn 2)) | 452 | (byte-listN) |
| 315 | ('byte-list3 | 453 | (byte-concatN) |
| 316 | (comp-limplify-listn 3)) | 454 | (byte-insertN) |
| 317 | ('byte-list4 | 455 | (byte-stack-set) |
| 318 | (comp-limplify-listn 4)) | 456 | (byte-stack-set2) |
| 319 | ('byte-return | 457 | (byte-discardN) |
| 320 | (comp-emit (list 'return (comp-slot))) | 458 | (byte-switch) |
| 321 | `(return ,(comp-slot))) | 459 | (byte-constant |
| 322 | (_ (error "Unexpected LAP op %s" (symbol-name op)))))) | 460 | (comp-set-const (cadr inst)))))) |
| 323 | 461 | ||
| 324 | (defun comp-limplify (func) | 462 | (defun comp-limplify (func) |
| 325 | "Given FUNC and return compute its LIMPLE ir." | 463 | "Given FUNC and return compute its LIMPLE ir." |