88#include < boost/wave.hpp>
99#include < boost/wave/cpplexer/cpp_lex_token.hpp>
1010#include < boost/wave/cpplexer/cpp_lex_iterator.hpp>
11+ #include < unordered_set>
1112
1213#include " nbl/asset/utils/IShaderCompiler.h"
1314
@@ -191,6 +192,7 @@ class context : private boost::noncopyable
191192 context (target_iterator_type const & first_, target_iterator_type const & last_, char const * fname, preprocessing_hooks const & hooks_)
192193 : first(first_), last(last_), filename(fname)
193194 , has_been_initialized(false )
195+ , current_filename(fname)
194196 , current_relative_filename(fname)
195197 , macros(*this_ ())
196198 , language(language_support(
@@ -440,6 +442,32 @@ class context : private boost::noncopyable
440442 }
441443
442444 public:
445+ #if BOOST_WAVE_SUPPORT_PRAGMA_ONCE != 0
446+ void set_current_filename (char const * real_name)
447+ {
448+ current_filename = real_name;
449+ }
450+ std::string const & get_current_filename () const
451+ {
452+ return current_filename;
453+ }
454+
455+ bool has_pragma_once (std::string const & filename_) const
456+ {
457+ return pragma_once_headers.contains (filename_);
458+ }
459+ bool add_pragma_once_header (std::string const & filename_, std::string const & guard_name)
460+ {
461+ get_hooks ().detected_include_guard (derived (), filename_, guard_name);
462+ return pragma_once_headers.emplace (filename_).second ;
463+ }
464+ bool add_pragma_once_header (token_type const & pragma_, std::string const & filename_)
465+ {
466+ get_hooks ().detected_pragma_once (derived (), pragma_, filename_);
467+ return pragma_once_headers.emplace (filename_).second ;
468+ }
469+ #endif
470+
443471 void set_current_relative_filename (char const * real_name)
444472 {
445473 current_relative_filename = real_name;
@@ -464,12 +492,16 @@ class context : private boost::noncopyable
464492 const std::string filename; // associated main filename
465493 bool has_been_initialized; // set cwd once
466494
495+ std::string current_filename; // real name of current preprocessed file
467496 std::string current_relative_filename; // real relative name of current preprocessed file
468497
469498 // Nabla Additions Start
470499 // these are temporaries!
471500 system::path current_dir;
472501 core::string located_include_content;
502+ #if BOOST_WAVE_SUPPORT_PRAGMA_ONCE != 0
503+ std::unordered_set<std::string> pragma_once_headers;
504+ #endif
473505 // Cache Additions
474506 bool cachingRequested = false ;
475507 std::vector<IShaderCompiler::CCache::SEntry::SPreprocessingDependency> dependencies = {};
@@ -525,6 +557,11 @@ template<> inline bool boost::wave::impl::pp_iterator_functor<nbl::wave::context
525557 return false ;
526558 }
527559
560+ #if BOOST_WAVE_SUPPORT_PRAGMA_ONCE != 0
561+ if (ctx.has_pragma_once (result.absolutePath .string ()))
562+ return true ;
563+ #endif
564+
528565 // If caching was requested, push a new SDependency onto dependencies
529566 if (ctx.cachingRequested ) {
530567 ctx.dependencies .emplace_back (ctx.get_current_directory (), file_path, standardInclude, std::move (result.hash ));
@@ -559,6 +596,9 @@ template<> inline bool boost::wave::impl::pp_iterator_functor<nbl::wave::context
559596 must_emit_line_directive = true ;
560597
561598 act_pos.set_file (iter_ctx->filename ); // initialize file position
599+ #if BOOST_WAVE_SUPPORT_PRAGMA_ONCE != 0
600+ ctx.set_current_filename (result.absolutePath .string ().c_str ());
601+ #endif
562602
563603 ctx.set_current_relative_filename (file_path.c_str ());
564604 iter_ctx->real_relative_filename = file_path.c_str ();
0 commit comments