Philippe said:
ostream.SetBuffer(buf, SIZE); /// here is what I would like to do
TestOutStream(ostream);
cout << buf << endl;
The writting in the ostream (or an inherited class, of course) would
write in the buffer buf. The buffer overloading would also be managed.
Do such an std class exist?
What should I do?
You should write streambuf class, in this group archives and
c.l.c++.moderated you have lot of examples, how to do this, also
anu decent stl book should have it.
This is sample of two buffers to write/read strings via rpc...
class RpcOutBuf: public std::streambuf {
public:
RpcOutBuf(const std::string& sName, const std::string& sHost, unsigned
long ulP
virtual ~RpcOutBuf();
protected:
/**
Flushes buffer
*/
int flushBuffer();
/**
when buffer is full this function is called;
@param current character c
function will write current c, and all previous characters
*/
int overflow(int c);
/**
Synchronizes data with server
*/
int sync();
private:
/**
Service number on Rpc Server
*/
unsigned long ulSvcNum_;
/**
Constant which limits buffers size;
*/
static const int sizeOf = 2048;
/**
Internal buffer
*/
char szBuffer_[sizeOf+1];
/**
Rpc Client used for connection
*/
RpcClient rpcOutBufClient_;
};
class RpcInBuf: public std::streambuf {
public:
RpcInBuf(const std::string& sName, const std::string& sHost, unsigned
long ulPr
protected:
/**
Reads characters via RPC into buffer
*/
virtual int underflow();
private:
/**
Service number on Rpc server
*/
unsigned long ulSvcNum_;
/**
Constant which limits buffers size;
*/
static const int sizeOf = 2048;
/**
Internal buffer
*/
char szBuffer_[sizeOf+1];
/**
Rpc Client used for connection
*/
RpcClient rpcInBufClient_;
};
RpcOutBuf::RpcOutBuf(const std::string& sName, const std::string& sHost,
unsign
: ulSvcNum_(ulSvcNum),
rpcOutBufClient_(sName, sHost, ulProg, ulVer)
{
rpcOutBufClient_.regProc("outbuf", ulSvcNum_,
(xdrproc_t)xdr_wrapstring, (xdrproc_t)xdr_int);
setp(szBuffer_, szBuffer_+(sizeOf-1));
}
RpcOutBuf::~RpcOutBuf()
{
sync();
}
int RpcOutBuf::flushBuffer()
{
int num = pptr()-pbase();
try{
if ( num ) {
szBuffer_[num]=0;
int status;timeval t={5,0};
#ifdef DEBUG
std::clog<<"\nbuffer to send: \n"<<szBuffer_<<'\n';
#endif
char*ptr=szBuffer_;
if(rpcOutBufClient_.call("outbuf",(char*)&ptr, (char*)&status,
t) != R
{
rpcOutBufClient_.throwRpcClientError();
}
}
}catch(const std::exception& e)
{
std::cerr<<e.what()<<'\n';
return EOF;
}
pbump(-num);
return num;
}
/**
when buffer is full this function is called;
function will write current c, and all previous characters
*/
int RpcOutBuf:
verflow(int c)
{
if(c!=EOF){
*pptr() = c;
pbump(1);
}
if(flushBuffer() == EOF){ /// this is transmit error
return EOF;
}
return c;
}
/**
Synchronizes data with server
*/
int RpcOutBuf::sync(){
if(flushBuffer() == EOF){ /// this is transmit error
return -1;
}
return 0;
}
RpcInBuf::RpcInBuf(const std::string& sName, const std::string& sHost,
unsigned
:ulSvcNum_(ulSvcNum),
rpcInBufClient_(sName, sHost, ulProg, ulVer)
{
rpcInBufClient_.regProc("inbuf", ulSvcNum_,
(xdrproc_t)xdr_int, (xdrproc_t)xdr_wrapstring);
setg(szBuffer_, szBuffer_, szBuffer_); /// this is the place to init
ungetc ar
/// perhaps to put some chars in
buffer,
/// unused for now....
}
/**
Insert new characters into buffer
*/
int RpcInBuf::underflow()
{
if(gptr() < egptr())
{
return *gptr();
}
try {
int request=1;timeval t={5,0};
char*ptr=szBuffer_;
if(rpcInBufClient_.call("inbuf",
(char*)&request,
(char*)&ptr,
t
)!= RPC_SUCCESS
)
{
rpcInBufClient_.throwRpcClientError();
}
#ifdef DEBUF
std::clog<<"\nbuffer contains: \n"<<szBuffer_<<'\n';
#endif
} catch(const std::exception& e)
{
std::cerr<<e.what()<<'\n';
}
if(!strlen(szBuffer_))
{
std::cerr<<"End of file...\n";
return EOF;
}
setg(szBuffer_, szBuffer_, szBuffer_+strlen(szBuffer_));
return *gptr();
}
I wrote this some 10 years ago, don;t ask for explanations
Greets