summaryrefslogtreecommitdiffstats
path: root/src/boost/libs/exception/example/example_io.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/boost/libs/exception/example/example_io.cpp')
-rw-r--r--src/boost/libs/exception/example/example_io.cpp209
1 files changed, 209 insertions, 0 deletions
diff --git a/src/boost/libs/exception/example/example_io.cpp b/src/boost/libs/exception/example/example_io.cpp
new file mode 100644
index 00000000..f4893328
--- /dev/null
+++ b/src/boost/libs/exception/example/example_io.cpp
@@ -0,0 +1,209 @@
+//Copyright (c) 2006-2009 Emil Dotchevski and Reverge Studios, Inc.
+
+//Distributed under the Boost Software License, Version 1.0. (See accompanying
+//file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
+
+//This program simulates errors on copying simple data files. It demonstrates
+//typical Boost Exception usage.
+
+//The output from this program can vary depending on the platform.
+
+#include <boost/throw_exception.hpp>
+#include <boost/exception/info.hpp>
+#include <boost/exception/get_error_info.hpp>
+#include <boost/exception/diagnostic_information.hpp>
+#include <boost/exception/errinfo_file_open_mode.hpp>
+#include <boost/exception/errinfo_file_handle.hpp>
+#include <boost/exception/errinfo_file_name.hpp>
+#include <boost/exception/errinfo_api_function.hpp>
+#include <boost/exception/errinfo_errno.hpp>
+#include <boost/shared_ptr.hpp>
+#include <boost/weak_ptr.hpp>
+#include <iostream>
+
+typedef boost::error_info<struct tag_file_name_src,std::string> errinfo_src_file_name;
+typedef boost::error_info<struct tag_file_name_dst,std::string> errinfo_dst_file_name;
+
+char const data[] = "example";
+size_t const data_size = sizeof(data);
+
+class
+error: //Base for all exception objects we throw.
+ public virtual std::exception,
+ public virtual boost::exception
+ {
+ public:
+
+ char const *
+ what() const BOOST_NOEXCEPT_OR_NOTHROW
+ {
+ return "example_io error";
+ }
+
+ protected:
+
+ ~error() BOOST_NOEXCEPT_OR_NOTHROW
+ {
+ }
+ };
+
+struct open_error: virtual error { };
+struct read_error: virtual error { };
+struct write_error: virtual error { };
+struct fopen_error: virtual open_error { };
+struct fread_error: virtual read_error { };
+struct fwrite_error: virtual write_error { };
+
+boost::shared_ptr<FILE>
+my_fopen( char const * name, char const * mode )
+ {
+ if( FILE * f = ::fopen(name,mode) )
+ return boost::shared_ptr<FILE>(f,fclose);
+ else
+ BOOST_THROW_EXCEPTION(fopen_error() <<
+ boost::errinfo_errno (errno) <<
+ boost::errinfo_file_name(name) <<
+ boost::errinfo_file_open_mode(mode) <<
+ boost::errinfo_api_function("fopen"));
+ }
+
+void
+my_fread( void * buffer, size_t size, size_t count, boost::shared_ptr<FILE> const & stream )
+ {
+ assert(stream);
+ if( count!=fread(buffer,size,count,stream.get()) || ferror(stream.get()) )
+ BOOST_THROW_EXCEPTION(fread_error() <<
+ boost::errinfo_api_function("fread") <<
+ boost::errinfo_errno(errno) <<
+ boost::errinfo_file_handle(boost::weak_ptr<FILE>(stream)));
+ }
+
+void
+my_fwrite( void const * buffer, size_t size, size_t count, boost::shared_ptr<FILE> const & stream )
+ {
+ assert(stream);
+ if( count!=fwrite(buffer,size,count,stream.get()) || ferror(stream.get()) )
+ BOOST_THROW_EXCEPTION(fwrite_error() <<
+ boost::errinfo_api_function("fwrite") <<
+ boost::errinfo_errno(errno) <<
+ boost::errinfo_file_handle(boost::weak_ptr<FILE>(stream)));
+ }
+
+void
+reset_file( char const * file_name )
+ {
+ (void) my_fopen(file_name,"wb");
+ }
+
+void
+create_data( char const * file_name )
+ {
+ boost::shared_ptr<FILE> f = my_fopen(file_name,"wb");
+ my_fwrite( data, 1, data_size, f );
+ }
+
+void
+copy_data( char const * src_file_name, char const * dst_file_name )
+ {
+ boost::shared_ptr<FILE> src = my_fopen(src_file_name,"rb");
+ boost::shared_ptr<FILE> dst = my_fopen(dst_file_name,"wb");
+ try
+ {
+ char buffer[data_size];
+ my_fread( buffer, 1, data_size, src );
+ my_fwrite( buffer, 1, data_size, dst );
+ }
+ catch(
+ boost::exception & x )
+ {
+ if( boost::weak_ptr<FILE> const * f=boost::get_error_info<boost::errinfo_file_handle>(x) )
+ if( boost::shared_ptr<FILE> fs = f->lock() )
+ {
+ if( fs==src )
+ x << boost::errinfo_file_name(src_file_name);
+ else if( fs==dst )
+ x << boost::errinfo_file_name(dst_file_name);
+ }
+ x <<
+ errinfo_src_file_name(src_file_name) <<
+ errinfo_dst_file_name(dst_file_name);
+ throw;
+ }
+ }
+
+void
+dump_copy_info( boost::exception const & x )
+ {
+ if( std::string const * src = boost::get_error_info<errinfo_src_file_name>(x) )
+ std::cerr << "Source file name: " << *src << "\n";
+ if( std::string const * dst = boost::get_error_info<errinfo_dst_file_name>(x) )
+ std::cerr << "Destination file name: " << *dst << "\n";
+ }
+
+void
+dump_file_info( boost::exception const & x )
+ {
+ if( std::string const * fn = boost::get_error_info<boost::errinfo_file_name>(x) )
+ std::cerr << "File name: " << *fn << "\n";
+ }
+
+void
+dump_clib_info( boost::exception const & x )
+ {
+ if( int const * err=boost::get_error_info<boost::errinfo_errno>(x) )
+ std::cerr << "OS error: " << *err << "\n";
+ if( char const * const * fn=boost::get_error_info<boost::errinfo_api_function>(x) )
+ std::cerr << "Failed function: " << *fn << "\n";
+ }
+
+void
+dump_all_info( boost::exception const & x )
+ {
+ std::cerr << "-------------------------------------------------\n";
+ dump_copy_info(x);
+ dump_file_info(x);
+ dump_clib_info(x);
+ std::cerr << "\nOutput from diagnostic_information():\n";
+ std::cerr << diagnostic_information(x);
+ }
+
+int
+main()
+ {
+ try
+ {
+ create_data( "tmp1.txt" );
+ copy_data( "tmp1.txt", "tmp2.txt" ); //This should succeed.
+
+ reset_file( "tmp1.txt" ); //Creates empty file.
+ try
+ {
+ copy_data( "tmp1.txt", "tmp2.txt" ); //This should fail, tmp1.txt is empty.
+ }
+ catch(
+ read_error & x )
+ {
+ std::cerr << "\nCaught 'read_error' exception.\n";
+ dump_all_info(x);
+ }
+
+ remove( "tmp1.txt" );
+ remove( "tmp2.txt" );
+ try
+ {
+ copy_data( "tmp1.txt", "tmp2.txt" ); //This should fail, tmp1.txt does not exist.
+ }
+ catch(
+ open_error & x )
+ {
+ std::cerr << "\nCaught 'open_error' exception.\n";
+ dump_all_info(x);
+ }
+ }
+ catch(
+ ... )
+ {
+ std::cerr << "\nCaught unexpected exception!\n";
+ std::cerr << boost::current_exception_diagnostic_information();
+ }
+ }