X-Git-Url: http://repo.macrolet.net/gitweb/?a=blobdiff_plain;ds=sidebyside;f=src%2Fcode%2Ffd-stream.lisp;h=825933b809a33dd52f328a946facb47dff413637;hb=a160917364f85b38dc0826a5e3dcef87e3c4c62c;hp=8961da47b59f6b1a881f3c0f4c15fd0a5e829953;hpb=5c6b1ed3209c4cbd7ad7a97719c4518264a87b22;p=sbcl.git diff --git a/src/code/fd-stream.lisp b/src/code/fd-stream.lisp index 8961da4..825933b 100644 --- a/src/code/fd-stream.lisp +++ b/src/code/fd-stream.lisp @@ -187,7 +187,10 @@ (external-format :default) ;; fixed width, or function to call with a character (char-size 1 :type (or fixnum function)) - (output-bytes #'ill-out :type function)) + (output-bytes #'ill-out :type function) + ;; a boolean indicating whether the stream is bivalent. For + ;; internal use only. + (bivalent-p nil :type boolean)) (def!method print-object ((fd-stream fd-stream) stream) (declare (type stream stream)) (print-unreadable-object (fd-stream stream :type t :identity t) @@ -418,12 +421,14 @@ (defun stream-decoding-error (stream octets) (error 'stream-decoding-error + :external-format (stream-external-format stream) :stream stream ;; FIXME: dunno how to get at OCTETS currently, or even if ;; that's the right thing to report. :octets octets)) (defun stream-encoding-error (stream code) (error 'stream-encoding-error + :external-format (stream-external-format stream) :stream stream :code code)) @@ -821,10 +826,10 @@ ;;; correct on win32. However, none of the places that use it require ;;; further assurance than "may" versus "will definitely not". (defun sysread-may-block-p (stream) - #+win32 + #!+win32 ;; This answers T at EOF on win32, I think. (not (sb!win32:fd-listen (fd-stream-fd stream))) - #-win32 + #!-win32 (sb!unix:with-restarted-syscall (count errno) (sb!alien:with-alien ((read-fds (sb!alien:struct sb!unix:fd-set))) (sb!unix:fd-zero read-fds) @@ -2039,10 +2044,24 @@ (do-listen))))))) (do-listen))) (:unread - (setf (fd-stream-unread fd-stream) arg1) + ;; If the stream is bivalent, the user might follow an + ;; unread-char with a read-byte. In this case, the bookkeeping + ;; is simpler if we adjust the buffer head by the number of code + ;; units in the character. + ;; FIXME: there has to be a proper way to check for bivalence, + ;; right? + (if (fd-stream-bivalent-p fd-stream) + (decf (buffer-head (fd-stream-ibuf fd-stream)) + (fd-stream-character-size fd-stream arg1)) + (setf (fd-stream-unread fd-stream) arg1)) (setf (fd-stream-listen fd-stream) t)) (:close - (cond (arg1 ; We got us an abort on our hands. + ;; Drop input buffers + (setf (ansi-stream-in-index fd-stream) +ansi-stream-in-buffer-length+ + (ansi-stream-cin-buffer fd-stream) nil + (ansi-stream-in-buffer fd-stream) nil) + (cond (arg1 + ;; We got us an abort on our hands. (let ((outputp (fd-stream-obuf fd-stream)) (file (fd-stream-file fd-stream)) (orig (fd-stream-original fd-stream))) @@ -2308,6 +2327,7 @@ :buffering buffering :dual-channel-p dual-channel-p :external-format external-format + :bivalent-p (eq element-type :default) :char-size (external-format-char-size external-format) :timeout (if timeout