summaryrefslogtreecommitdiff
path: root/streams.c
diff options
context:
space:
mode:
Diffstat (limited to 'streams.c')
-rw-r--r--streams.c85
1 files changed, 79 insertions, 6 deletions
diff --git a/streams.c b/streams.c
index d089b23..56cecc1 100644
--- a/streams.c
+++ b/streams.c
@@ -1,5 +1,6 @@
#include <u.h>
#include <libc.h>
+#include <bio.h>
#include "dat.h"
#include "fns.h"
@@ -9,6 +10,7 @@ typedef struct Stream Stream;
struct Stream
{
ulong fd;
+ Biobuf *bio;
int type;
int mode;
int nalias;
@@ -31,7 +33,7 @@ static Stream *streams;
static Stream *currentinput;
static Stream *currentoutput;
-Stream *openstreamfd(int, int, int);
+Stream *openstreamfd(int, Biobuf *, int, int);
Stream *getstreambyfd(int);
Stream *getstreambyalias(Rune *);
Stream *getstream(Term *);
@@ -39,8 +41,14 @@ Stream *getstream(Term *);
void
initstreams(void)
{
- currentinput = openstreamfd(0, TextStream, ReadStream);
- currentoutput = openstreamfd(1, TextStream, WriteStream);
+ int infd = dup(0, -1);
+ int outfd = dup(1, -1);
+
+ Biobuf *bioin = Bfdopen(infd, OREAD);
+ Biobuf *bioout = Bfdopen(outfd, OWRITE);
+
+ currentinput = openstreamfd(infd, bioin, TextStream, ReadStream);
+ currentoutput = openstreamfd(outfd, bioout, TextStream, WriteStream);
}
int
@@ -69,7 +77,13 @@ openstream(Rune *sourcesink, Rune *mode, Term *options, Term **stream)
*stream = permissionerror(L"open", L"source_sink", mkatom(sourcesink));
return 1;
}
- Stream *s = openstreamfd(fd, TextStream, smode);
+ Biobuf *bio = Bfdopen(fd, omode);
+ if(bio == nil){
+ *stream = permissionerror(L"open", L"source_sink", mkatom(sourcesink));
+ return 1;
+ }
+
+ Stream *s = openstreamfd(fd, bio, TextStream, smode);
*stream = mknumber(NumberInt, s->fd, 0);
return 0;
}
@@ -81,6 +95,9 @@ closestream(Term *t)
if(s == nil)
return;
+ Bterm(s->bio);
+ close(s->fd);
+
Stream *tmp;
Stream *prev = nil;
for(tmp = streams; tmp != nil; tmp = tmp->next){
@@ -154,11 +171,66 @@ isoutputstream(Term *t)
return 0;
}
+int
+istextstream(Term *t)
+{
+ Stream *s = getstream(t);
+ if(s && s->type == TextStream)
+ return 1;
+ else
+ return 0;
+}
+
+int
+isbinarystream(Term *t)
+{
+ Stream *s = getstream(t);
+ if(s && s->type == BinaryStream)
+ return 1;
+ else
+ return 0;
+}
+
+int
+readterm(Term *stream, Term *options, Term **term)
+{
+ USED(options);
+
+ Stream *s = getstream(stream);
+ if(s == nil){
+ *term = existenceerror(L"stream", stream);
+ return 1;
+ }
+ print(": ");
+ *term = parse(0, s->bio, 1);
+
+ return 0;
+}
+
+void
+writeterm(Term *stream, Term *options, Term *term)
+{
+ USED(options);
+
+ Stream *s = getstream(stream);
+ if(s == nil)
+ return;
+
+ int quoted = 0;
+ int ignoreops = 0;
+ int numbervars = 0;
+
+ Rune *output = prettyprint(term, quoted, ignoreops, numbervars);
+ Bprint(s->bio, "%S", output);
+ Bflush(s->bio);
+}
+
Stream *
-openstreamfd(int fd, int type, int mode)
+openstreamfd(int fd, Biobuf *bio, int type, int mode)
{
Stream *s = malloc(sizeof(Stream));
s->fd = fd;
+ s->bio = bio;
s->type = type;
s->mode = mode;
s->nalias = 0;
@@ -201,4 +273,5 @@ getstream(Term *t)
else if(t->tag == AtomTerm)
s = getstreambyalias(t->text);
return s;
-} \ No newline at end of file
+}
+