(in-package #:monparser) (declaim (ftype (function (parser string) result) parse)) (defun parse (parser data) (funcall parser (make-instance 'cursor :data data) (make-instance 'cursor :data data))) (declaim (ftype (function (parser string) parser) append-on-failure)) (defun append-on-failure (p message) (lambda (start input) (let ((result (funcall p start input))) (if (failure-p result) (make-failure :place (failure-place result) :message (concatenate 'string message (failure-message result)) :priority (failure-priority result)) result)))) (defmacro defparser (name args parser) (let ((message (format nil "In ~a:~&" name))) (if (and (listp args) (every #'symbolp args)) (let (definition) (when (= (length args) 0) (push `(defparameter ,name (,name)) definition)) (push `(defun ,name (,@args) (append-on-failure ,parser ,message)) definition) (push 'progn definition) definition) (error "Malformed argument list."))))