[Vm-dev] [commit][3092] Fix line-buffered input in
sqFilePluginBasicPrims. c when buffer size > 1.
commits at squeakvm.org
commits at squeakvm.org
Fri Oct 3 16:44:43 UTC 2014
Revision: 3092
Author: eliot
Date: 2014-10-03 09:44:41 -0700 (Fri, 03 Oct 2014)
Log Message:
-----------
Fix line-buffered input in sqFilePluginBasicPrims.c when buffer size > 1.
fread cannot be relied upon to answer lines.
Modified Paths:
--------------
trunk/platforms/Cross/plugins/FilePlugin/sqFilePluginBasicPrims.c
Property Changed:
----------------
trunk/platforms/Cross/plugins/sqPluginsSCCSVersion.h
Modified: trunk/platforms/Cross/plugins/FilePlugin/sqFilePluginBasicPrims.c
===================================================================
--- trunk/platforms/Cross/plugins/FilePlugin/sqFilePluginBasicPrims.c 2014-10-03 00:09:21 UTC (rev 3091)
+++ trunk/platforms/Cross/plugins/FilePlugin/sqFilePluginBasicPrims.c 2014-10-03 16:44:41 UTC (rev 3092)
@@ -298,20 +298,24 @@
sqInt
sqFileStdioHandlesInto(SQFile files[3])
{
-#if defined(_IONBF) && 0
+ /* streams connected to a terminal are supposed to be line-buffered anyway.
+ * And for some reason this has no effect on e.g. Mac OS X. So use
+ * fgets instead of fread when reading from these streams.
+ */
+#if defined(_IOLBF) && 0
if (isatty(fileno(stdin)))
-# if 0
- setvbuf(stdin,0,_IONBF,1);
-# else
- setvbuf(stdin,0,_IOFBF,0);
-# endif
+ setvbuf(stdin,0,_IOLBF,0);
#endif
files[0].sessionID = thisSession;
files[0].file = stdin;
files[0].fileSize = 0;
files[0].writable = false;
files[0].lastOp = READ_OP;
+#if 0
files[0].isStdioStream = true;
+#else
+ files[0].isStdioStream = isatty(fileno(stdin));
+#endif
files[0].lastChar = EOF;
files[1].sessionID = thisSession;
@@ -347,6 +351,10 @@
#if COGMTVM
sqInt myThreadIndex;
#endif
+#if COGMTVM && SPURVM
+ int wasPinned;
+ sqInt bufferOop = (sqInt)byteArrayIndex - BaseHeaderSize;
+#endif
if (!sqFileValid(f))
return interpreterProxy->success(false);
@@ -359,8 +367,15 @@
fseek(file, 0, SEEK_CUR); /* seek between writing and reading */
}
dst = byteArrayIndex + startIndex;
+ if (f->isStdioStream) {
#if COGMTVM
- if (f->isStdioStream) {
+# if SPURVM
+ if (!(wasPinned = interpreterProxy->isPinned(bufferOop))) {
+ if (!(bufferOop = interpreterProxy->pinObject(bufferOop)))
+ return 0;
+ dst = bufferOop + BaseHeaderSize + startIndex;
+ }
+# else
if (interpreterProxy->isInMemory((sqInt)f)
&& interpreterProxy->isYoung((sqInt)f)
|| interpreterProxy->isInMemory((sqInt)dst)
@@ -368,17 +383,37 @@
interpreterProxy->primitiveFailFor(PrimErrObjectMayMove);
return 0;
}
+# endif
myThreadIndex = interpreterProxy->disownVM(DisownVMLockOutFullGC);
- }
-#endif
- do {
- clearerr(file);
- bytesRead = fread(dst, 1, count, file);
- } while (bytesRead <= 0 && ferror(file) && errno == EINTR);
+#endif /* COGMTVM */
+ /* Line buffering in fread can't be relied upon, at least on Mac OS X
+ * and mingw win32. So do it the hard way.
+ */
+ bytesRead = 0;
+ do {
+ clearerr(file);
+ if (fread(dst, 1, 1, file) == 1) {
+ bytesRead += 1;
+ if (dst[bytesRead-1] == '\n'
+ || dst[bytesRead-1] == '\r')
+ break;
+ }
+ }
+ while (bytesRead <= 0 && ferror(file) && errno == EINTR);
#if COGMTVM
- if (f->isStdioStream)
interpreterProxy->ownVM(myThreadIndex);
-#endif
+# if SPURVM
+ if (!wasPinned)
+ interpreterProxy->unpinObject(bufferOop);
+# endif
+#endif /* COGMTVM */
+ }
+ else
+ do {
+ clearerr(file);
+ bytesRead = fread(dst, 1, count, file);
+ }
+ while (bytesRead <= 0 && ferror(file) && errno == EINTR);
/* support for skipping back 1 character for stdio streams */
if (f->isStdioStream)
if (bytesRead > 0)
Property changes on: trunk/platforms/Cross/plugins/sqPluginsSCCSVersion.h
___________________________________________________________________
Modified: checkindate
- Mon Jun 16 13:39:17 PDT 2014
+ Fri Oct 3 09:44:15 PDT 2014
More information about the Vm-dev
mailing list