// ### %read-from-string string eof-error-p eof-value start end preserve-whitespace // => object, position Value SYS_read_from_string_internal(Value arg1, Value arg2, Value arg3, Value arg4, Value arg5, Value arg6) { AbstractString * string = check_string(arg1); bool eof_error_p = (arg2 != NIL); bool preserve_whitespace = (arg6 != NIL); INDEX start; if (arg4 != NIL) start = check_index(arg4); else start = 0; INDEX end; if (arg5 != NIL) end = check_index(arg5); else end = string->length(); StringInputStream * in = new StringInputStream(string, start, end); Thread * const thread = current_thread(); Value result; Readtable * rt = check_readtable(thread->symbol_value(S_current_readtable)); if (preserve_whitespace) result = stream_read_preserving_whitespace(make_value(in), eof_error_p, arg3, false, thread, rt); else result = stream_read(make_value(in), eof_error_p, arg3, false, thread, rt); return thread->set_values(result, make_fixnum(in->offset())); }
bool BottleImpl::fromBytes(const Bytes& data) { String wrapper(data.get(),data.length()); StringInputStream sis; sis.add(wrapper); StreamConnectionReader reader; Route route; reader.reset(sis,NULL,route,data.length(),false); clear(); dirty = true; // for clarity if (!nested) { clear(); specialize(0); int code = reader.expectInt(); if (reader.isError()) { return false; } YMSG(("READ got top level code %d\n", code)); code = code & UNIT_MASK; if (code!=0) { specialize(code); } } int len = reader.expectInt(); if (reader.isError()) { return false; } YMSG(("READ bottle length %d\n", len)); for (int i=0; i<len; i++) { bool ok = fromBytes(reader); if (!ok) return false; } return true; }
void testSequence(char *seq, size_t len, const char *fmt, Bottle ref, bool testWrite = true) { char err[1024]; printf("\n"); printf("================================================\n"); printf(" READ %s\n", fmt); Bytes b1(seq, len); WireTwiddler tt; tt.configure(fmt, fmt); printf(">>> %s\n", tt.toString().c_str()); Bottle bot; checkTrue(tt.read(bot, b1), "Read failed"); snprintf(err, 1024, "%s: read %s, expected %s", fmt, bot.toString().c_str(), ref.toString().c_str()); checkTrue(bot == ref, err); printf("[1] %s: read %s as expected\n", fmt, bot.toString().c_str()); StringInputStream sis; sis.add(b1); sis.add(b1); WireTwiddlerReader twiddled_input(sis, tt); Route route; bot.clear(); twiddled_input.reset(); ConnectionReader::readFromStream(bot, twiddled_input); snprintf(err, 1024, "%s: read %s, expected %s", fmt, bot.toString().c_str(), ref.toString().c_str()); checkTrue(bot == ref, err); printf("[2] %s: read %s as expected\n", fmt, bot.toString().c_str()); bot.clear(); twiddled_input.reset(); ConnectionReader::readFromStream(bot, twiddled_input); snprintf(err, 1024, "%s: read %s, expected %s", fmt, bot.toString().c_str(), ref.toString().c_str()); checkTrue(bot == ref, err); printf("[3] %s: read %s as expected\n", fmt, bot.toString().c_str()); if (testWrite) { printf("\n"); printf("================================================\n"); printf(" WRITE %s\n", fmt); ManagedBytes output; checkTrue(tt.write(ref, output), "WRITE FAILED"); snprintf(err, 1024, "WRITE MISMATCH, length %zd, expected %zd", output.length(), len); checkTrue(output.length() == len, err); for (size_t i = 0; i < output.length(); i++) { snprintf(err, 1024, "WRITE MISMATCH, at %zd, have [%d:%c] expected [%d:%c]\n", i, output.get()[i], output.get()[i], seq[i], seq[i]); checkTrue(output.get()[i] == seq[i], err); } printf("[4] %s: wrote %s as expected\n", fmt, bot.toString().c_str()); } }
void BottleImpl::fromBinary(const char *text, int len) { String wrapper(text,len); StringInputStream sis; sis.add(wrapper); StreamConnectionReader reader; Route route; reader.reset(sis,NULL,route,len,false); read(reader); }
ConnectionReader& getReader() { writer.stopWrite(); String s = writer.toString(); sis.reset(); sis.add(s); Route r; reader.reset(sis, NULL, r, s.length(), textMode); return reader; }
void testRead() { report(0,"testing reading..."); StringInputStream sis; StringOutputStream sos; sis.add("Hello\ngood evening and welcome"); StreamConnectionReader sbr; Route route; sbr.reset(sis,NULL,route,10,true); String line = sbr.expectLine(); checkEqual(line,"Hello","one line"); }
void testTextReading() { report(0,"testing text-mode reading..."); PortCommand cmd; StringInputStream sis; StreamConnectionReader br; sis.add("d\r\n"); Route route; br.reset(sis,NULL,route,sis.toString().length(),true); cmd.read(br); checkEqual('d',cmd.getKey(),"basic data command"); }
bool getEnvelope(PortReader& envelope) { if (prev==nullptr) { return false; } StringInputStream sis; sis.add(prev->envelope.c_str()); sis.add("\r\n"); StreamConnectionReader sbr; Route route; sbr.reset(sis, nullptr, route, 0, true); return envelope.read(sbr); }
void testStreaming() { report(0,"testing streaming (just text mode)..."); BottleImpl bot; bot.addInt(5); bot.addString("hello"); BufferedConnectionWriter bbw(true); bot.write(bbw); String s; StringInputStream sis; StreamConnectionReader sbr; s = bbw.toString(); sis.add(s); Route route; sbr.reset(sis,NULL,route,s.length(),true); BottleImpl bot2; bot2.read(sbr); checkEqual(bot2.toString(),bot.toString(),"to/from stream"); }
void testRead() { report(0,"test reading..."); StringInputStream sis; sis.add("Hello my friend"); char buf[256]; sis.check(); Bytes b(buf,sizeof(buf)); int len = sis.read(b,0,5); checkEqual(len,5,"len of first read"); buf[len] = '\0'; checkEqual("Hello",buf,"first read"); char ch = sis.read(); checkEqual(ch,' ',"the space"); len = sis.read(b,0,2); checkEqual(len,2,"len of second read"); buf[len] = '\0'; checkEqual("my",buf,"second read"); }
void testReread() { report(0,"testing reread specialization is not broken..."); Bottle bot("10 20 30"); // first a specialized list Bottle bot2; { BufferedConnectionWriter writer(false); bot.write(writer); StringInputStream sis; sis.add(writer.toString()); StreamConnectionReader br; br.reset(sis,NULL,Route(),sis.toString().length(),false); bot2.read(br); //printf("bot is %s\n", bot.toString().c_str()); //printf("bot2 is %s\n", bot2.toString().c_str()); checkEqual(bot.size(),bot2.size(),"length check"); checkTrue(bot2.get(2).isInt(),"type check"); checkEqual(bot.toString().c_str(),bot2.toString().c_str(), "content check"); } bot.fromString("10 20 30.5"); // now an unspecialized list { BufferedConnectionWriter writer(false); bot.write(writer); StringInputStream sis; sis.add(writer.toString()); StreamConnectionReader br; br.reset(sis,NULL,Route(),sis.toString().length(),false); bot2.read(br); checkEqual(bot.size(),bot2.size(),"length check"); checkTrue(bot2.get(2).isDouble(),"type check"); checkEqual(bot.toString().c_str(),bot2.toString().c_str(), "content check"); } }
bool testSequence(char *seq, int len, const char *fmt, Bottle ref, bool testWrite = true) { printf("\n"); printf("================================================\n"); printf(" READ %s\n", fmt); Bytes b1(seq,len); WireTwiddler tt; tt.configure(fmt); printf(">>> %s\n", tt.toString().c_str()); Bottle bot; if (!tt.read(bot,b1)) { fprintf(stderr,"Read failed\n"); return 1; } if (bot!=ref) { printf("%s: read %s, expected %s\n", fmt, bot.toString().c_str(), ref.toString().c_str()); printf("MISMATCH\n"); exit(1); return false; } printf("[1] %s: read %s as expected\n", fmt, bot.toString().c_str()); StringInputStream sis; sis.add(b1); sis.add(b1); WireTwiddlerReader twiddled_input(sis,tt); Route route; StreamConnectionReader reader2; reader2.reset(twiddled_input,NULL,route,0,false); bot.clear(); twiddled_input.reset(); bot.read(reader2); if (bot!=ref) { printf("%s: read %s, expected %s\n", fmt, bot.toString().c_str(), ref.toString().c_str()); printf("MISMATCH\n"); exit(1); return false; } printf("[2] %s: read %s as expected\n", fmt, bot.toString().c_str()); StreamConnectionReader reader3; reader3.reset(twiddled_input,NULL,route,0,false); bot.clear(); twiddled_input.reset(); bot.read(reader3); if (bot!=ref) { printf("%s: read %s, expected %s\n", fmt, bot.toString().c_str(), ref.toString().c_str()); printf("MISMATCH\n"); exit(1); return false; } printf("[3] %s: read %s as expected\n", fmt, bot.toString().c_str()); if (testWrite) { printf("\n"); printf("================================================\n"); printf(" WRITE %s\n", fmt); ManagedBytes output; tt.write(ref,output); if (output.length()!=(size_t)len) { fprintf(stderr,"WRITE MISMATCH, length %d, expected %d\n", (int)output.length(), len); exit(1); return false; } for (size_t i=0; i<output.length(); i++) { if (output.get()[i] != seq[i]) { fprintf(stderr,"WRITE MISMATCH, at %d, have [%d:%c] expected [%d:%c]\n", (int)i, output.get()[i], output.get()[i], seq[i], seq[i]); exit(1); return false; } } printf("[4] %s: wrote %s as expected\n", fmt, bot.toString().c_str()); } return true; }
bool XmlRpcCarrier::write(Protocol& proto, SizedWriter& writer) { //XmlRpc::setVerbosity(10); StringOutputStream sos; StringInputStream sis; writer.write(sos); sis.reset(sos.toString()); String header; if (sender) { header = NetType::readLine(sis); } String body = NetType::readLine(sis); //printf("Asked to write: hdr %s body %s\n", // header.c_str(), body.c_str()); Value v; //printf("HEADER %s\n", header.c_str()); if (header[0]=='q') { body = "yarp.quit"; // XMLRPC does not need a quit message, this should get stripped return false; } Bottle *bot = v.asList(); //Bottle aux; bot->fromString(body.c_str()); ConstString methodName; if (sender) { methodName = bot->get(0).toString(); *bot = bot->tail(); } XmlRpcValue args; if (bot->size()==1) { toXmlRpcValue(bot->get(0),args); } else { toXmlRpcValue(v,args); } //printf("xmlrpc block to write is %s\n", args.toXml().c_str()); std::string req; if (sender) { const Address& addr = host.isValid()?host:proto.getStreams().getRemoteAddress(); XmlRpcClient c(addr.getName().c_str(),(addr.getPort()>0)?addr.getPort():80); c.generateRequest(methodName.c_str(),args); req = c.getRequest(); } else { XmlRpcServerConnection c(0,NULL); c.generateResponse(args.toXml()); req = c.getResponse(); } int start = 0; //printf("converts to %s\n", req.c_str()); if (sender) { if (req.length()<8) { fprintf(stderr, "XmlRpcCarrier fail, %s:%d\n", __FILE__, __LINE__); return false; } for (int i=0; i<(int)req.length(); i++) { if (req[i] == '\n') { start++; break; } start++; } if (!firstRound) { Bytes b((char*)http.c_str(),http.length()); proto.os().write(b); } firstRound = false; } Bytes b((char*)req.c_str()+start,req.length()-start); //printf("WRITING [%s]\n", req.c_str()+start); proto.os().write(b); return proto.os().isOk(); }
void fromConfig(const char *txt,Searchable& env, bool wipe=true) { StringInputStream sis; sis.add(txt); sis.add("\n"); if (wipe) { clear(); } String tag = ""; Bottle accum; bool done = false; do { bool isTag = false; bool including = false; String buf; bool good = true; buf = sis.readLine('\n',&good); while (good && !BottleImpl::isComplete(buf.c_str())) { buf += sis.readLine('\n',&good); } if (!good) { done = true; } if (!done) { including = false; if (buf.find("//")!=String::npos) { bool quoted = false; int comment = 0; for (unsigned int i=0; i<buf.length(); i++) { char ch = buf[i]; if (ch=='\"') { quoted = !quoted; } if (!quoted) { if (ch=='/') { comment++; if (comment==2) { //buf = buf.substr(0,buf.strstr("//")); buf = buf.substr(0,i); break; } } else { comment = 0; } } else { comment = 0; } } } // expand any environment references buf = expand(buf.c_str(),env,owner).c_str(); if (buf.length()>0 && buf[0]=='[') { size_t stop = buf.find("]"); if (stop!=String::npos) { buf = buf.substr(1,stop-1); size_t space = buf.find(" "); if (space!=String::npos) { Bottle bot(buf.c_str()); if (bot.size()>1) { if (bot.get(0).toString() == "include") { including = true; if (bot.size()>2) { if (tag!="") { if (accum.size()>=1) { putBottleCompat(tag.c_str(), accum); } tag = ""; } ConstString subName, fname; if (bot.size()==3) { // [include section "filename"] subName = bot.get(1).toString(); fname = bot.get(2).toString(); } else if (bot.size()==4) { // [include type section "filename"] ConstString key; key = bot.get(1).toString(); subName = bot.get(2).toString(); fname = bot.get(3).toString(); Bottle *target = getBottle(key.c_str()); if (target==NULL) { Bottle init; init.addString(key.c_str()); init.addString(subName.c_str()); putBottleCompat(key.c_str(), init); } else { target->addString(subName.c_str()); } } else { YARP_ERROR(Logger::get(), String("bad include")); return; } Property p; if (getBottle(subName)!=NULL) { p.fromString(getBottle(subName)->tail().toString()); //printf(">>> prior p %s\n", // p.toString().c_str()); } p.fromConfigFile(fname.c_str(), env, false); accum.fromString(p.toString()); tag = subName.c_str(); //printf(">>> tag %s accum %s\n", // tag.c_str(), // accum.toString().c_str()); if (tag!="") { if (accum.size()>=1) { Bottle b; b.addString(tag.c_str()); //Bottle& subList = b.addList(); //subList.copy(accum); b.append(accum); putBottleCompat(tag.c_str(), b); } tag = ""; } } else { tag = ""; ConstString fname = bot.get(1).toString(); //printf("Including %s\n", fname.c_str()); fromConfigFile(fname.c_str(), env, false); } } } if (bot.size()==2 && !including) { buf = bot.get(1).toString().c_str(); String key = bot.get(0).toString().c_str(); Bottle *target = getBottle(key.c_str()); if (target==NULL) { Bottle init; init.addString(key.c_str()); init.addString(buf.c_str()); putBottleCompat(key.c_str(),init); } else { target->addString(buf.c_str()); } } } if (!including) { isTag = true; } } } } if (!isTag && !including) { Bottle bot; bot.fromString(buf.c_str()); if (bot.size()>=1) { if (tag=="") { putBottleCompat(bot.get(0).toString().c_str(),bot); } else { if (bot.get(1).asString()=="=") { Bottle& b = accum.addList(); for (int i=0; i<bot.size(); i++) { if (i!=1) { b.add(bot.get(i)); } } } else { accum.addList().copy(bot); } } } } if (isTag||done) { if (tag!="") { if (accum.size()>=1) { putBottleCompat(tag.c_str(),accum); } tag = ""; } tag = buf; accum.clear(); accum.addString(tag.c_str()); if (tag!="") { if (getBottle(tag.c_str())!=NULL) { // merge data accum.append(getBottle(tag.c_str())->tail()); //printf("MERGE %s, got %s\n", tag.c_str(), // accum.toString().c_str()); } } } } while (!done); }
bool XmlRpcCarrier::write(ConnectionState& proto, SizedWriter& writer) { StringOutputStream sos; StringInputStream sis; writer.write(sos); sis.reset(sos.toString()); ConstString header; if (sender) { header = sis.readLine(); } ConstString body = sis.readLine(); Value v; if (header.length()>0 && header[0]=='q') { body = "yarp.quit"; // XMLRPC does not need a quit message, this should get stripped return false; } Bottle *bot = v.asList(); bot->fromString(body.c_str()); ConstString methodName; if (sender) { methodName = bot->get(0).toString(); *bot = bot->tail(); } XmlRpcValue args; if (bot->size()==1) { toXmlRpcValue(bot->get(0),args); } else { toXmlRpcValue(v,args); } std::string req; if (sender) { const Contact& addr = host.isValid()?host:proto.getStreams().getRemoteAddress(); XmlRpcClient c(addr.getHost().c_str(),(addr.getPort()>0)?addr.getPort():80); c.generateRequest(methodName.c_str(),args); req = c.getRequest(); } else { XmlRpcServerConnection c(0,NULL); c.generateResponse(args.toXml()); req = c.getResponse(); } int start = 0; if (sender) { if (req.length()<8) { fprintf(stderr, "XmlRpcCarrier fail, %s:%d\n", __FILE__, __LINE__); return false; } for (int i=0; i<(int)req.length(); i++) { if (req[i] == '\n') { start++; break; } start++; } if (!firstRound) { Bytes b((char*)http.c_str(),http.length()); proto.os().write(b); } firstRound = false; } Bytes b((char*)req.c_str()+start,req.length()-start); proto.os().write(b); return proto.os().isOk(); }
bool WireTwiddler::read(Bottle& bot, const Bytes& data) { StringInputStream sis; sis.add(data); WireTwiddlerReader twiddled_input(sis,*this); return ConnectionReader::readFromStream(bot,twiddled_input); }