Thread: create fstream from raw file descriptor

  1. #16
    Registered User
    Join Date
    Oct 2006
    Posts
    3,445
    I will try that when I get a chance, but it will have to wait until monday, as I am done with work for the week. I'll let you know the results when I have them.

  2. #17
    Registered User
    Join Date
    Oct 2006
    Posts
    3,445
    I was able to debug the program... had to do it from the command line because it is a multi-process server, so I had to attach to a child process, but I was able to find the spot where it crashed.

    the line from the debugger was:
    Code:
    0xb7d01adc in std::istream::istream::sentry::sentry () from /usr/lib/libstdc++.so.6
    I'm not really sure where to go from here.

  3. #18
    Cat without Hat CornedBee's Avatar
    Join Date
    Apr 2003
    Posts
    8,895
    Hmm, looks like the problem is in Boost.Iostreams after all. Most likely, it crashes when trying to skip whitespace. Unless the streambuf is for some reason null - that would crash there, too. Can you ensure that
    Code:
    assert(static_cast<std::istream&>(stream).rdbuf());
    just before the I/O operation that leads to the crash?
    All the buzzt!
    CornedBee

    "There is not now, nor has there ever been, nor will there ever be, any programming language in which it is the least bit difficult to write bad code."
    - Flon's Law

  4. #19
    Registered User
    Join Date
    Oct 2006
    Posts
    3,445
    inserting that line causes it to crash at that line.

  5. #20
    Cat without Hat CornedBee's Avatar
    Join Date
    Apr 2003
    Posts
    8,895
    The call to rdbuf() crashes? Now that is seriously weird. This is the implementation:
    Code:
         basic_streambuf<_CharT, _Traits>*
          rdbuf() const
          { return _M_streambuf; }
    Or does the assertion simply fail?
    All the buzzt!
    CornedBee

    "There is not now, nor has there ever been, nor will there ever be, any programming language in which it is the least bit difficult to write bad code."
    - Flon's Law

  6. #21
    Registered User
    Join Date
    Oct 2006
    Posts
    3,445
    the debugger shows that it crashes (SIGSEGV) right at the assert() line. In fact, it doesn't even show that it entered the rdbuf() function.

  7. #22
    Cat without Hat CornedBee's Avatar
    Join Date
    Apr 2003
    Posts
    8,895
    OK, I'm stumped.
    All the buzzt!
    CornedBee

    "There is not now, nor has there ever been, nor will there ever be, any programming language in which it is the least bit difficult to write bad code."
    - Flon's Law

  8. #23
    Registered User
    Join Date
    Sep 2010
    Posts
    1

    Correct way to use boost::iostreams::file_descriptor

    I know this is an old thread but in case anyone else finds this:

    Try using boost::iostreams::file_descriptor like this:

    Code:
    int fd = open("filename.txt", O_RDWR);
    if (fd == -1) throw "Failed to open file";
    
    io::stream<io::file_descriptor> stream(fd, true);
    stream is now an std::iostream which you can both read and write to and of course fd is the file descriptor which you can lock.

  9. #24
    Registered User
    Join Date
    Feb 2011
    Posts
    1

    Thumbs up Test code to create fstream from raw file desc/FILE*

    Well, after the better part of a day of dabbling in the black arts of the various C++ streams classes, I've constructed the following test code that _seems_ to work, and I thought it would be nice to share. I'm not really sure it works properly, so I welcome review by those more steeped in the black arts.

    Code:
    #include <fstream>
    #include <iostream>
    #include <string>
    #include <cmath>
    #include <cassert>
    #include <cstdio>
    #include <stdlib.h>
    #include <string.h>
    #include <ext/stdio_filebuf.h>
    
    using namespace std;
    
    
    //std::ofstream stream_002;
    
    int main(){
    	char *f_template;
    	f_template = new char(12);
    	memcpy(f_template, "/tmp/XXXXXX", 12);
    	int fd = mkstemp(f_template);
    	std::cout << "File Descriptor # is: " << fd << " file name = " << f_template <<std::endl;
    
    //	FILE *frp=fdopen(fd, "r"); // convert it into a FILE *
    	FILE *fwp=fdopen(fd, "w"); // convert it into a FILE *
    
    // create a file buffer(NOT an iostream yet) from FILE *
    //	__gnu_cxx::stdio_filebuf<char> frb (frp, ios_base::in);
    
    // Uses:
    //   stdio_filebuf (std::__c_file *__f, std::ios_base::openmode __mode, size_t __size=static_cast< size_t >(BUFSIZ))
    	__gnu_cxx::stdio_filebuf<char> fwb (fwp, std::ios_base::out);
    // so   fwb   is of type   stdio_filebuf
    
    //	istream my_temp_in (&frb);    // create a stream from file buffer
    
    	std::iostream my_temp_stream_out (&fwb);    // create a stream from file buffer
    
    	std::fstream my_temp_fstream;
    
    
    //	streambuf *bsbp;
    //	bsbp = my_temp_out.rdbuf();
    //	my_temp_fstream.rdbuf(bsbp);
    	my_temp_fstream.std::ios::rdbuf(my_temp_stream_out.rdbuf());
    
    //	my_temp_out << "iostream : Some test text" << std::endl;
    //	my_temp_out.flush();
    
    	my_temp_fstream << "fstream : Some test text" << std::endl;
    	my_temp_fstream.close();
    //	while(1){}
    // Now take a look in your temp directory for the file
    //name printed from the above cout statement. If you cat it out,
    //you should see the "test text".
    	return 0;
    }

  10. #25
    Thang Le thavali's Avatar
    Join Date
    Jan 2011
    Location
    Earth
    Posts
    20
    (from: Streams and File Descriptors - The GNU C Library)

    11.1.1 Streams and File Descriptors

    When you want to do input or output to a file, you have a choice of two basic mechanisms for representing the connection between your program and the file: file descriptors and streams. File descriptors are represented as objects of type int, while streams are represented as FILE * objects.

    File descriptors provide a primitive, low-level interface to input and output operations. Both file descriptors and streams can represent a connection to a device (such as a terminal), or a pipe or socket for communicating with another process, as well as a normal file. But, if you want to do control operations that are specific to a particular kind of device, you must use a file descriptor; there are no facilities to use streams in this way. You must also use file descriptors if your program needs to do input or output in special modes, such as nonblocking (or polled) input (see File Status Flags).

    Streams provide a higher-level interface, layered on top of the primitive file descriptor facilities. The stream interface treats all kinds of files pretty much alike—the sole exception being the three styles of buffering that you can choose (see Stream Buffering).

    The main advantage of using the stream interface is that the set of functions for performing actual input and output operations (as opposed to control operations) on streams is much richer and more powerful than the corresponding facilities for file descriptors. The file descriptor interface provides only simple functions for transferring blocks of characters, but the stream interface also provides powerful formatted input and output functions (printf and scanf) as well as functions for character- and line-oriented input and output.

    Since streams are implemented in terms of file descriptors, you can extract the file descriptor from a stream and perform low-level operations directly on the file descriptor. You can also initially open a connection as a file descriptor and then make a stream associated with that file descriptor.

    In general, you should stick with using streams rather than file descriptors, unless there is some specific operation you want to do that can only be done on a file descriptor. If you are a beginning programmer and aren't sure what functions to use, we suggest that you concentrate on the formatted input functions (see Formatted Input) and formatted output functions (see Formatted Output).

    If you are concerned about portability of your programs to systems other than GNU, you should also be aware that file descriptors are not as portable as streams. You can expect any system running ISO C to support streams, but non-GNU systems may not support file descriptors at all, or may only implement a subset of the GNU functions that operate on file descriptors. Most of the file descriptor functions in the GNU library are included in the POSIX.1 standard, however.

    ==========================

    anyone please present by a example about this ? how to open a connection as a file descriptor and then make a stream associated with that file descriptor ?.
    Last edited by thavali; 02-13-2011 at 08:39 AM.

  11. #26
    Thang Le thavali's Avatar
    Join Date
    Jan 2011
    Location
    Earth
    Posts
    20
    anyone has any idea ?

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Formatting the contents of a text file
    By dagorsul in forum C++ Programming
    Replies: 2
    Last Post: 04-29-2008, 12:36 PM
  2. gcc link external library
    By spank in forum C Programming
    Replies: 6
    Last Post: 08-08-2007, 03:44 PM
  3. Inventory records
    By jsbeckton in forum C Programming
    Replies: 23
    Last Post: 06-28-2007, 04:14 AM
  4. C++ std routines
    By siavoshkc in forum C++ Programming
    Replies: 33
    Last Post: 07-28-2006, 12:13 AM
  5. Simple File encryption
    By caroundw5h in forum C Programming
    Replies: 2
    Last Post: 10-13-2004, 10:51 PM