123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221 |
- /*
- * misc_util.h
- * -----------
- * Purpose: Various useful utility functions.
- * Notes : (currently none)
- * Authors: OpenMPT Devs
- * The OpenMPT source code is released under the BSD license. Read LICENSE for more details.
- */
- #pragma once
- #include "openmpt/all/BuildSettings.hpp"
- #include "mpt/base/span.hpp"
- #include "mpt/exception_text/exception_text.hpp"
- #include "mptAssert.h"
- #include "mptBaseMacros.h"
- #include "mptBaseTypes.h"
- #include "mptBaseUtils.h"
- #include "mptString.h"
- // old
- #include "mptBaseUtils.h"
- #include "mptStringFormat.h"
- #include "mptStringParse.h"
- #include "mptTime.h"
- #include <stdexcept>
- #include <optional>
- #include <vector>
- #include <cstdlib>
- #include <stdlib.h>
- OPENMPT_NAMESPACE_BEGIN
- namespace Util
- {
- // Insert a range of items [insStart, insEnd], and possibly shift item fix to the left.
- template<typename T>
- void InsertItem(const T insStart, const T insEnd, T &fix)
- {
- MPT_ASSERT(insEnd >= insStart);
- if(fix >= insStart)
- {
- fix += (insEnd - insStart + 1);
- }
- }
- // Insert a range of items [insStart, insEnd], and possibly shift items in range [fixStart, fixEnd] to the right.
- template<typename T>
- void InsertRange(const T insStart, const T insEnd, T &fixStart, T &fixEnd)
- {
- MPT_ASSERT(insEnd >= insStart);
- const T insLength = insEnd - insStart + 1;
- if(fixStart >= insEnd)
- {
- fixStart += insLength;
- }
- if(fixEnd >= insEnd)
- {
- fixEnd += insLength;
- }
- }
- // Delete a range of items [delStart, delEnd], and possibly shift item fix to the left.
- template<typename T>
- void DeleteItem(const T delStart, const T delEnd, T &fix)
- {
- MPT_ASSERT(delEnd >= delStart);
- if(fix > delEnd)
- {
- fix -= (delEnd - delStart + 1);
- }
- }
- // Delete a range of items [delStart, delEnd], and possibly shift items in range [fixStart, fixEnd] to the left.
- template<typename T>
- void DeleteRange(const T delStart, const T delEnd, T &fixStart, T &fixEnd)
- {
- MPT_ASSERT(delEnd >= delStart);
- const T delLength = delEnd - delStart + 1;
- if(delStart < fixStart && delEnd < fixStart)
- {
- // cut part is before loop start
- fixStart -= delLength;
- fixEnd -= delLength;
- } else if(delStart < fixStart && delEnd < fixEnd)
- {
- // cut part is partly before loop start
- fixStart = delStart;
- fixEnd -= delLength;
- } else if(delStart >= fixStart && delEnd < fixEnd)
- {
- // cut part is in the loop
- fixEnd -= delLength;
- } else if(delStart >= fixStart && delStart < fixEnd && delEnd > fixEnd)
- {
- // cut part is partly before loop end
- fixEnd = delStart;
- }
- }
- template<typename T, std::size_t n>
- class fixed_size_queue
- {
- private:
- T buffer[n+1];
- std::size_t read_position;
- std::size_t write_position;
- public:
- fixed_size_queue() : read_position(0), write_position(0)
- {
- return;
- }
- void clear()
- {
- read_position = 0;
- write_position = 0;
- }
- std::size_t read_size() const
- {
- if ( write_position > read_position )
- {
- return write_position - read_position;
- } else if ( write_position < read_position )
- {
- return write_position - read_position + n + 1;
- } else
- {
- return 0;
- }
- }
- std::size_t write_size() const
- {
- if ( write_position > read_position )
- {
- return read_position - write_position + n;
- } else if ( write_position < read_position )
- {
- return read_position - write_position - 1;
- } else
- {
- return n;
- }
- }
- bool push( const T & v )
- {
- if ( !write_size() )
- {
- return false;
- }
- buffer[write_position] = v;
- write_position = ( write_position + 1 ) % ( n + 1 );
- return true;
- }
- bool pop() {
- if ( !read_size() )
- {
- return false;
- }
- read_position = ( read_position + 1 ) % ( n + 1 );
- return true;
- }
- T peek() {
- if ( !read_size() )
- {
- return T();
- }
- return buffer[read_position];
- }
- const T * peek_p()
- {
- if ( !read_size() )
- {
- return nullptr;
- }
- return &(buffer[read_position]);
- }
- const T * peek_next_p()
- {
- if ( read_size() < 2 )
- {
- return nullptr;
- }
- return &(buffer[(read_position+1)%(n+1)]);
- }
- };
- } // namespace Util
- #if MPT_OS_WINDOWS
- template <typename Tstring, typename Tbuf, typename Tsize>
- Tstring ParseMaybeNullTerminatedStringFromBufferWithSizeInBytes(const Tbuf *buf, Tsize sizeBytes)
- {
- // REG_SZ may contain a single NUL terminator, multiple NUL terminators, or no NUL terminator at all
- return Tstring(reinterpret_cast<const typename Tstring::value_type*>(buf), reinterpret_cast<const typename Tstring::value_type*>(buf) + (sizeBytes / sizeof(typename Tstring::value_type))).c_str();
- }
- #endif // MPT_OS_WINDOWS
- OPENMPT_NAMESPACE_END
|