# See './mkChangelog -h' for help.
#
SET(LIBZYPP_MAJOR "15")
-SET(LIBZYPP_COMPATMINOR "5")
-SET(LIBZYPP_MINOR "9")
+SET(LIBZYPP_COMPATMINOR "10")
+SET(LIBZYPP_MINOR "10")
SET(LIBZYPP_PATCH "0")
#
-# LAST RELEASED: 15.9.0 (5)
+# LAST RELEASED: 15.10.0 (10)
# (The number in parenthesis is LIBZYPP_COMPATMINOR)
#=======
-------------------------------------------------------------------
+Thu Jul 30 16:13:49 CEST 2015 - ma@suse.de
+
+- Resolver: Track changed requested locales and adjust installed
+ packages accordingly. (part of FATE#318099)
+- Testcase: Store autoinstalled packages
+- Locale: Make it IdString based
+- Get rid of std::tr1:: hashes
+- Flags: Fix to work with 'enum class'
+- Hide away resolver internals
+- version 15.10.0 (10)
+
+-------------------------------------------------------------------
+Thu Jul 30 01:13:30 CEST 2015 - ma@suse.de
+
+- Update zypp-po.tar.bz2
+
+-------------------------------------------------------------------
+Tue Jul 28 14:14:54 CEST 2015 - ma@suse.de
+
+- Update sle-zypp-po.tar.bz2
+
+-------------------------------------------------------------------
+Mon Jul 27 09:30:38 CEST 2015 - ma@suse.de
+
+- Update zypp-po.tar.bz2
+
+-------------------------------------------------------------------
+Sun Jul 26 01:13:37 CEST 2015 - ma@suse.de
+
+- Update zypp-po.tar.bz2
+
+-------------------------------------------------------------------
+Thu Jul 16 01:13:33 CEST 2015 - ma@suse.de
+
+- Update zypp-po.tar.bz2
+
+-------------------------------------------------------------------
+Sun Jul 12 01:13:20 CEST 2015 - ma@suse.de
+
+- Update zypp-po.tar.bz2
+
+-------------------------------------------------------------------
Thu Jul 9 16:43:12 CEST 2015 - ma@suse.de
- Resolver allow tuning DUP mode solver flags (FATE#319128)
Flags
InstanceId
KeyRing
+ Locale
Locks
MediaSetAccess
PathInfo
using std::endl;
using namespace zypp;
-enum TBits
+enum class E
{
- T_0 = 0,
- T_1 = 1 << 0,
- T_2 = 1 << 1,
- T_3 = T_2 | T_1,
- T_4 = 1 << 2,
- T_5 = T_4 | T_1,
- T_8 = 1 << 3,
+ _0 = 0,
+ _1 = 1 << 0,
+ _2 = 1 << 1,
+ _3 = _2 | _1,
+ _4 = 1 << 2,
+ _5 = _4 | _1,
+ _8 = 1 << 3,
};
-ZYPP_DECLARE_FLAGS( TFlags, TBits );
+ZYPP_DECLARE_FLAGS( TFlags, E );
ZYPP_DECLARE_OPERATORS_FOR_FLAGS( TFlags );
-static const TFlags T_6( T_4 | T_2 );
-static const TFlags T_7( T_4 | T_2 | T_1 );
+inline std::ostream & operator<<( std::ostream & str, const E & obj )
+{ return str << TFlags(obj); }
+
+static const TFlags T_6( E::_4 | E::_2 );
+static const TFlags T_7( E::_4 | E::_2 | E::_1 );
+
BOOST_AUTO_TEST_CASE(flags)
{
TFlags t0;
BOOST_CHECK_EQUAL( t0, 0 );
- BOOST_CHECK_EQUAL( t0, T_0 );
+ BOOST_CHECK_EQUAL( E::_0, t0 );
+ BOOST_CHECK_EQUAL( t0, E::_0 );
BOOST_CHECK_EQUAL( t0, TFlags(0) );
BOOST_CHECK_EQUAL( ~t0, ~0 );
BOOST_CHECK_EQUAL( ~~t0, 0 );
- BOOST_CHECK_EQUAL( ~t0, ~T_0 );
- BOOST_CHECK_EQUAL( ~~t0, T_0 );
+ BOOST_CHECK_EQUAL( ~t0, ~E::_0 );
+ BOOST_CHECK_EQUAL( ~~t0, E::_0 );
+
+ BOOST_CHECK_EQUAL( TFlags::none(), TFlags(0) );
+ BOOST_CHECK_EQUAL( TFlags::all(), ~TFlags(0) );
- TFlags t1( T_1 );
+ TFlags t1( E::_1 );
BOOST_CHECK_EQUAL( t1, 1 );
- BOOST_CHECK_EQUAL( t1, T_1 );
+ BOOST_CHECK_EQUAL( t1, E::_1 );
BOOST_CHECK_EQUAL( t1, TFlags(1) );
TFlags t;
- // t = 1; // must not compile: assign from int_type
- t = T_2; // = enum
- BOOST_CHECK_EQUAL( t, T_2 );
+ //t = 1; // must not compile: assign from int_type
+ t = E::_2; // = enum
+ BOOST_CHECK_EQUAL( t, E::_2 );
t = T_6; // = TFlags
BOOST_CHECK_EQUAL( t, T_6 );
// enum op enum
- t = ~T_1; BOOST_CHECK_EQUAL( ~t, T_1 );
- t = T_1 & T_2; BOOST_CHECK_EQUAL( t, T_0 );
- t = T_1 | T_2; BOOST_CHECK_EQUAL( t, T_3 );
- t = T_1 ^ T_2; BOOST_CHECK_EQUAL( t, T_3 );
+ t = ~E::_1; BOOST_CHECK_EQUAL( ~t, E::_1 );
+ t = E::_1 & E::_2; BOOST_CHECK_EQUAL( t, E::_0 );
+ t = E::_1 | E::_2; BOOST_CHECK_EQUAL( t, E::_3 );
+ t = E::_1 ^ E::_2; BOOST_CHECK_EQUAL( t, E::_3 );
// enum op TFlags
- t = T_2 & T_6; BOOST_CHECK_EQUAL( t, T_2 );
- t = T_2 | T_6; BOOST_CHECK_EQUAL( t, T_6 );
- t = T_2 ^ T_6; BOOST_CHECK_EQUAL( t, T_4 );
-
- // TFlags op enum
- t = ~T_7; BOOST_CHECK_EQUAL( ~t, T_7 );
- t = T_7 & T_2; BOOST_CHECK_EQUAL( t, T_2 );
- t = T_7 | T_2; BOOST_CHECK_EQUAL( t, T_7 );
- t = T_7 ^ T_2; BOOST_CHECK_EQUAL( t, T_5 );
+ t = E::_2 & T_6; BOOST_CHECK_EQUAL( t, E::_2 );
+ t = E::_2 | T_6; BOOST_CHECK_EQUAL( t, T_6 );
+ t = E::_2 ^ T_6; BOOST_CHECK_EQUAL( t, E::_4 );
// TFlags op enum
- t = T_7 & T_6; BOOST_CHECK_EQUAL( t, T_6 );
- t = T_7 | T_6; BOOST_CHECK_EQUAL( t, T_7 );
- t = T_7 ^ T_7; BOOST_CHECK_EQUAL( t, T_0 );
+ t = ~T_7; BOOST_CHECK_EQUAL( ~t, T_7 );
+ t = T_7 & E::_2; BOOST_CHECK_EQUAL( t, E::_2 );
+ t = T_7 | E::_2; BOOST_CHECK_EQUAL( t, T_7 );
+ t = T_7 ^ E::_2; BOOST_CHECK_EQUAL( t, E::_5 );
+ // TFlags op TFlags
+ t = T_7 & T_6; BOOST_CHECK_EQUAL( t, T_6 );
+ t = T_7 | T_6; BOOST_CHECK_EQUAL( t, T_7 );
+ t = T_7 ^ T_7; BOOST_CHECK_EQUAL( t, E::_0 );
- t = T_3;
- BOOST_CHECK( ! t.testFlag( T_0 ) ); // fails as T_3 != 0
- BOOST_CHECK( t.testFlag( T_1 ) );
- BOOST_CHECK( t.testFlag( T_2 ) );
- BOOST_CHECK( t.testFlag( T_3 ) );
- t.unsetFlag( T_2 ); BOOST_CHECK( t.testFlag( T_1 ) );
- t.setFlag( T_1, false ); BOOST_CHECK( t.testFlag( T_0 ) ); // succeed as T_3 == 0
- t.setFlag( T_3, true ); BOOST_CHECK( t.testFlag( T_3 ) );
+ t = E::_3;
+ BOOST_CHECK( ! t.testFlag( E::_0 ) ); // fails as t != 0
+ BOOST_CHECK( t.testFlag( E::_1 ) );
+ BOOST_CHECK( t.testFlag( E::_2 ) );
+ BOOST_CHECK( t.testFlag( E::_3 ) );
+ t.unsetFlag( E::_2 ); BOOST_CHECK( t.testFlag( E::_1 ) );
+ t.setFlag( E::_1, false ); BOOST_CHECK( t.testFlag( E::_0 ) ); // succeed as t == 0
+ t.setFlag( E::_3, true ); BOOST_CHECK( t.testFlag( E::_3 ) );
}
--- /dev/null
+#include <cstdlib>
+#include <iostream>
+#include <boost/test/auto_unit_test.hpp>
+
+#include "zypp/Locale.h"
+
+#define BOOST_TEST_MODULE Locale
+
+using std::cout;
+using std::endl;
+
+using namespace zypp;
+using namespace boost::unit_test;
+
+BOOST_AUTO_TEST_CASE(static_deps)
+{
+ setenv( "LANG", "C", 1 );
+
+ // static vars initialization sequence: Locale depends on LanguageCode
+ BOOST_CHECK_EQUAL( LanguageCode::enCode.code(), "en" );
+ BOOST_CHECK_EQUAL( IdString(Locale::enCode), IdString(LanguageCode::enCode) );
+
+ // solver communication: Both must lead to the same ID
+ BOOST_CHECK_EQUAL( Locale::enCode.id(), IdString(LanguageCode::enCode.code()).id() );
+}
+
+//
+// NOTE: In checks testing for empty codes (IdString::Null/IdString::Empty)
+// explicitly use the ID, because both share the same string representation.
+//
+// This way you get "failed [1 != 0]" rather than "failed [ != ]"
+//
+
+BOOST_AUTO_TEST_CASE(no_codes)
+{
+ // IdString::Null is probably a rare case
+ BOOST_CHECK_EQUAL( LanguageCode(nullptr).id(), IdString::Null.id() );
+ BOOST_CHECK_EQUAL( CountryCode(nullptr).id(), IdString::Null.id() );
+ BOOST_CHECK_EQUAL( Locale(nullptr).id(), IdString::Null.id() );
+ BOOST_CHECK_EQUAL( Locale(nullptr).language().id(), IdString::Null.id() );
+ BOOST_CHECK_EQUAL( Locale(nullptr).country().id(), IdString::Null.id() );
+
+ // IdString::Null is the ususal noCode
+ BOOST_CHECK_EQUAL( LanguageCode::noCode.id(), LanguageCode().id() );
+ BOOST_CHECK_EQUAL( LanguageCode::noCode.id(), LanguageCode("").id() );
+ BOOST_CHECK_EQUAL( LanguageCode::noCode.id(), IdString::Empty.id() );
+
+ BOOST_CHECK_EQUAL( CountryCode::noCode.id(), CountryCode().id() );
+ BOOST_CHECK_EQUAL( CountryCode::noCode.id(), CountryCode("").id() );
+ BOOST_CHECK_EQUAL( CountryCode::noCode.id(), IdString::Empty.id() );
+
+ BOOST_CHECK_EQUAL( Locale::noCode.id(), Locale().id() );
+ BOOST_CHECK_EQUAL( Locale::noCode.id(), Locale("").id() );
+ BOOST_CHECK_EQUAL( Locale::noCode.id(), IdString::Empty.id() );
+ BOOST_CHECK_EQUAL( Locale::noCode.language().id(), LanguageCode::noCode.id() );
+ BOOST_CHECK_EQUAL( Locale::noCode.country().id(), CountryCode::noCode.id() );
+
+ //
+ const char * nc = "No Code";
+ BOOST_CHECK_EQUAL( LanguageCode(nullptr).name(), nc );
+ BOOST_CHECK_EQUAL( CountryCode(nullptr).name(), nc );
+ BOOST_CHECK_EQUAL( Locale(nullptr).name(), nc );
+
+ BOOST_CHECK_EQUAL( LanguageCode::noCode.name(), nc );
+ BOOST_CHECK_EQUAL( CountryCode::noCode.name(), nc );
+ BOOST_CHECK_EQUAL( Locale::noCode.name(), nc );
+
+}
+
+BOOST_AUTO_TEST_CASE(language_code)
+{
+ // language code: ger deu de, N_( "German" )
+ std::string name( "German" );
+ for ( const char * s : { "ger", "deu", "de" } )
+ {
+ BOOST_CHECK_EQUAL( LanguageCode(s).code(), s );
+ BOOST_CHECK_EQUAL( LanguageCode(s), IdString(s) );
+ BOOST_CHECK_EQUAL( LanguageCode(s).id(), IdString(s).id() );
+
+ BOOST_CHECK_EQUAL( LanguageCode(s).name(), name );
+ }
+ BOOST_CHECK( LanguageCode("de") < LanguageCode("deu") );
+ BOOST_CHECK( LanguageCode("deu") < LanguageCode("ger") );
+
+ BOOST_CHECK_EQUAL( LanguageCode("XX"), IdString("XX") );
+}
+
+BOOST_AUTO_TEST_CASE(country_code)
+{
+ // country code: "DE", N_("Germany)
+ std::string name( "Germany" );
+ for ( const char * s : { "DE" } )
+ {
+ BOOST_CHECK_EQUAL( CountryCode(s).code(), s );
+ BOOST_CHECK_EQUAL( CountryCode(s), IdString(s) );
+ BOOST_CHECK_EQUAL( CountryCode(s).id(), IdString(s).id() );
+
+ BOOST_CHECK_EQUAL( CountryCode(s).name(), name );
+ }
+
+ BOOST_CHECK( CountryCode("AA") < CountryCode("DE") );
+
+ BOOST_CHECK_EQUAL( CountryCode("XX"), IdString("XX") );
+}
+
+BOOST_AUTO_TEST_CASE(locale)
+{
+ // IdString::Null (rare)
+ {
+ for ( const Locale & l : { Locale( nullptr ), Locale( LanguageCode(nullptr), CountryCode(nullptr) ) } )
+ {
+ BOOST_CHECK_EQUAL( l.id(), IdString::Null.id() );
+ BOOST_CHECK_EQUAL( l.language().id(), IdString::Null.id() );
+ BOOST_CHECK_EQUAL( l.country().id(), IdString::Null.id() );
+ BOOST_CHECK_EQUAL( bool(l), false );
+ BOOST_CHECK_EQUAL( bool(l.language()), false );
+ BOOST_CHECK_EQUAL( bool(l.country()), false );
+ }
+ }
+ // Trailing garbage ([.@].*) is ignored
+ {
+ for ( const Locale & l : { Locale(), Locale( "" ), Locale( "@UTF-8" ), Locale( ".UTF-8" )
+ , Locale( LanguageCode(), CountryCode(nullptr) )
+ , Locale( LanguageCode(nullptr), CountryCode() )
+ , Locale( LanguageCode(), CountryCode() ) } )
+ {
+ BOOST_CHECK_EQUAL( l.id(), IdString::Empty.id() );
+ BOOST_CHECK_EQUAL( l.language().id(), IdString::Empty.id() );
+ BOOST_CHECK_EQUAL( l.country().id(), IdString::Empty.id() );
+ BOOST_CHECK_EQUAL( bool(l), false );
+ BOOST_CHECK_EQUAL( bool(l.language()), false );
+ BOOST_CHECK_EQUAL( bool(l.country()), false );
+ }
+ }
+ {
+ for ( const Locale & l : { Locale("de_DE"), Locale( "de_DE@UTF-8" )
+ , Locale( LanguageCode("de"), CountryCode("DE") ) } )
+ {
+ BOOST_CHECK_EQUAL( l, IdString("de_DE") );
+ BOOST_CHECK_EQUAL( l.language(), IdString("de") );
+ BOOST_CHECK_EQUAL( l.country(), IdString("DE") );
+ BOOST_CHECK_EQUAL( bool(l), true );
+ BOOST_CHECK_EQUAL( bool(l.language()), true );
+ BOOST_CHECK_EQUAL( bool(l.country()), true );
+ }
+ }
+ {
+ for ( const Locale & l : { Locale("de"), Locale( "de@UTF-8" )
+ , Locale( LanguageCode("de") ) } )
+ {
+ BOOST_CHECK_EQUAL( l.id(), l.language().id() );
+ BOOST_CHECK_EQUAL( l.country().id(), IdString::Empty.id() );
+ BOOST_CHECK_EQUAL( bool(l), true );
+ BOOST_CHECK_EQUAL( bool(l.language()), true );
+ BOOST_CHECK_EQUAL( bool(l.country()), false );
+ }
+ }
+}
+
+BOOST_AUTO_TEST_CASE(fallback)
+{
+ { // default fallback...
+ Locale l( "de_DE" );
+ BOOST_CHECK_EQUAL( (l = l.fallback()), "de" );
+ BOOST_CHECK_EQUAL( (l = l.fallback()), "en" );
+ BOOST_CHECK_EQUAL( (l = l.fallback()), "" );
+ }
+ { // special rules...
+ Locale l( "pt_BR" );
+ BOOST_CHECK_EQUAL( (l = l.fallback()), "en" );
+ BOOST_CHECK_EQUAL( (l = l.fallback()), "" );
+ }
+}
#include "zypp/base/Logger.h"
#include "zypp/base/Exception.h"
#include "zypp/base/NonCopyable.h"
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/Arch.h"
#include "zypp/Bit.h"
typedef Arch::CompatEntry CompatEntry;
typedef CompatEntry::CompatBits CompatBits;
- typedef std::tr1::unordered_set<CompatEntry> Set;
+ typedef std::unordered_set<CompatEntry> Set;
typedef Set::iterator iterator;
typedef Set::const_iterator const_iterator;
};
///////////////////////////////////////////////////////////////////
- /** \relates AutoDispose<_Tp> Stream output of the \c _Tp object. */
+ /** \relates AutoDispose Stream output of the \c _Tp object. */
template<class _Tp>
inline std::ostream & operator<<( std::ostream & str, const AutoDispose<_Tp> & obj )
{ return str << obj.value(); }
ResObjects.h
Resolvable.h
Resolver.h
+ ResolverNamespace.h
ResolverProblem.h
ResPool.h
ResPoolProxy.h
base/PtrTypes.h
base/ReferenceCounted.h
base/SetRelationMixin.h
+ base/SetTracker.h
base/Signal.h
base/String.h
base/StrMatcher.h
)
SET( zypp_solver_detail_SRCS
- solver/detail/Helper.cc
solver/detail/ProblemSolutionIgnore.cc
solver/detail/ProblemSolutionCombi.cc
solver/detail/Resolver.cc
)
SET( zypp_solver_detail_HEADERS
- solver/detail/Helper.h
solver/detail/ProblemSolutionIgnore.h
solver/detail/ProblemSolutionCombi.h
solver/detail/Resolver.h
solver/detail/SolverQueueItemUpdate.h
solver/detail/SolverQueueItemInstallOneOf.h
solver/detail/SolverQueueItemLock.h
+ solver/detail/ItemCapKind.h
solver/detail/SATResolver.h
solver/detail/SystemCheck.h
)
: _id( relFromStr( myPool().getPool(), arch_r, name_r, op_r, ed_r, prefix_r ) )
{}
+ ///////////////////////////////////////////////////////////////////
+ // Ctor creating a namespace: capability.
+ ///////////////////////////////////////////////////////////////////
+
+ Capability::Capability( ResolverNamespace namespace_r, IdString value_r )
+ : _id( ::pool_rel2id( myPool().getPool(), asIdString(namespace_r).id(), (value_r.empty() ? STRID_NULL : value_r.id() ), REL_NAMESPACE, /*create*/true ) )
+ {}
+
+
const char * Capability::c_str() const
{ return( _id ? ::pool_dep2str( myPool().getPool(), _id ) : "" ); }
#include "zypp/Edition.h"
#include "zypp/Rel.h"
#include "zypp/ResTraits.h"
-
+#include "zypp/ResolverNamespace.h"
#include "zypp/CapMatch.h"
///////////////////////////////////////////////////////////////////
class CapDetail;
class Arch;
- typedef std::tr1::unordered_set<Capability> CapabilitySet;
+ typedef std::unordered_set<Capability> CapabilitySet;
///////////////////////////////////////////////////////////////////
//
Capability( const Arch & arch_r, const std::string & name_r, Rel op_r, const Edition & ed_r, const ResKind & prefix_r = ResKind() );
//@}
+ /** \name Ctor creating a namespace: capability.
+ * An empty \a value_r (std::string or IdString) will also be mapped to IdString::Null,
+ * creating a namespace: capability which in most contexts matches all members of this namespace.
+ */
+ //@{
+ Capability( ResolverNamespace namespace_r, IdString value_r = IdString::Null );
+ Capability( ResolverNamespace namespace_r, const char * value_r ) : Capability( namespace_r, IdString(value_r) ) {}
+ Capability( ResolverNamespace namespace_r, const std::string & value_r ) : Capability( namespace_r, IdString(value_r) ) {}
+ //@}
public:
/** No or Null \ref Capability ( Id \c 0 ). */
static const Capability Null;
#include "zypp/base/Logger.h"
#include "zypp/base/String.h"
#include "zypp/base/Gettext.h"
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/CountryCode.h"
///////////////////////////////////////////////////////////////////
namespace zypp
-{ /////////////////////////////////////////////////////////////////
-
+{
///////////////////////////////////////////////////////////////////
namespace
- { /////////////////////////////////////////////////////////////////
+ {
/** Wrap static codemap data. */
struct CodeMaps // singleton
{
- typedef std::tr1::unordered_map<std::string,std::string> CodeMap;
- typedef CodeMap::const_iterator Index;
+ /** The singleton */
+ static CodeMaps & instance()
+ {
+ static CodeMaps _instance;
+ return _instance;
+ }
- /** Return the CodeMap Index for \a code_r. */
- static Index getIndex( const std::string & code_r )
+ /** Lookup (translated) name for \a index_r.*/
+ std::string name( IdString index_r )
{
- static CodeMaps _maps; // the singleton instance
- return _maps.lookup( code_r );
+ Link link( getIndex( index_r ) );
+
+ std::string ret;
+ if ( link->second )
+ { ret = _(link->second); }
+ else
+ {
+ ret = _("Unknown country: ");
+ ret += "'";
+ ret += index_r.c_str();
+ ret += "'";
+ }
+ return ret;
}
private:
+ typedef std::unordered_map<std::string,const char *> CodeMap;
+ typedef CodeMap::const_iterator Link;
+
+ typedef std::unordered_map<IdString,Link> IndexMap;
+
/** Ctor initializes the code maps.
* http://www.iso.org/iso/en/prods-services/iso3166ma/02iso-3166-code-lists/list-en1.html
- */
+ */
CodeMaps();
- /** Make shure the code is in the code maps and return it's index. */
- inline Index lookup( const std::string & code_r );
+ /** Return \ref Link for \a index_r, creating it if necessary. */
+ Link getIndex( IdString index_r )
+ {
+ auto it = _indexMap.find( index_r );
+ return( it != _indexMap.end()
+ ? it->second
+ : newIndex( index_r, index_r.asString() ) );
+ }
+
+ /** Return the CodeMap Index for \a code_r. */
+ Link newIndex( IdString index_r, const std::string & code_r )
+ {
+ Link link = _codeMap.find( code_r );
+ if ( link != _codeMap.end() )
+ return (_indexMap[index_r] = link);
+
+ // not found: Remember a new code
+ CodeMap::value_type nval( code_r, nullptr );
+
+ if ( code_r.size() != 2 )
+ WAR << "Malformed CountryCode '" << code_r << "' (expect 2-letter)" << endl;
+
+ std::string ucode( str::toUpper( code_r ) );
+ if ( ucode != code_r )
+ {
+ WAR << "Malformed CountryCode '" << code_r << "' (not upper case)" << endl;
+ // but maybe we're lucky with the lower case code
+ // and find a language name.
+ link = _codeMap.find( ucode );
+ if ( link != _codeMap.end() )
+ {
+ nval.second = link->second;
+ }
+ }
+ MIL << "Remember CountryCode '" << code_r << "': '" << nval.second << "'" << endl;
+ return (_indexMap[index_r] = _codeMap.insert( nval ).first);
+ }
private:
- /** All the codes. */
- CodeMap codes;
+ CodeMap _codeMap;
+ IndexMap _indexMap;
};
-
- inline CodeMaps::Index CodeMaps::lookup( const std::string & code_r )
- {
- Index it = codes.find( code_r );
- if ( it != codes.end() )
- return it;
-
- // not found: Remember a new code
- CodeMap::value_type nval( code_r, std::string() );
-
- if ( code_r.size() != 2 )
- WAR << "Malformed CountryCode '" << code_r << "' (expect 2-letter)" << endl;
-
- std::string lcode( str::toUpper( code_r ) );
- if ( lcode != code_r )
- {
- WAR << "Malformed CountryCode '" << code_r << "' (not upper case)" << endl;
- // but maybe we're lucky with the upper case code
- // and find a country name.
- it = codes.find( lcode );
- if ( it != codes.end() )
- nval.second = it->second;
- }
-
- MIL << "Remember CountryCode '" << code_r << "': '" << nval.second << "'" << endl;
- return codes.insert( nval ).first;
- }
-
- /////////////////////////////////////////////////////////////////
} // namespace
///////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////
- //
- // CLASS NAME : CountryCode::Impl
- //
- /** CountryCode implementation.
- * \note CodeMaps contain the untranslated country names.
- * Translation is done in \ref name.
- */
- struct CountryCode::Impl
- {
- Impl()
- : _index( CodeMaps::getIndex( std::string() ) )
- {}
-
- Impl( const std::string & code_r )
- : _index( CodeMaps::getIndex( code_r ) )
- {}
-
- std::string code() const
- { return _index->first; }
-
- std::string name() const {
- if ( _index->second.empty() )
- {
- std::string ret( _("Unknown country: ") );
- ret += "'";
- ret += _index->first;
- ret += "'";
- return ret;
- }
- return _( _index->second.c_str() );
- }
-
- private:
- /** index into code map. */
- CodeMaps::Index _index;
-
- public:
- /** Offer default Impl. */
- static shared_ptr<Impl> nullimpl()
- {
- static shared_ptr<Impl> _nullimpl( new Impl );
- return _nullimpl;
- }
- };
- ///////////////////////////////////////////////////////////////////
-
- ///////////////////////////////////////////////////////////////////
- //
- // CLASS NAME : CountryCode
- //
+ // class CountryCode
///////////////////////////////////////////////////////////////////
const CountryCode CountryCode::noCode;
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : CountryCode::CountryCode
- // METHOD TYPE : Ctor
- //
CountryCode::CountryCode()
- : _pimpl( Impl::nullimpl() )
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : CountryCode::CountryCode
- // METHOD TYPE : Ctor
- //
- CountryCode::CountryCode( const std::string & code_r )
- : _pimpl( new Impl( code_r ) )
+ CountryCode::CountryCode( IdString str_r )
+ : _str( str_r )
+ {}
+
+ CountryCode::CountryCode( const std::string & str_r )
+ : _str( str_r )
+ {}
+
+ CountryCode::CountryCode( const char * str_r )
+ : _str( str_r )
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : CountryCode::~CountryCode
- // METHOD TYPE : Dtor
- //
CountryCode::~CountryCode()
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : CountryCode::code
- // METHOD TYPE : std::string
- //
- std::string CountryCode::code() const
- { return _pimpl->code(); }
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : CountryCode::name
- // METHOD TYPE : std::string
- //
std::string CountryCode::name() const
- { return _pimpl->name(); }
+ { return CodeMaps::instance().name( _str ); }
///////////////////////////////////////////////////////////////////
namespace
CodeMaps::CodeMaps()
{
// Defined CountryCode constants
- codes[""] = N_( "No Code" );
+ _codeMap[""] = N_( "No Code" );
struct Init
{
};
for (const Init * i = init; i->iso3166 != NULL; ++i)
- codes[i->iso3166] = i->name;
+ _codeMap[i->iso3166] = i->name;
}
/////////////////////////////////////////////////////////////////
#include <iosfwd>
#include <string>
-#include "zypp/base/PtrTypes.h"
+#include "zypp/IdStringType.h"
///////////////////////////////////////////////////////////////////
namespace zypp
-{ /////////////////////////////////////////////////////////////////
-
- class CountryCode;
- inline bool operator==( const CountryCode & lhs, const CountryCode & rhs );
- inline bool operator!=( const CountryCode & lhs, const CountryCode & rhs );
-
+{
+ ///////////////////////////////////////////////////////////////////
+ /// \class CountryCode
+ /// \brief Country codes (iso3166-1-alpha-2).
+ ///
+ /// In fact the class will not prevent to use a non iso country code.
+ /// Just a warning will appear in the log.
///////////////////////////////////////////////////////////////////
- //
- // CLASS NAME : CountryCode
- //
- /** Country codes (iso3166-1-alpha-2).
- *
- * In fact the class will not prevent to use a non iso country code.
- * Just a warning will appear in the log.
- */
- class CountryCode
+ class CountryCode : public IdStringType<CountryCode>
{
- friend std::ostream & operator<<( std::ostream & str, const CountryCode & obj );
-
public:
- /** Implementation */
- class Impl;
-
- public:
- /** Default ctor */
+ /** Default Ctor: \ref noCode */
CountryCode();
- /** Ctor taking a string. */
- explicit
- CountryCode( const std::string & code_r );
+ /** Ctor from string. */
+ explicit CountryCode( IdString str_r );
+
+ /** Ctor from string. */
+ explicit CountryCode( const std::string & str_r );
+
+ /** Ctor from string. */
+ explicit CountryCode( const char * str_r );
/** Dtor */
~CountryCode();
/** \name CountryCode constants. */
//@{
- /** No or empty code. */
+ /** Empty code. */
static const CountryCode noCode;
//@}
public:
- /** Return the country code. */
- std::string code() const;
+ /** Return the country code asString. */
+ std::string code() const
+ { return std::string(_str); }
- /** Return the country name; if not available the country code. */
+ /** Return the translated country name; if unknown the country code. */
std::string name() const;
- /** <tt>*this != noCode</tt>. */
- bool hasCode() const
- { return *this != noCode; }
-
private:
- /** Pointer to implementation */
- RW_pointer<Impl> _pimpl;
+ friend class IdStringType<CountryCode>;
+ IdString _str;
};
- ///////////////////////////////////////////////////////////////////
-
- /** \relates CountryCode Stream output */
- inline std::ostream & operator<<( std::ostream & str, const CountryCode & obj )
- { return str << obj.code(); }
-
- /** Comparison based on string value. */
- //@{
- /** \relates CountryCode */
- inline bool operator==( const CountryCode & lhs, const CountryCode & rhs ) {
- return( lhs.code() == rhs.code() );
- }
- /** \relates CountryCode */
- inline bool operator==( const std::string & lhs, const CountryCode & rhs ) {
- return( lhs == rhs.code() );
- }
- /** \relates CountryCode */
- inline bool operator==( const CountryCode & lhs, const std::string & rhs ) {
- return( lhs.code() == rhs );
- }
-
- /** \relates CountryCode */
- inline bool operator!=( const CountryCode & lhs, const CountryCode & rhs ) {
- return( ! operator==( lhs, rhs ) );
- }
- /** \relates CountryCode */
- inline bool operator!=( const std::string & lhs, const CountryCode & rhs ) {
- return( ! operator==( lhs, rhs ) );
- }
- /** \relates CountryCode */
- inline bool operator!=( const CountryCode & lhs, const std::string & rhs ) {
- return( ! operator==( lhs, rhs ) );
- }
- //@}
-
- /////////////////////////////////////////////////////////////////
} // namespace zypp
///////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////
-namespace std
-{ /////////////////////////////////////////////////////////////////
- /** \relates zypp::CountryCode Default order for std::container based on code string value.*/
- template<>
- inline bool less<zypp::CountryCode>::operator()( const zypp::CountryCode & lhs, const zypp::CountryCode & rhs ) const
- { return lhs.code() < rhs.code(); }
- /////////////////////////////////////////////////////////////////
-} // namespace std
-///////////////////////////////////////////////////////////////////
+
+ZYPP_DEFINE_ID_HASHABLE( ::zypp::CountryCode );
+
#endif // ZYPP_COUNTRYCODE_H
: _id( ::pool_str2id( myPool().getPool(), str_r, /*create*/true ) )
{}
+ IdString::IdString( const char * str_r, unsigned len_r )
+ : _id( ::pool_strn2id( myPool().getPool(), str_r, len_r, /*create*/true ) )
+ {}
+
IdString::IdString( const std::string & str_r )
- : _id( ::pool_str2id( myPool().getPool(), str_r.c_str(), /*create*/true ) )
+ : IdString( str_r.c_str(), str_r.length() )
+ {}
+
+ IdString::IdString( boost::string_ref str_r )
+ : IdString( str_r.data(), str_r.length() )
{}
unsigned IdString::size() const
#include <iosfwd>
#include <string>
+#include <boost/utility/string_ref_fwd.hpp>
+
#include "zypp/sat/detail/PoolMember.h"
///////////////////////////////////////////////////////////////////
{ /////////////////////////////////////////////////////////////////
class IdString;
- typedef std::tr1::unordered_set<IdString> IdStringSet;
+ typedef std::unordered_set<IdString> IdStringSet;
///////////////////////////////////////////////////////////////////
//
public:
/** Default ctor, empty string. */
- IdString() : _id( sat::detail::emptyId ) {}
+ constexpr IdString() : _id( sat::detail::emptyId ) {}
/** Ctor from id. */
- explicit IdString( IdType id_r ) : _id( id_r ) {}
+ constexpr explicit IdString( IdType id_r ) : _id( id_r ) {}
/** Ctor from string. */
explicit IdString( const char * str_r );
+ /** Ctor from string (pointer,length). */
+ IdString( const char * str_r, unsigned len_r );
+
/** Ctor from string. */
explicit IdString( const std::string & str_r );
+ /** Ctor from boost::string_ref. */
+ explicit IdString( boost::string_ref str_r );
+
public:
/** No or Null string ( Id \c 0 ). */
static const IdString Null;
public:
/** Evaluate in a boolean context <tt>( != \c Null )</tt>. */
- explicit operator bool() const
+ constexpr explicit operator bool() const
{ return _id; }
/** Whether the string is empty.
* This is true for \ref Null and \ref Empty.
*/
- bool empty() const
+ constexpr bool empty() const
{ return( _id == sat::detail::emptyId || _id == sat::detail::noId ); }
/** The strings size. */
std::string asString() const
{ return c_str(); }
+ /** Explicit conversion to std::string */
+ explicit operator std::string() const
+ { return asString(); }
+
public:
/** Fast compare equal. */
bool compareEQ( const IdString & rhs ) const
const Derived & self() const { return *static_cast<const Derived*>( this ); }
public:
- const IdString & idStr() const { return self()._str; }
+ IdString idStr() const { return self()._str; }
bool empty() const { return idStr().empty(); }
unsigned size() const { return idStr().size(); }
explicit operator bool() const
{ return ! empty(); }
+ /** Explicit conversion to IdString */
+ explicit operator IdString() const
+ { return idStr(); }
+
+ /** Explicit conversion to std::string */
+ explicit operator std::string() const
+ { return asString(); }
+
public:
// - break it down to idString/const char* <=> idString/cont char*
// - handle idString(0)/NULL being the least value
#include "zypp/base/Logger.h"
#include "zypp/base/String.h"
#include "zypp/base/Gettext.h"
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/LanguageCode.h"
///////////////////////////////////////////////////////////////////
namespace zypp
-{ /////////////////////////////////////////////////////////////////
-
+{
///////////////////////////////////////////////////////////////////
namespace
- { /////////////////////////////////////////////////////////////////
-
+ {
/** Wrap static codemap data. */
- struct CodeMaps // singleton
+ struct CodeMaps
{
- typedef std::tr1::unordered_map<std::string,std::string> CodeMap;
- typedef CodeMap::const_iterator Index;
+ /** The singleton */
+ static CodeMaps & instance()
+ {
+ static CodeMaps _instance;
+ return _instance;
+ }
- /** Return the CodeMap Index for \a code_r. */
- static Index getIndex( const std::string & code_r )
+ /** Lookup (translated) name for \a index_r.*/
+ std::string name( IdString index_r )
{
- static CodeMaps _maps; // the singleton instance
- return _maps.lookup( code_r );
+ Link link( getIndex( index_r ) );
+
+ std::string ret;
+ if ( link->second )
+ { ret = _(link->second); }
+ else
+ {
+ ret = _("Unknown language: ");
+ ret += "'";
+ ret += index_r.c_str();
+ ret += "'";
+ }
+ return ret;
}
private:
+ typedef std::unordered_map<std::string,const char *> CodeMap;
+ typedef CodeMap::const_iterator Link;
+
+ typedef std::unordered_map<IdString,Link> IndexMap;
+
/** Ctor initializes the code maps.
* http://www.loc.gov/standards/iso639-2/ISO-639-2_values_8bits.txt
*/
CodeMaps();
- /** Make shure the code is in the code maps and return it's index. */
- inline Index lookup( const std::string & code_r );
-
- private:
- /** All the codes. */
- CodeMap codes;
- };
-
- inline CodeMaps::Index CodeMaps::lookup( const std::string & code_r )
- {
- Index it = codes.find( code_r );
- if ( it != codes.end() )
- return it;
+ /** Return \ref Link for \a index_r, creating it if necessary. */
+ Link getIndex( IdString index_r )
+ {
+ auto it = _indexMap.find( index_r );
+ return( it != _indexMap.end()
+ ? it->second
+ : newIndex( index_r, index_r.asString() ) );
+ }
- // not found: Remember a new code
- CodeMap::value_type nval( code_r, std::string() );
+ /** Return the CodeMap Index for \a code_r. */
+ Link newIndex( IdString index_r, const std::string & code_r )
+ {
+ Link link = _codeMap.find( code_r );
+ if ( link != _codeMap.end() )
+ return (_indexMap[index_r] = link);
- if ( code_r.size() > 3 || code_r.size() < 2 )
- WAR << "Malformed LanguageCode '" << code_r << "' (expect 2 or 3-letter)" << endl;
+ // not found: Remember a new code
+ CodeMap::value_type nval( code_r, nullptr );
- std::string lcode( str::toLower( code_r ) );
- if ( lcode != code_r )
- {
- WAR << "Malformed LanguageCode '" << code_r << "' (not lower case)" << endl;
- // but maybe we're lucky with the lower case code
- // and find a language name.
- it = codes.find( lcode );
- if ( it != codes.end() )
- nval.second = it->second;
- }
+ if ( code_r.size() > 3 || code_r.size() < 2 )
+ WAR << "Malformed LanguageCode '" << code_r << "' (expect 2 or 3-letter)" << endl;
- MIL << "Remember LanguageCode '" << code_r << "': '" << nval.second << "'" << endl;
- return codes.insert( nval ).first;
- }
+ std::string lcode( str::toLower( code_r ) );
+ if ( lcode != code_r )
+ {
+ WAR << "Malformed LanguageCode '" << code_r << "' (not lower case)" << endl;
+ // but maybe we're lucky with the lower case code
+ // and find a language name.
+ link = _codeMap.find( lcode );
+ if ( link != _codeMap.end() )
+ {
+ nval.second = link->second;
+ }
+ }
+ MIL << "Remember LanguageCode '" << code_r << "': '" << nval.second << "'" << endl;
+ return (_indexMap[index_r] = _codeMap.insert( nval ).first);
+ }
- /////////////////////////////////////////////////////////////////
+ private:
+ CodeMap _codeMap;
+ IndexMap _indexMap;
+ };
} // namespace
///////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////
- //
- // CLASS NAME : LanguageCode::Impl
- //
- /** LanguageCode implementation.
- * \note CodeMaps contain the untranslated language names.
- * Translation is done in \ref name.
- */
- struct LanguageCode::Impl
- {
- Impl()
- : _index( CodeMaps::getIndex( std::string() ) )
- {}
-
- Impl( const std::string & code_r )
- : _index( CodeMaps::getIndex( code_r ) )
- {}
-
- std::string code() const
- { return _index->first; }
-
- std::string name() const {
- if ( _index->second.empty() )
- {
- std::string ret( _("Unknown language: ") );
- ret += "'";
- ret += _index->first;
- ret += "'";
- return ret;
- }
- return _( _index->second.c_str() );
- }
-
- private:
- /** index into code map. */
- CodeMaps::Index _index;
-
- public:
- /** Offer default Impl. */
- static shared_ptr<Impl> nullimpl()
- {
- static shared_ptr<Impl> _nullimpl( new Impl );
- return _nullimpl;
- }
- };
- ///////////////////////////////////////////////////////////////////
-
- ///////////////////////////////////////////////////////////////////
- //
- // CLASS NAME : LanguageCode
- //
+ // class LanguageCode
///////////////////////////////////////////////////////////////////
const LanguageCode LanguageCode::noCode;
+ //const LanguageCode LanguageCode::enCode("en"); in Locale.cc as Locale::enCode depends on it
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : LanguageCode::LanguageCode
- // METHOD TYPE : Ctor
- //
LanguageCode::LanguageCode()
- : _pimpl( Impl::nullimpl() )
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : LanguageCode::LanguageCode
- // METHOD TYPE : Ctor
- //
- LanguageCode::LanguageCode( const std::string & code_r )
- : _pimpl( new Impl( code_r ) )
+ LanguageCode::LanguageCode( IdString str_r )
+ : _str( str_r )
+ {}
+
+ LanguageCode::LanguageCode( const std::string & str_r )
+ : _str( str_r )
+ {}
+
+ LanguageCode::LanguageCode( const char * str_r )
+ : _str( str_r )
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : LanguageCode::~LanguageCode
- // METHOD TYPE : Dtor
- //
LanguageCode::~LanguageCode()
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : LanguageCode::code
- // METHOD TYPE : std::string
- //
- std::string LanguageCode::code() const
- { return _pimpl->code(); }
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : LanguageCode::name
- // METHOD TYPE : std::string
- //
std::string LanguageCode::name() const
- { return _pimpl->name(); }
+ { return CodeMaps::instance().name( _str ); }
///////////////////////////////////////////////////////////////////
namespace
- { /////////////////////////////////////////////////////////////////
-
+ {
CodeMaps::CodeMaps()
{
// Defined LanguageCode constants
- codes[""] = N_("No Code");
+ _codeMap[""] = N_("No Code");
struct LangInit
{
for (const LangInit * i = langInit; i->iso639_2 != NULL; ++i)
{
- std::string name( i->name );
- codes[i->iso639_2] = name;
+ const char * name( i->name );
+ _codeMap[i->iso639_2] = name;
if (i->iso639_1 != NULL)
- codes[i->iso639_1] = name;
+ _codeMap[i->iso639_1] = name;
}
}
-
- /////////////////////////////////////////////////////////////////
} // namespace
///////////////////////////////////////////////////////////////////
-
- /////////////////////////////////////////////////////////////////
} // namespace zypp
///////////////////////////////////////////////////////////////////
#include <iosfwd>
#include <string>
-#include "zypp/base/PtrTypes.h"
+#include "zypp/IdStringType.h"
///////////////////////////////////////////////////////////////////
namespace zypp
-{ /////////////////////////////////////////////////////////////////
-
- class LanguageCode;
- inline bool operator==( const LanguageCode & lhs, const LanguageCode & rhs );
- inline bool operator!=( const LanguageCode & lhs, const LanguageCode & rhs );
-
+{
+ ///////////////////////////////////////////////////////////////////
+ /// \class LanguageCode
+ /// \brief Language codes (iso639_2/iso639_1).
+ ///
+ /// In fact the class will not prevent to use a non iso language code.
+ /// Just a warning will appear in the log.
///////////////////////////////////////////////////////////////////
- //
- // CLASS NAME : LanguageCode
- //
- /** Language codes (iso639_2/iso639_1).
- *
- * In fact the class will not prevent to use a non iso language code.
- * Just a warning will appear in the log.
- */
- class LanguageCode
+ class LanguageCode : public IdStringType<LanguageCode>
{
- friend std::ostream & operator<<( std::ostream & str, const LanguageCode & obj );
-
public:
- /** Implementation */
- class Impl;
-
- public:
- /** Default ctor */
+ /** Default Ctor: \ref noCode */
LanguageCode();
- /** Ctor taking a string. */
- explicit
- LanguageCode( const std::string & code_r );
+ /** Ctor from string. */
+ explicit LanguageCode( IdString str_r );
+
+ /** Ctor from string. */
+ explicit LanguageCode( const std::string & str_r );
- /** Dtor */
+ /** Ctor from string. */
+ explicit LanguageCode( const char * str_r );
+
+ /** Dtor */
~LanguageCode();
public:
/** \name LanguageCode constants. */
//@{
- /** No or empty code. */
+ /** Empty code. */
static const LanguageCode noCode;
+ /** Last resort "en". */
+ static const LanguageCode enCode;
//@}
public:
- /** Return the language code. */
- std::string code() const;
+ /** Return the language code asString. */
+ std::string code() const
+ { return std::string(_str); }
- /** Return the language name; if not available the language code. */
+ /** Return the translated language name; if unknown the language code. */
std::string name() const;
- /** <tt>*this != noCode</tt>. */
- inline bool hasCode() const
- { return *this != noCode; }
-
private:
- /** Pointer to implementation */
- RW_pointer<Impl> _pimpl;
+ friend class IdStringType<LanguageCode>;
+ IdString _str;
};
- ///////////////////////////////////////////////////////////////////
-
- /** \relates LanguageCode Stream output */
- inline std::ostream & operator<<( std::ostream & str, const LanguageCode & obj )
- { return str << obj.code(); }
-
- /** Comparison based on string value. */
- //@{
- /** \relates LanguageCode */
- inline bool operator==( const LanguageCode & lhs, const LanguageCode & rhs ) {
- return( lhs.code() == rhs.code() );
- }
- /** \relates LanguageCode */
- inline bool operator==( const std::string & lhs, const LanguageCode & rhs ) {
- return( lhs == rhs.code() );
- }
- /** \relates LanguageCode */
- inline bool operator==( const LanguageCode & lhs, const std::string & rhs ) {
- return( lhs.code() == rhs );
- }
-
- /** \relates LanguageCode */
- inline bool operator!=( const LanguageCode & lhs, const LanguageCode & rhs ) {
- return( ! operator==( lhs, rhs ) );
- }
- /** \relates LanguageCode */
- inline bool operator!=( const std::string & lhs, const LanguageCode & rhs ) {
- return( ! operator==( lhs, rhs ) );
- }
- /** \relates LanguageCode */
- inline bool operator!=( const LanguageCode & lhs, const std::string & rhs ) {
- return( ! operator==( lhs, rhs ) );
- }
- //@}
-
- /////////////////////////////////////////////////////////////////
} // namespace zypp
///////////////////////////////////////////////////////////////////
-///////////////////////////////////////////////////////////////////
-namespace std
-{ /////////////////////////////////////////////////////////////////
- /** \relates zypp::LanguageCode Default order for std::container based on code string value.*/
- template<>
- inline bool less<zypp::LanguageCode>::operator()( const zypp::LanguageCode & lhs, const zypp::LanguageCode & rhs ) const
- { return lhs.code() < rhs.code(); }
- /////////////////////////////////////////////////////////////////
-} // namespace std
-///////////////////////////////////////////////////////////////////
+ZYPP_DEFINE_ID_HASHABLE( ::zypp::LanguageCode );
+
#endif // ZYPP_LANGUAGECODE_H
///////////////////////////////////////////////////////////////////
namespace zypp
-{ /////////////////////////////////////////////////////////////////
+{
+ /** Wrap static codemap data. */
+ struct CodeMaps
+ {
+ /** Return IdString without trailing garbage. */
+ static IdString withoutTrash( IdString code_r )
+ {
+ boost::string_ref::size_type sep = trashStart( code_r );
+ if ( sep != boost::string_ref::npos )
+ code_r = IdString( code_r.c_str(), sep );
+ return code_r;
+ }
- typedef std::map<std::string, std::string> OtherDefaultLanguage;
- static OtherDefaultLanguage otherDefaultLanguage;
+ /** Return IdString without trailing garbage. */
+ static IdString withoutTrash( const std::string & code_r )
+ { return withoutTrash( boost::string_ref(code_r) ); }
- ///////////////////////////////////////////////////////////////////
- //
- // CLASS NAME : Locale::Impl
- //
- /** Locale implementation. */
- struct Locale::Impl
- {
- Impl()
- {}
+ /** Return IdString without trailing garbage. */
+ static IdString withoutTrash( const char * code_r )
+ { return( code_r ? withoutTrash( boost::string_ref(code_r) ) : IdString::Null ); }
- Impl( const std::string & code_r )
+ /** Return IdString from language/country codes. */
+ static IdString combineLC( LanguageCode language_r, CountryCode country_r )
{
- std::string t;
- std::string::size_type sep = code_r.find_first_of( "@." );
- if ( sep == std::string::npos ) {
- t = code_r;
- } else {
- t = code_r.substr( 0, sep );
+ IdString ret;
+ if ( language_r )
+ {
+ if ( country_r )
+ ret = IdString( std::string(language_r) + "_" + country_r.c_str() );
+ else
+ ret = IdString(language_r);
}
-
- sep = t.find( '_' );
- if ( sep == std::string::npos ) {
- _language = LanguageCode( t );
- } else {
- _language = LanguageCode( t.substr( 0, sep ) );
- _country = CountryCode( t.substr( sep+1 ) );
+ else
+ {
+ if ( country_r )
+ ret = IdString( "_" + std::string(country_r) );
+ else if ( ! ( IdString(language_r) || IdString(country_r) ) )
+ ret = IdString::Null;
+ // else IdString::Empty
}
+ return ret;
}
- Impl( const LanguageCode & language_r,
- const CountryCode & country_r )
- : _language( language_r )
- , _country( country_r )
- {}
+ /** The singleton */
+ static CodeMaps & instance()
+ {
+ static CodeMaps _instance;
+ return _instance;
+ }
- const LanguageCode & language() const
- { return _language; }
+ LanguageCode language( IdString index_r )
+ { return getIndex( index_r )._l; }
- const CountryCode & country() const
- { return _country; }
+ CountryCode country( IdString index_r )
+ { return getIndex( index_r )._c; }
- std::string code() const
+ std::string name( IdString index_r )
{
- std::string ret( _language.code() );
- if ( _country.hasCode() )
- ret += "_" + _country.code();
+ const LC & lc( getIndex( index_r ) );
+ std::string ret( lc._l.name() );
+ if ( lc._c )
+ {
+ ret += " (";
+ ret += lc._c.name();
+ ret += ")";
+ }
return ret;
}
- std::string name() const
+ Locale fallback( IdString index_r )
{
- std::string ret( _language.name() );
- if ( _country.hasCode() )
- ret += " (" + _country.name() + ")";
+ static const IdString special( "pt_BR" );
+ Locale ret;
+ if ( index_r == special ) // "pt_BR"->"en" - by now the only fallback exception
+ ret = Locale::enCode;
+ else
+ {
+ const LC & lc( getIndex( index_r ) );
+ if ( lc._c )
+ ret = lc._l;
+ else if ( lc._l && lc._l != LanguageCode::enCode )
+ ret = Locale::enCode;
+ }
return ret;
}
- Locale fallback() const
+ private:
+ static IdString withoutTrash( boost::string_ref code_r )
{
- if (otherDefaultLanguage.size() == 0) {
- // initial inserting map
- otherDefaultLanguage["pt_BR"] = "en";
- }
-
- if (otherDefaultLanguage.find(code()) != otherDefaultLanguage.end())
- return LanguageCode(otherDefaultLanguage[code()]);
-
- if ( _country.hasCode() )
- return _language;
+ boost::string_ref::size_type sep = trashStart( code_r );
+ if ( sep != boost::string_ref::npos )
+ code_r = code_r.substr( 0, sep );
+ return IdString( code_r );
+ }
- if ( _language.hasCode() && _language != LanguageCode("en") )
- return LanguageCode("en");
+ static boost::string_ref::size_type trashStart( boost::string_ref code_r )
+ { return code_r.find_first_of( "@." ); }
- return Locale();
- }
+ static boost::string_ref::size_type trashStart( IdString code_r )
+ { return trashStart( boost::string_ref(code_r.c_str()) ); }
private:
+ struct LC {
+ LC() {}
+ LC( LanguageCode l_r ) : _l( l_r ) {}
+ LC( LanguageCode l_r, CountryCode c_r ) : _l( l_r ), _c( c_r ) {}
+ LanguageCode _l;
+ CountryCode _c;
+ };
+ typedef std::unordered_map<IdString,LC> CodeMap;
+
+ /** Ctor initializes the code maps. */
+ CodeMaps()
+ : _codeMap( { { IdString::Null, LC( LanguageCode(IdString::Null), CountryCode(IdString::Null) ) }
+ , { IdString::Empty, LC( LanguageCode(IdString::Empty), CountryCode(IdString::Empty) ) } } )
+ {}
- LanguageCode _language;
- CountryCode _country;
-
- public:
- /** Offer default Impl. */
- static shared_ptr<Impl> nullimpl()
+ /** Return \ref LC for \a index_r, creating it if necessary. */
+ const LC & getIndex( IdString index_r )
{
- static shared_ptr<Impl> _nullimpl( new Impl );
- return _nullimpl;
+ auto it = _codeMap.find( index_r );
+ if ( it == _codeMap.end() )
+ {
+ CodeMap::value_type newval( index_r, LC() );
+
+ boost::string_ref str( index_r.c_str() );
+ boost::string_ref::size_type sep = str.find( '_' );
+ if ( sep == boost::string_ref::npos )
+ newval.second._l = LanguageCode( IdString(index_r) );
+ else
+ {
+ newval.second._l = LanguageCode( IdString(str.substr( 0, sep )) );
+ newval.second._c = CountryCode( IdString(str.substr( sep+1 )) );
+ }
+
+ it = _codeMap.insert( std::move(newval) ).first;
+ }
+ return it->second;
}
- };
- ///////////////////////////////////////////////////////////////////
- /** \relates Locale::Impl Stream output */
- inline std::ostream & operator<<( std::ostream & str, const Locale::Impl & obj )
- {
- return str << "Locale::Impl";
- }
+ private:
+ CodeMap _codeMap;
+ };
///////////////////////////////////////////////////////////////////
- //
- // CLASS NAME : Locale
- //
+ // class Locale
///////////////////////////////////////////////////////////////////
const Locale Locale::noCode;
+ const LanguageCode LanguageCode::enCode("en"); // from in LanguageCode.cc as Locale::enCode depends on it
+ const Locale Locale::enCode( LanguageCode::enCode );
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : Locale::Locale
- // METHOD TYPE : Ctor
- //
Locale::Locale()
- : _pimpl( Impl::nullimpl() )
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : Locale::Locale
- // METHOD TYPE : Ctor
- //
- Locale::Locale( IdString code_r )
- : _pimpl( new Impl( code_r.asString() ) )
+ Locale::Locale( IdString str_r )
+ : _str( CodeMaps::withoutTrash( str_r ) )
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : Locale::Locale
- // METHOD TYPE : Ctor
- //
- Locale::Locale( const std::string & code_r )
- : _pimpl( new Impl( code_r ) )
+ Locale::Locale( const std::string & str_r )
+ : _str( CodeMaps::withoutTrash( str_r ) )
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : Locale::Locale
- // METHOD TYPE : Ctor
- //
- Locale::Locale( const char * code_r )
- : _pimpl( new Impl( C_Str(code_r).c_str() ) )
+ Locale::Locale( const char * str_r )
+ : _str( CodeMaps::withoutTrash( str_r ) )
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : Locale::Locale
- // METHOD TYPE : Ctor
- //
- Locale::Locale( const LanguageCode & language_r,
- const CountryCode & country_r )
- : _pimpl( new Impl( language_r, country_r ) )
+ Locale::Locale( LanguageCode language_r, CountryCode country_r )
+ : _str( CodeMaps::combineLC( language_r, country_r ) )
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : Locale::~Locale
- // METHOD TYPE : Dtor
- //
Locale::~Locale()
{}
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : Locale::
- // METHOD TYPE :
- //
- const LanguageCode & Locale::language() const
- { return _pimpl->language(); }
+ LanguageCode Locale::language() const
+ { return CodeMaps::instance().language( _str ); }
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : Locale::
- // METHOD TYPE :
- //
- const CountryCode & Locale::country() const
- { return _pimpl->country(); }
+ CountryCode Locale::country() const
+ { return CodeMaps::instance().country( _str ); }
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : Locale::
- // METHOD TYPE :
- //
- std::string Locale::code() const
- { return _pimpl->code(); }
-
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : Locale::
- // METHOD TYPE :
- //
std::string Locale::name() const
- { return _pimpl->name(); }
+ { return CodeMaps::instance().name( _str ); }
- ///////////////////////////////////////////////////////////////////
- //
- // METHOD NAME : Locale::
- // METHOD TYPE :
- //
Locale Locale::fallback() const
- { return _pimpl->fallback(); }
-
+ { return CodeMaps::instance().fallback( _str ); }
///////////////////////////////////////////////////////////////////
- Locale Locale::bestMatch( const LocaleSet & avLocales_r, const Locale & requested_r )
+ Locale Locale::bestMatch( const LocaleSet & avLocales_r, Locale requested_r )
{
if ( ! avLocales_r.empty() )
{
- for ( Locale check( requested_r == noCode ? ZConfig::instance().textLocale() : requested_r );
- check != noCode; check = check.fallback() )
+ if ( ! requested_r )
+ requested_r = ZConfig::instance().textLocale();
+ for ( ; requested_r; requested_r = requested_r.fallback() )
{
- if ( avLocales_r.find( check ) != avLocales_r.end() )
- return check;
+ if ( avLocales_r.count( requested_r ) )
+ return requested_r;
}
}
- return noCode;
+ return Locale();
}
-
- /////////////////////////////////////////////////////////////////
} // namespace zypp
///////////////////////////////////////////////////////////////////
#define ZYPP_LOCALE_H
#include <iosfwd>
+#include <string>
-#include "zypp/base/PtrTypes.h"
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
-#include "zypp/IdString.h"
+#include "zypp/IdStringType.h"
#include "zypp/LanguageCode.h"
#include "zypp/CountryCode.h"
///////////////////////////////////////////////////////////////////
namespace zypp
-{ /////////////////////////////////////////////////////////////////
-
+{
class Locale;
- typedef std::tr1::unordered_set<Locale> LocaleSet;
+ typedef std::unordered_set<Locale> LocaleSet;
///////////////////////////////////////////////////////////////////
- //
- // CLASS NAME : Locale
- //
- /**
- * \todo migrate to IdString
- */
- class Locale
+ /// \class Locale
+ /// \brief 'Language[_Country]' codes.
+ ///
+ /// In fact the class will not prevent to use a non iso code.
+ /// Just a warning will appear in the log. Construction from string
+ /// consider everything up to the first \c '.' or \c '@'.
+ /// \code
+ /// Locale l( "de_DE.UTF-8" );
+ ///
+ /// l.code() == "de_DE";
+ /// l.language() == "de";
+ /// l.country() == "DE";
+ ///
+ /// l.fallback() == "de";
+ /// l.fallback().fallback() == Locale::enCode == "en";
+ /// l.fallback().fallback().fallback() == Locale::noCode == "";
+ /// \endcode
+ ///////////////////////////////////////////////////////////////////
+ class Locale : public IdStringType<Locale>
{
- friend std::ostream & operator<<( std::ostream & str, const Locale & obj );
-
- public:
- /** Implementation */
- class Impl;
-
public:
- /** Default ctor */
+ /** Default Ctor: \ref noCode */
Locale();
- /** Ctor taking a string. */
- explicit
- Locale( IdString code_r );
+ /** Ctor from string. */
+ explicit Locale( IdString str_r );
- explicit
- Locale( const std::string & code_r );
+ /** Ctor from string. */
+ explicit Locale( const std::string & str_r );
- explicit
- Locale( const char * code_r );
+ /** Ctor from string. */
+ explicit Locale( const char * str_r );
/** Ctor taking LanguageCode and optional CountryCode. */
- Locale( const LanguageCode & language_r,
- const CountryCode & country_r = CountryCode() );
+ Locale( LanguageCode language_r, CountryCode country_r = CountryCode() );
/** Dtor */
~Locale();
public:
/** \name Locale constants. */
//@{
- /** No or empty code. */
+ /** Empty code. */
static const Locale noCode;
+
+ /** Last resort "en". */
+ static const Locale enCode;
//@}
public:
- /** */
- const LanguageCode & language() const;
- /** */
- const CountryCode & country() const;
+ /** The language part. */
+ LanguageCode language() const;
- /** Return the locale code. */
- std::string code() const;
+ /** The county part.*/
+ CountryCode country() const;
- /** Return the name made of language and country name. */
- std::string name() const;
+ /** Return the locale code asString. */
+ std::string code() const
+ { return std::string(_str); }
- /** Return a fallback locale for this locale, when giving up, returns empty Locale() */
- Locale fallback() const;
+ /** Return the translated locale name. */
+ std::string name() const;
public:
+ /** Return the fallback locale for this locale, if no fallback exists the empty Locale::noCode.
+ * The usual fallback sequence is "language_COUNTRY" -> "language" -> Locale::enCode ("en")
+ * ->Locale::noCode (""). Some exceptions like "pt_BR"->"en"->"" do exist.
+ */
+ Locale fallback() const;
- /** Return the best match for \ref Locale \c requested_r within the available \c avLocales_r.
+ /** Return the best match for \ref Locale \a requested_r within the available \a avLocales_r.
*
- * If \c requested_r is nor specified or equals \ref Locale::noCode,
- * \ref ZConfig::textLocale is assumed.
+ * If \a requested_r is not specified \ref ZConfig::textLocale is assumed.
*
- * If neither \c requested_r nor any of it's \ref fallback locales
- * are available, \ref Locale::noCode is returned.
- */
- static Locale bestMatch( const LocaleSet & avLocales_r, const Locale & requested_r = Locale() );
+ * If neither \c requested_r nor any of it's \ref fallback locales are available
+ * in \a avLocales_r, \ref Locale::noCode is returned.
+ */
+ static Locale bestMatch( const LocaleSet & avLocales_r, Locale requested_r = Locale() );
private:
- /** Pointer to implementation */
- RW_pointer<Impl> _pimpl;
+ friend class IdStringType<Locale>;
+ IdString _str;
};
- ///////////////////////////////////////////////////////////////////
-
- /** \relates Locale Stream output */
- inline std::ostream & operator<<( std::ostream & str, const Locale & obj )
- { return str << obj.code(); }
-
- /** Comparison based on string value. */
- //@{
- /** \relates Locale */
- inline bool operator==( const Locale & lhs, const Locale & rhs ) {
- return( lhs.code() == rhs.code() );
- }
- /** \relates Locale */
- inline bool operator==( const std::string & lhs, const Locale & rhs ) {
- return( lhs == rhs.code() );
- }
- /** \relates Locale */
- inline bool operator==( const Locale & lhs, const std::string & rhs ) {
- return( lhs.code() == rhs );
- }
-
- /** \relates Locale */
- inline bool operator!=( const Locale & lhs, const Locale & rhs ) {
- return( ! operator==( lhs, rhs ) );
- }
- /** \relates Locale */
- inline bool operator!=( const std::string & lhs, const Locale & rhs ) {
- return( ! operator==( lhs, rhs ) );
- }
- /** \relates Locale */
- inline bool operator!=( const Locale & lhs, const std::string & rhs ) {
- return( ! operator==( lhs, rhs ) );
- }
- //@}
-
- /////////////////////////////////////////////////////////////////
} // namespace zypp
///////////////////////////////////////////////////////////////////
-namespace std { namespace tr1 {
- /** \relates ::zypp::Locale hash function */
- template<> struct hash< ::zypp::Locale>
- {
- size_t operator()( const ::zypp::Locale & __s ) const
- { return hash<std::string>()(__s.code()); }
- };
-}}
+ZYPP_DEFINE_ID_HASHABLE( ::zypp::Locale );
-///////////////////////////////////////////////////////////////////
-namespace std
-{ /////////////////////////////////////////////////////////////////
- /** \relates zypp::Locale Default order for std::container based on code string value.*/
- template<>
- inline bool less<zypp::Locale>::operator()( const zypp::Locale & lhs, const zypp::Locale & rhs ) const
- { return lhs.code() < rhs.code(); }
- /////////////////////////////////////////////////////////////////
-} // namespace std
-///////////////////////////////////////////////////////////////////
#endif // ZYPP_LOCALE_H
#include "zypp/base/PtrTypes.h"
#include "zypp/base/Function.h"
#include "zypp/base/Iterator.h"
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/PoolItem.h"
*/
class PoolItemBest
{
- typedef std::tr1::unordered_map<IdString,PoolItem> Container;
+ typedef std::unordered_map<IdString,PoolItem> Container;
public:
/** Predicate returning \c True if \a lhs is a better choice. */
typedef boost::function<bool ( const PoolItem & lhs, const PoolItem & rhs )> Predicate;
#include <iosfwd>
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/base/Exception.h"
#include "zypp/sat/SolvIterMixin.h"
* MIL << result << endl;
* \endcode
*/
- class PoolQueryResult : public sat::SolvIterMixin<PoolQueryResult,std::tr1::unordered_set<sat::Solvable>::const_iterator>
+ class PoolQueryResult : public sat::SolvIterMixin<PoolQueryResult,std::unordered_set<sat::Solvable>::const_iterator>
{
public:
- typedef std::tr1::unordered_set<sat::Solvable> ResultSet;
+ typedef std::unordered_set<sat::Solvable> ResultSet;
typedef ResultSet::size_type size_type;
typedef ResultSet::const_iterator const_iterator;
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
* 02111-1307, USA.
*/
-#include "zypp/solver/detail/Types.h"
+
+#define ZYPP_USE_RESOLVER_INTERNALS
+
+#include "zypp/base/Gettext.h"
#include "zypp/solver/detail/SolutionAction.h"
#include "zypp/ProblemSolution.h"
#include "zypp/base/Logger.h"
#include "zypp/solver/detail/Resolver.h"
-using namespace std;
+using std::endl;
/////////////////////////////////////////////////////////////////////////
namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
-
-IMPL_PTR_TYPE(ProblemSolution);
-
-//---------------------------------------------------------------------------
-
-ostream&
-operator<<( ostream& os, const ProblemSolution & solution)
{
- os << "Solution:" << endl;
- os << solution._description << endl;
- if ( ! solution._details.empty() )
- os << solution._details << endl;
- os << solution._actions;
- return os;
-}
-
-ostream&
-operator<<( ostream& os, const ProblemSolutionList & solutionlist)
-{
- for (ProblemSolutionList::const_iterator iter = solutionlist.begin(); iter != solutionlist.end(); ++iter) {
- os << *(*iter);
+ IMPL_PTR_TYPE(ProblemSolution);
+
+ ///////////////////////////////////////////////////////////////////
+ /// \class ProblemSolution::Impl
+ /// \brief ProblemSolution implementation.
+ ///////////////////////////////////////////////////////////////////
+ struct ProblemSolution::Impl
+ {
+ Impl()
+ {}
+
+ Impl( std::string && description )
+ : _description( std::move(description) )
+ {}
+
+ Impl( std::string && description, std::string && details )
+ : _description( std::move(description) )
+ , _details( std::move(details) )
+ {}
+
+ std::string _description;
+ std::string _details;
+ SolutionActionList _actions;
+
+ private:
+ friend Impl * rwcowClone<Impl>( const Impl * rhs );
+ /** clone for RWCOW_pointer */
+ Impl * clone() const
+ { return new Impl( *this ); }
+ };
+ ///////////////////////////////////////////////////////////////////
+
+ ProblemSolution::ProblemSolution()
+ : _pimpl( new Impl() )
+ {}
+
+ ProblemSolution::ProblemSolution( std::string description )
+ : _pimpl( new Impl( std::move(description) ) )
+ {}
+
+ ProblemSolution::ProblemSolution( std::string description, std::string details )
+ : _pimpl( new Impl( std::move(description), std::move(details) ) )
+ {}
+
+ ProblemSolution::~ProblemSolution()
+ {}
+
+
+ const std::string & ProblemSolution::description() const
+ { return _pimpl->_description; }
+
+ const std::string & ProblemSolution::details() const
+ { return _pimpl->_details; }
+
+ const ProblemSolution::SolutionActionList & ProblemSolution::actions() const
+ { return _pimpl->_actions; }
+
+
+ void ProblemSolution::setDescription( std::string description )
+ { _pimpl->_description = std::move(description); }
+
+ void ProblemSolution::setDetails( std::string details )
+ { _pimpl->_details += "\n"; _pimpl->_details += std::move(details); }
+
+ void ProblemSolution::pushDescriptionDetail( std::string description, bool front )
+ {
+ if ( _pimpl->_details.empty() )
+ {
+ if ( _pimpl->_description.empty() ) // first entry
+ {
+ _pimpl->_description = std::move(description);
+ return;
+ }
+ else // second entry: form headline in _description
+ {
+ _pimpl->_description.swap( _pimpl->_details );
+ _pimpl->_description = _("Following actions will be done:");
+ }
}
- return os;
-}
-
-ostream&
-operator<<( ostream& os, const CProblemSolutionList & solutionlist)
-{
- for (CProblemSolutionList::const_iterator iter = solutionlist.begin(); iter != solutionlist.end(); ++iter) {
- os << *(*iter) << endl;
- }
- return os;
-}
-
-//---------------------------------------------------------------------------
+ if ( front )
+ { _pimpl->_details.swap( description ); }
+ _pimpl->_details += "\n";
+ _pimpl->_details += std::move(description);
+ }
-ProblemSolution::ProblemSolution( ResolverProblem_Ptr parent, const string & description, const string & details )
- : _problem (parent)
- , _description (description)
- , _details (details)
-{
-}
-
-
-ProblemSolution::~ProblemSolution()
-{
-}
+ void ProblemSolution::addAction( solver::detail::SolutionAction_Ptr action )
+ { _pimpl->_actions.push_back( action ); }
-/**
- * Apply this solution, i.e. execute all of its actions.
- *
- * Returns 'true' on success, 'false' if actions could not be performed.
- **/
-
-bool
-ProblemSolution::apply (solver::detail::Resolver & resolver)
-{
- DBG << "apply solution " << *this << endl;
- bool ret = true;
- for (solver::detail::CSolutionActionList::const_iterator iter = _actions.begin();
- iter != _actions.end(); ++iter) {
- solver::detail::SolutionAction_constPtr action = *iter;
- if (! action->execute (resolver))
- {
- WAR << "apply solution action failed: " << action << endl;
- ret = false;
- break;
- }
- }
- return ret;
-}
-
-
-/**
- * Add an action to the actions list.
- **/
-void
-ProblemSolution::addAction (solver::detail::SolutionAction_constPtr action)
-{
- _actions.push_back (action);
-}
+ std::ostream & operator<<( std::ostream & os, const ProblemSolution & obj )
+ {
+ os << "Solution:" << endl;
+ os << obj.description() << endl;
+ if ( ! obj.details().empty() )
+ os << obj.details() << endl;
+ os << obj.actions();
+ return os;
+ }
-void
-ProblemSolution::clear()
-{
- _actions.clear();
-}
+ std::ostream & operator<<( std::ostream & os, const ProblemSolutionList & obj )
+ {
+ for ( const auto & ptr: obj )
+ { os << ptr; }
+ return os;
+ }
- ///////////////////////////////////////////////////////////////////////
-};// namespace zypp
+} // namespace zypp
/////////////////////////////////////////////////////////////////////////
#include <list>
#include <string>
-#include "zypp/base/ReferenceCounted.h"
-#include "zypp/base/PtrTypes.h"
-#include "zypp/solver/detail/Resolver.h"
+#include "zypp/ProblemTypes.h"
#include "zypp/ResolverProblem.h"
-#include "zypp/solver/detail/SolutionAction.h"
-#include "zypp/solver/detail/Types.h"
/////////////////////////////////////////////////////////////////////////
namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
+{
+ /////////////////////////////////////////////////////////////////////////
+ /// \class ProblemSolution
+ /// \brief Class representing one possible solution to one problem found during resolving
+ ///
+ /// All problems should have at least 2-3 (mutually exclusive) solutions:
+ ///
+ /// - Undo: Do not perform the offending transaction
+ /// (do not install the package that had unsatisfied requirements,
+ /// do not remove the package that would break other packages' requirements)
+ ///
+ /// - Remove referrers: Remove all packages that would break because
+ /// they depend on the package that is requested to be removed
+ ///
+ /// - Ignore: Inject artificial "provides" for a missing requirement
+ /// (pretend that requirement is satisfied)
+ /////////////////////////////////////////////////////////////////////////
+ class ProblemSolution : public base::ReferenceCounted
+ {
+ public:
+ typedef solver::detail::SolutionAction_Ptr SolutionAction_Ptr;
+ typedef solver::detail::SolutionActionList SolutionActionList;
+
+ /** Constructor. */
+ ProblemSolution();
+
+ /** Constructor. */
+ ProblemSolution( std::string description );
+
+ /** Constructor. */
+ ProblemSolution( std::string description, std::string details );
+
+ /** Destructor. */
+ virtual ~ProblemSolution();
/**
- * Class representing one possible solution to one problem found during resolving
- *
- * All problems should have at least 2-3 (mutually exclusive) solutions:
- *
- * - Undo: Do not perform the offending transaction
- * (do not install the package that had unsatisfied requirements,
- * do not remove the package that would break other packages' requirements)
- *
- * - Remove referrers: Remove all packages that would break because
- * they depend on the package that is requested to be removed
- *
- * - Ignore: Inject artificial "provides" for a missing requirement
- * (pretend that requirement is satisfied)
+ * Return a one-line text description of this solution.
**/
- class ProblemSolution : public base::ReferenceCounted
- {
- protected:
-
- /**
- * Clear all data.
- * In particular, delete all members of _actions.
- **/
- void clear();
-
- //
- // Data members
- //
- ResolverProblem_Ptr _problem;
- solver::detail::CSolutionActionList _actions;
- std::string _description;
- std::string _details;
-
- public:
-
- /**
- * Constructor.
- **/
- ProblemSolution( ResolverProblem_Ptr parent, const std::string & description, const std::string & details );
-
- /**
- * Destructor.
- **/
- ~ProblemSolution();
-
- // ---------------------------------- I/O
-
- friend std::ostream& operator<<(std::ostream&, const ProblemSolution & solution);
- friend std::ostream& operator<<(std::ostream&, const ProblemSolutionList & solutionlist);
- friend std::ostream& operator<<(std::ostream&, const CProblemSolutionList & solutionlist);
-
- // ---------------------------------- accessors
- /**
- * Return a one-line text description of this solution.
- **/
- std::string description() const { return _description; }
-
- /**
- * Return a (possibly multi-line) detailed description of this
- * solution or an empty string if there are no useful details.
- **/
- std::string details() const { return _details; }
-
- /**
- * Return the parent dependency problem.
- **/
- ResolverProblem_Ptr problem() const { return _problem; }
-
- // ---------------------------------- methods
-
- /**
- * Apply this solution, i.e. execute all of its actions.
- *
- * Returns 'true' on success, 'false' if actions could not be performed.
- **/
- bool apply (solver::detail::Resolver & resolver);
-
- /**
- * Add an action to the actions list.
- **/
- void addAction( solver::detail::SolutionAction_constPtr action );
-
- solver::detail::CSolutionActionList actions() {return _actions;}
-
- };
-
-
- ///////////////////////////////////////////////////////////////////////
-};// namespace zypp
-/////////////////////////////////////////////////////////////////////////
+ const std::string & description() const;
+
+ /**
+ * Return a (possibly multi-line) detailed description of this
+ * solution or an empty string if there are no useful details.
+ **/
+ const std::string & details() const;
+
+ /**
+ * Return the list of actions forming this solution.
+ **/
+ const SolutionActionList & actions() const;
+
+
+ /**
+ * Return the parent dependency problem.
+ **/
+ ResolverProblem_Ptr problem() const { return nullptr; }
+
+
+ /**
+ * Set description of the problem.
+ **/
+ void setDescription( std::string description );
+ /**
+ * Set detail description of the problem.
+ **/
+ void setDetails( std::string details );
+
+ /**
+ * Collect multiple action descriptions in \ref details (NL separated)
+ **/
+ void pushDescriptionDetail( std::string description, bool front = false );
+
+
+ /**
+ * Add an action to the actions list.
+ **/
+ void addAction( SolutionAction_Ptr action );
+
+
+ private:
+ class Impl;
+ RWCOW_pointer<Impl> _pimpl;
+ };
+
+ /** \relates ProblemSolution Stream output */
+ std::ostream& operator<<(std::ostream&, const ProblemSolution & obj );
+
+ /** \relates ProblemSolution Stream output */
+ std::ostream& operator<<(std::ostream&, const ProblemSolutionList & obj );
+
+} // namespace zypp
+/////////////////////////////////////////////////////////////////////////
#endif // ZYPP_PROBLEMSOLUTION_H
#define ZYPP_PROBLEMTYPES_H
#include <iosfwd>
+#include <string>
#include <list>
#include <set>
#include <map>
-#include <string>
#include "zypp/base/ReferenceCounted.h"
#include "zypp/base/NonCopyable.h"
#include "zypp/base/PtrTypes.h"
#include "zypp/base/Functional.h"
+#include "zypp/solver/detail/Types.h" // SolutionAction type
+
/////////////////////////////////////////////////////////////////////////
namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
-
- DEFINE_PTR_TYPE(Resolver);
-
- DEFINE_PTR_TYPE(ProblemSolution);
- typedef std::list<ProblemSolution_Ptr> ProblemSolutionList;
- typedef std::list<ProblemSolution_constPtr> CProblemSolutionList;
-
- DEFINE_PTR_TYPE(ResolverProblem);
- typedef std::list<ResolverProblem_Ptr> ResolverProblemList;
- typedef std::list<ResolverProblem_constPtr> CResolverProblemList;
-
- ///////////////////////////////////////////////////////////////////////
-};// namespace zypp
-/////////////////////////////////////////////////////////////////////////
+{
+ DEFINE_PTR_TYPE(Resolver);
+ DEFINE_PTR_TYPE(ProblemSolution);
+ typedef std::list<ProblemSolution_Ptr> ProblemSolutionList;
+
+ DEFINE_PTR_TYPE(ResolverProblem);
+ typedef std::list<ResolverProblem_Ptr> ResolverProblemList;
+
+} // namespace zypp
+/////////////////////////////////////////////////////////////////////////
#endif // ZYPP_SOLVER_DETAIL_TYPES_H
return std::string();
Locale getLang( Locale::bestMatch( avlocales, lang_r ) );
- if ( getLang == Locale::noCode
- && avlocales.find( Locale::noCode ) == avlocales.end() )
+ if ( !getLang && avlocales.find( Locale::noCode ) == avlocales.end() )
{
WAR << "License.tar.gz contains no fallback text! " << *this << endl;
// Using the fist locale instead of returning no text at all.
// now extract the license file.
static const std::string licenseFileFallback( "license.txt" );
- std::string licenseFile( getLang == Locale::noCode
- ? licenseFileFallback
- : str::form( "license.%s.txt", getLang.code().c_str() ) );
+ std::string licenseFile( !getLang ? licenseFileFallback
+ : str::form( "license.%s.txt", getLang.c_str() ) );
ExternalProgram::Arguments cmd;
cmd.push_back( "tar" );
friend std::ostream & operator<<( std::ostream & str, const Impl & obj );
friend std::ostream & dumpOn( std::ostream & str, const Impl & obj );
- typedef std::tr1::unordered_map<sat::detail::IdType,ui::Selectable::Ptr> SelectableIndex;
+ typedef std::unordered_map<sat::detail::IdType,ui::Selectable::Ptr> SelectableIndex;
typedef ResPoolProxy::const_iterator const_iterator;
public:
*/
#include <iostream>
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/Resolver.h"
#include "zypp/ZConfig.h"
#include "zypp/TriBool.h"
#include "zypp/solver/detail/Resolver.h"
#include "zypp/solver/detail/Testcase.h"
+#include "zypp/solver/detail/ItemCapKind.h"
#include "zypp/sat/Transaction.h"
using namespace std;
// METHOD TYPE : Ctor
//
Resolver::Resolver( const ResPool & pool )
- : _pimpl( new Impl(pool) )
+ : _pimpl( new solver::detail::ResolverInternal(pool) )
{}
///////////////////////////////////////////////////////////////////
#include "zypp/base/PtrTypes.h"
#include "zypp/ResPool.h"
-#include "zypp/solver/detail/Resolver.h"
-#include "zypp/solver/detail/SolverQueueItem.h"
+#include "zypp/PoolItem.h"
+#include "zypp/Capabilities.h"
+#include "zypp/Capability.h"
+
+#include "zypp/solver/detail/Types.h"
+
#include "zypp/ProblemTypes.h"
+#include "zypp/ResolverProblem.h"
+#include "zypp/ProblemSolution.h"
///////////////////////////////////////////////////////////////////
namespace zypp
private:
friend std::ostream & operator<<( std::ostream & str, const Resolver & obj );
-
- typedef solver::detail::Resolver Impl;
- zypp::RW_pointer<Impl,rw_pointer::Intrusive<Impl> > _pimpl;
+ zypp::RW_pointer<solver::detail::ResolverInternal> _pimpl;
};
///////////////////////////////////////////////////////////////////
--- /dev/null
+/*---------------------------------------------------------------------\
+| ____ _ __ __ ___ |
+| |__ / \ / / . \ . \ |
+| / / \ V /| _/ _/ |
+| / /__ | | | | | | |
+| /_____||_| |_| |_| |
+| |
+\---------------------------------------------------------------------*/
+/** \file zypp/ResolverNamespace.h
+ */
+#ifndef ZYPP_RESOLVERNAMESPACE_H
+#define ZYPP_RESOLVERNAMESPACE_H
+
+#include <iosfwd>
+#include <cstdint>
+
+#include "zypp/base/Flags.h"
+#include "zypp/IdString.h"
+
+///////////////////////////////////////////////////////////////////
+namespace zypp
+{
+ /** The resolvers dependency namespaces */
+ enum class ResolverNamespace : std::uint8_t
+ {
+ language = 1<<0, ///< language support
+ modalias = 1<<1, ///< hardware support
+ filesystem = 1<<2, ///< filesystems
+ };
+
+ /** \relates ResolverNamespace Flags */
+ ZYPP_DECLARE_FLAGS_AND_OPERATORS(ResolverNamespaces,ResolverNamespace);
+
+ /** \relates ResolverNamespace The underlying libsolv ID */
+ inline constexpr IdString asIdString( ResolverNamespace obj )
+ {
+ return IdString( obj == ResolverNamespace::language ? sat::detail::namespaceLanguage
+ : obj == ResolverNamespace::modalias ? sat::detail::namespaceModalias
+ : obj == ResolverNamespace::filesystem ? sat::detail::namespaceFilesystem
+ : sat::detail::noId );
+ }
+
+ /** \relates ResolverNamespace String representation */
+ inline std::string asString( ResolverNamespace obj )
+ { return asIdString( obj ).asString(); }
+
+ /** \relates ResolverNamespace Stream output */
+ inline std::ostream & operator<<( std::ostream & str, ResolverNamespace obj )
+ { return str << asIdString( obj ); }
+
+ /** \relates ResolverNamespaces Stream output */
+ inline std::ostream & operator<<( std::ostream & str, ResolverNamespaces obj )
+ {
+ return str << stringify( obj, {
+ { ResolverNamespace::language, "language" },
+ { ResolverNamespace::modalias, "modalias" },
+ { ResolverNamespace::filesystem, "filesystem" },
+ }, "namespace:", "|", "" );
+ }
+
+} // namespace zypp
+///////////////////////////////////////////////////////////////////
+#endif // ZYPP_RESOLVERNAMESPACE_H
* 02111-1307, USA.
*/
+#include "zypp/base/LogTools.h"
+
#include "zypp/ResolverProblem.h"
#include "zypp/ProblemSolution.h"
-using namespace std;
+using std::endl;
/////////////////////////////////////////////////////////////////////////
namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
+{
+ IMPL_PTR_TYPE(ResolverProblem);
-IMPL_PTR_TYPE(ResolverProblem);
+ ///////////////////////////////////////////////////////////////////
+ /// \class ResolverProblem::Impl
+ /// \brief ResolverProblem implementation.
+ ///////////////////////////////////////////////////////////////////
+ struct ResolverProblem::Impl
+ {
+ Impl()
+ {}
-//---------------------------------------------------------------------------
+ Impl( std::string && description )
+ : _description( std::move(description) )
+ {}
-ostream&
-operator<<( ostream& os, const ResolverProblem & problem)
-{
- os << "Problem:" << endl;
- os << "==============================" << endl;
- os << problem._description << endl;
- os << problem._details << endl;
- os << "------------------------------" << endl;
- os << problem._solutions;
- os << "==============================" << endl;
- return os;
-}
+ Impl( std::string && description, std::string && details )
+ : _description( std::move(description) )
+ , _details( std::move(details) )
+ {}
+ std::string _description;
+ std::string _details;
+ ProblemSolutionList _solutions;
-ostream&
-operator<<( ostream& os, const ResolverProblemList & problemlist)
-{
- for (ResolverProblemList::const_iterator iter = problemlist.begin(); iter != problemlist.end(); ++iter) {
- if (iter != problemlist.begin())
- os << ", ";
- os << (*iter);
- }
- return os;
-}
+ private:
+ friend Impl * rwcowClone<Impl>( const Impl * rhs );
+ /** clone for RWCOW_pointer */
+ Impl * clone() const
+ { return new Impl( *this ); }
+ };
+ ///////////////////////////////////////////////////////////////////
-//---------------------------------------------------------------------------
+ ResolverProblem::ResolverProblem()
+ : _pimpl( new Impl() )
+ {}
-/**
- * Constructor.
- **/
-ResolverProblem::ResolverProblem( const string & description, const string & details )
- : _description (description)
- , _details (details)
-{
-}
+ ResolverProblem::ResolverProblem( std::string description )
+ : _pimpl( new Impl( std::move(description) ) )
+ {}
-/**
- * Destructor.
- **/
-ResolverProblem::~ResolverProblem()
-{
-}
+ ResolverProblem::ResolverProblem( std::string description, std::string details )
+ : _pimpl( new Impl( std::move(description), std::move(details) ) )
+ {}
-/**
- * Return the possible solutions to this problem.
- * All problems should have at least 2-3 (mutually exclusive) solutions:
- *
- * - Undo: Do not perform the offending transaction
- * (do not install the package that had unsatisfied requirements,
- * do not remove the package that would break other packages' requirements)
- *
- * - Remove referrers: Remove all packages that would break because
- * they depend on the package that is requested to be removed
- *
- * - Ignore: Inject artificial "provides" for a missing requirement
- * (pretend that requirement is satisfied)
- **/
+ ResolverProblem::~ResolverProblem()
+ {}
-ProblemSolutionList
-ResolverProblem::solutions() const
-{
- return _solutions;
-}
-/**
- * Add a solution to this problem. This class takes over ownership of
- * the problem and will delete it when neccessary.
- **/
+ const std::string & ResolverProblem::description() const
+ { return _pimpl->_description; }
-void
-ResolverProblem::addSolution( ProblemSolution_Ptr solution,
- bool inFront )
-{
- if (inFront) {
- _solutions.push_front (solution);
- } else {
- _solutions.push_back (solution);
- }
-}
-
-void
-ResolverProblem::clear()
-{
- _solutions.clear();
-}
+ const std::string & ResolverProblem::details() const
+ { return _pimpl->_details; }
+
+ const ProblemSolutionList & ResolverProblem::solutions() const
+ { return _pimpl->_solutions; }
+
+
+ void ResolverProblem::setDescription( std::string description )
+ { _pimpl->_description = std::move(description); }
+
+ void ResolverProblem::setDetails( std::string details )
+ { _pimpl->_details = std::move(details); }
+
+ void ResolverProblem::addSolution( ProblemSolution_Ptr solution, bool inFront )
+ {
+ if (inFront)
+ { _pimpl->_solutions.push_front( solution ); }
+ else
+ { _pimpl->_solutions.push_back( solution ); }
+ }
+
+
+ std::ostream & operator<<( std::ostream & os, const ResolverProblem & obj )
+ {
+ os << "Problem:" << endl;
+ os << "==============================" << endl;
+ os << obj.description() << endl;
+ os << obj.details() << endl;
+ os << "------------------------------" << endl;
+ os << obj.solutions();
+ os << "==============================" << endl;
+ return os;
+ }
+
+ std::ostream & operator<<( std::ostream & os, const ResolverProblemList & obj )
+ { return dumpRange( os, obj.begin(), obj.end(), "", "", ", ", "", "" ); }
- ///////////////////////////////////////////////////////////////////////
-};// namespace zypp
+} // namespace zypp
/////////////////////////////////////////////////////////////////////////
#include <list>
#include <string>
-#include "zypp/base/ReferenceCounted.h"
-#include "zypp/base/PtrTypes.h"
+#include "zypp/ProblemTypes.h"
#include "zypp/ProblemSolution.h"
/////////////////////////////////////////////////////////////////////////
namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
-
-
- class ResolverProblem : public base::ReferenceCounted
- {
- private:
-
- /**
- * Clear all data.
- * In particular, delete all members of _solutions.
- **/
- void clear();
-
-
- //
- // Data members
- //
-
- Resolver_constPtr _resolver;
- std::string _description;
- std::string _details;
- ProblemSolutionList _solutions;
-
- public:
-
- /**
- * Constructor.
- **/
- ResolverProblem( const std::string & description, const std::string & details );
-
- /**
- * Destructor.
- **/
- ~ResolverProblem();
-
- // ---------------------------------- I/O
-
- friend std::ostream& operator<<(std::ostream&, const ResolverProblem & problem);
-
- // ---------------------------------- accessors
-
- /**
- * Return a one-line description of the problem.
- **/
- std::string description() const { return _description; }
-
- /**
- * Return a (possibly muti-line) detailed description of the problem
- * or an empty string if there are no useful details.
- **/
- std::string details() const { return _details; }
-
- /**
- * Set description of the problem.
- **/
- void setDescription(const std::string & description)
- { _description=description; }
-
- /**
- * Set detail description of the problem.
- **/
- void setDetails(const std::string & detail)
- { _details=detail; }
-
- /**
- * Return the possible solutions to this problem.
- * All problems should have at least 2-3 (mutually exclusive) solutions:
- *
- * - Undo: Do not perform the offending transaction
- * (do not install the package that had unsatisfied requirements,
- * do not remove the package that would break other packages' requirements)
- *
- * - Remove referrers: Remove all packages that would break because
- * they depend on the package that is requested to be removed
- *
- * - Ignore: Inject artificial "provides" for a missing requirement
- * (pretend that requirement is satisfied)
- **/
- ProblemSolutionList solutions() const;
-
- /**
- * Return the parent dependency resolver.
- **/
- Resolver_constPtr resolver() const { return _resolver; }
-
- // ---------------------------------- methods
-
- /**
- * Add a solution to this problem. This class takes over ownership of
- * the problem and will delete it when neccessary.
- **/
- void addSolution( ProblemSolution_Ptr solution, bool inFront = false );
-
- };
- ///////////////////////////////////////////////////////////////////////
-};// namespace zypp
+{
+ ///////////////////////////////////////////////////////////////////////
+ /// \class ResolverProblem
+ /// \brief Describe a solver problem and offer solutions.
+ ///////////////////////////////////////////////////////////////////////
+ class ResolverProblem : public base::ReferenceCounted
+ {
+ public:
+ /** Constructor. */
+ ResolverProblem();
+ /** Constructor. */
+ ResolverProblem( std::string description );
+ /** Constructor. */
+ ResolverProblem( std::string description, std::string details );
+
+ /** Destructor. */
+ ~ResolverProblem();
+
+
+ /**
+ * Return a one-line description of the problem.
+ **/
+ const std::string & description() const;
+
+ /**
+ * Return a (possibly muti-line) detailed description of the problem
+ * or an empty string if there are no useful details.
+ **/
+ const std::string & details() const;
+
+ /**
+ * Return the possible solutions to this problem.
+ * All problems should have at least 2-3 (mutually exclusive) solutions:
+ *
+ * - Undo: Do not perform the offending transaction
+ * (do not install the package that had unsatisfied requirements,
+ * do not remove the package that would break other packages' requirements)
+ *
+ * - Remove referrers: Remove all packages that would break because
+ * they depend on the package that is requested to be removed
+ *
+ * - Ignore: Inject artificial "provides" for a missing requirement
+ * (pretend that requirement is satisfied)
+ **/
+ const ProblemSolutionList & solutions() const;
+
+
+ /**
+ * Set description of the problem.
+ **/
+ void setDescription( std::string description );
+
+ /**
+ * Set detail description of the problem.
+ **/
+ void setDetails( std::string details );
+
+ /**
+ * Add a solution to this problem. This class takes over ownership of
+ * the problem and will delete it when neccessary.
+ **/
+ void addSolution( ProblemSolution_Ptr solution, bool inFront = false );
+
+ private:
+ class Impl;
+ RWCOW_pointer<Impl> _pimpl;
+ };
+
+ /** \relates ResolverProblem Stream output */
+ std::ostream & operator<<( std::ostream &, const ResolverProblem & obj );
+
+ /** \relates ResolverProblem Stream output */
+ std::ostream & operator<<( std::ostream &, const ResolverProblemList & obj );
+
+
+} // namespace zypp
/////////////////////////////////////////////////////////////////////////
-
#endif // ZYPP_RESOLVERPROBLEM_H
namespace
{ /////////////////////////////////////////////////////////////////
typedef DefaultIntegral<int,0> VendorMatchEntry;
- typedef std::tr1::unordered_map<IdString, VendorMatchEntry> VendorMatch;
+ typedef std::unordered_map<IdString, VendorMatchEntry> VendorMatch;
int _nextId = -1;
VendorMatch _vendorMatch;
*/
Locale _autodetectTextLocale()
{
- Locale ret( "en" );
+ Locale ret( Locale::enCode );
const char * envlist[] = { "LC_ALL", "LC_MESSAGES", "LANG", NULL };
for ( const char ** envvar = envlist; *envvar; ++envvar )
{
if ( envstr != "POSIX" && envstr != "C" )
{
Locale lang( envstr );
- if ( ! lang.code().empty() )
+ if ( lang )
{
MIL << "Found " << *envvar << "=" << envstr << endl;
ret = lang;
*/
struct TraceCADBase
{
- enum What { CTOR, COPYCTOR, ASSIGN, DTOR, PING };
+ enum What { CTOR, COPYCTOR, MOVECTOR, ASSIGN, MOVEASSIGN, DTOR, PING };
std::string _ident;
};
{
switch( obj )
{
- case TraceCADBase::CTOR: return str << "CTOR";
- case TraceCADBase::COPYCTOR: return str << "COPYCTOR";
- case TraceCADBase::ASSIGN: return str << "ASSIGN";
- case TraceCADBase::DTOR: return str << "DTOR";
- case TraceCADBase::PING: return str << "PING";
+ case TraceCADBase::CTOR: return str << "CTOR";
+ case TraceCADBase::COPYCTOR: return str << "COPYCTOR";
+ case TraceCADBase::MOVECTOR: return str << "MOVECTOR";
+ case TraceCADBase::ASSIGN: return str << "ASSIGN";
+ case TraceCADBase::MOVEASSIGN: return str << "MOVEASSIGN";
+ case TraceCADBase::DTOR: return str << "DTOR";
+ case TraceCADBase::PING: return str << "PING";
}
return str;
}
{ ++_totalTraceCAD();
traceCAD( COPYCTOR, *this, rhs ); }
+ TraceCAD( TraceCAD && rhs )
+ { ++_totalTraceCAD();
+ traceCAD( MOVECTOR, *this, rhs ); }
+
TraceCAD & operator=( const TraceCAD & rhs )
{ traceCAD( ASSIGN, *this, rhs ); return *this; }
+ TraceCAD & operator=( TraceCAD && rhs )
+ { traceCAD( MOVEASSIGN, *this, rhs ); return *this; }
+
virtual ~TraceCAD()
{ --_totalTraceCAD();
traceCAD( DTOR, *this, *this ); }
break;
case TraceCADBase::COPYCTOR:
+ case TraceCADBase::MOVECTOR:
case TraceCADBase::ASSIGN:
+ case TraceCADBase::MOVEASSIGN:
_DBG("DEBUG") << what_r << self_r << "( " << rhs_r << ")" << " (" << self_r._ident << ")" << std::endl;
break;
}
typedef typename std::underlying_type<Enum>::type Integral; ///< The underlying integral type
public:
- constexpr Flags() : _val( 0 ) {}
- constexpr Flags( Enum flag_r ) : _val( flag_r ) {}
- explicit constexpr Flags( Integral flag_r ) : _val( flag_r ) {}
+ constexpr Flags() : _val( 0 ) {}
+ constexpr Flags( Enum flag_r ) : _val( integral(flag_r) ) {}
+ constexpr explicit Flags( Integral flag_r ) : _val( flag_r ) {}
- Flags & operator&=( Flags rhs ) { _val &= rhs._val; return *this; }
- Flags & operator&=( Enum rhs ) { _val &= rhs; return *this; }
+ constexpr static Flags none() { return Flags( Integral(0) ); }
+ constexpr static Flags all() { return Flags( ~Integral(0) ); }
- Flags & operator|=( Flags rhs ) { _val |= rhs._val; return *this; }
- Flags & operator|=( Enum rhs ) { _val |= rhs; return *this; }
+ constexpr bool isNone() const { return _val == Integral(0); }
+ constexpr bool isAll() const { return _val == ~Integral(0); }
- Flags & operator^=( Flags rhs ) { _val ^= rhs._val; return *this; }
- Flags & operator^=( Enum rhs ) { _val ^= rhs; return *this; }
+ Flags & operator&=( Flags rhs ) { _val &= integral(rhs); return *this; }
+ Flags & operator&=( Enum rhs ) { _val &= integral(rhs); return *this; }
+
+ Flags & operator|=( Flags rhs ) { _val |= integral(rhs); return *this; }
+ Flags & operator|=( Enum rhs ) { _val |= integral(rhs); return *this; }
+
+ Flags & operator^=( Flags rhs ) { _val ^= integral(rhs); return *this; }
+ Flags & operator^=( Enum rhs ) { _val ^= integral(rhs); return *this; }
public:
- constexpr operator Integral() const { return _val; }
+ constexpr operator Integral() const { return _val; }
+
+ constexpr Flags operator&( Flags rhs ) const { return Flags( _val & integral(rhs) ); }
+ constexpr Flags operator&( Enum rhs ) const { return Flags( _val & integral(rhs) ); }
- constexpr Flags operator&( Flags rhs ) const { return Flags( _val & rhs._val ); }
- constexpr Flags operator&( Enum rhs ) const { return Flags( _val & rhs ); }
+ constexpr Flags operator|( Flags rhs ) const { return Flags( _val | integral(rhs) ); }
+ constexpr Flags operator|( Enum rhs ) const { return Flags( _val | integral(rhs) ); }
- constexpr Flags operator|( Flags rhs ) const { return Flags( _val | rhs._val ); }
- constexpr Flags operator|( Enum rhs ) const { return Flags( _val | rhs ); }
+ constexpr Flags operator^( Flags rhs ) const { return Flags( _val ^ integral(rhs) ); }
+ constexpr Flags operator^( Enum rhs ) const { return Flags( _val ^ integral(rhs) ); }
- constexpr Flags operator^( Flags rhs ) const { return Flags( _val ^ rhs._val ); }
- constexpr Flags operator^( Enum rhs ) const { return Flags( _val ^ rhs ); }
+ constexpr Flags operator~() const { return Flags( ~_val ); }
- constexpr Flags operator~() const { return Flags( ~_val ); }
+ constexpr bool operator==( Enum rhs ) const { return( _val == integral(rhs) ); }
+ constexpr bool operator!=( Enum rhs ) const { return( _val != integral(rhs) ); }
public:
- Flags & setFlag( Flags flag_r, bool newval_r ) { return( newval_r ? setFlag(flag_r) : unsetFlag(flag_r) ); }
- Flags & setFlag( Enum flag_r, bool newval_r ) { return( newval_r ? setFlag(flag_r) : unsetFlag(flag_r) ); }
+ Flags & setFlag( Flags flag_r, bool newval_r ) { return( newval_r ? setFlag(flag_r) : unsetFlag(flag_r) ); }
+ Flags & setFlag( Enum flag_r, bool newval_r ) { return( newval_r ? setFlag(flag_r) : unsetFlag(flag_r) ); }
- Flags & setFlag( Flags flag_r ) { _val |= flag_r; return *this; }
- Flags & setFlag( Enum flag_r ) { _val |= flag_r; return *this; }
+ Flags & setFlag( Flags flag_r ) { _val |= integral(flag_r); return *this; }
+ Flags & setFlag( Enum flag_r ) { _val |= integral(flag_r); return *this; }
- Flags & unsetFlag( Flags flag_r ) { _val &= ~flag_r; return *this; }
- Flags & unsetFlag( Enum flag_r ) { _val &= ~flag_r; return *this; }
+ Flags & unsetFlag( Flags flag_r ) { _val &= ~integral(flag_r); return *this; }
+ Flags & unsetFlag( Enum flag_r ) { _val &= ~integral(flag_r); return *this; }
- bool testFlag( Flags flag_r ) const { return flag_r ? ( _val & flag_r ) == flag_r : !_val; }
- bool testFlag( Enum flag_r ) const { return flag_r ? ( _val & flag_r ) == flag_r : !_val; }
+ constexpr bool testFlag( Flags flag_r ) const { return testFlag( integral(flag_r) ); }
+ constexpr bool testFlag( Enum flag_r ) const { return testFlag( integral(flag_r) ); }
private:
+ constexpr bool testFlag( Integral flag ) { return flag ? ( _val & flag ) == flag : !_val; }
+
+ constexpr static Integral integral( Flags obj ) { return obj._val; }
+ constexpr static Integral integral( Enum obj ) { return static_cast<Integral>(obj); }
+
Integral _val;
};
///////////////////////////////////////////////////////////////////
return ret;
}
- template<typename Enum>
- inline std::ostream & operator<<( std::ostream & str, const Flags<Enum> & obj )
+ template<typename _Enum>
+ inline std::ostream & operator<<( std::ostream & str, const Flags<_Enum> & obj )
{ return str << str::hexstring(obj); }
+ template<typename _Enum>
+ inline std::ostream & operator<<( std::ostream & str, const typename Flags<_Enum>::Enum & obj )
+ { return str << Flags<_Enum>(obj); }
+
/** \relates Flags */
#define ZYPP_DECLARE_FLAGS(Name,Enum) typedef zypp::base::Flags<Enum> Name
/** \relates Flags */
#define ZYPP_DECLARE_OPERATORS_FOR_FLAGS(Name) \
+inline constexpr bool operator==( Name::Enum lhs, Name rhs ) { return( rhs == lhs ); } \
+inline constexpr bool operator!=(Name:: Enum lhs, Name rhs ) { return( rhs != lhs ); } \
inline constexpr Name operator&( Name::Enum lhs, Name::Enum rhs ) { return Name( lhs ) & rhs; } \
inline constexpr Name operator&( Name::Enum lhs, Name rhs ) { return rhs & lhs; } \
inline constexpr Name operator|( Name::Enum lhs, Name::Enum rhs ) { return Name( lhs ) | rhs; } \
--- /dev/null
+/*---------------------------------------------------------------------\
+| ____ _ __ __ ___ |
+| |__ / \ / / . \ . \ |
+| / / \ V /| _/ _/ |
+| / /__ | | | | | | |
+| /_____||_| |_| |_| |
+| |
+\---------------------------------------------------------------------*/
+/** \file zypp/base/Hash.h
+ *
+*/
+#ifndef ZYPP_BASE_HASH_H
+#define ZYPP_BASE_HASH_H
+
+#include <iosfwd>
+#include <unordered_set>
+#include <unordered_map>
+
+/** Define hash function for id based classes.
+ * Class has to provide a method \c id() retuning a unique number.
+ * \code
+ * // in global namespace define:
+ * ZYPP_DEFINE_ID_HASHABLE( ::zypp::sat::Solvable )
+ * \endcode
+ */
+#define ZYPP_DEFINE_ID_HASHABLE(C) \
+namespace std { \
+ template<class _Tp> struct hash; \
+ template<> struct hash<C> \
+ { \
+ size_t operator()( const C & __s ) const \
+ { return __s.id(); } \
+ }; \
+}
+
+///////////////////////////////////////////////////////////////////
+namespace std
+{
+ /** clone function for RW_pointer */
+ template<class _D>
+ inline unordered_set<_D> * rwcowClone( const std::unordered_set<_D> * rhs )
+ { return new std::unordered_set<_D>( *rhs ); }
+
+ /** clone function for RW_pointer */
+ template<class _K, class _V>
+ inline std::unordered_map<_K,_V> * rwcowClone( const std::unordered_map<_K,_V> * rhs )
+ { return new std::unordered_map<_K,_V>( *rhs ); }
+} // namespace std
+///////////////////////////////////////////////////////////////////
+#endif // ZYPP_BASE_HASH_H
#include <set>
#include <map>
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/base/Logger.h"
#include "zypp/base/Iterator.h"
#include "zypp/APIConfig.h"
{ return dumpRange( str, obj.begin(), obj.end() ); }
template<class _Tp>
- std::ostream & operator<<( std::ostream & str, const std::tr1::unordered_set<_Tp> & obj )
+ std::ostream & operator<<( std::ostream & str, const std::unordered_set<_Tp> & obj )
{ return dumpRange( str, obj.begin(), obj.end() ); }
template<class _Tp>
{ return str << dumpMap( obj ); }
template<class _Key, class _Tp>
- std::ostream & operator<<( std::ostream & str, const std::tr1::unordered_map<_Key, _Tp> & obj )
+ std::ostream & operator<<( std::ostream & str, const std::unordered_map<_Key, _Tp> & obj )
{ return str << dumpMap( obj ); }
template<class _Key, class _Tp>
{
///////////////////////////////////////////////////////////////////
- /// \class NamedValue<_Tp>
+ /// \class NamedValue
/// \brief Simple value<>name mapping supporting aliases.
/// \code
/// enum Commands {
namespace base
{
///////////////////////////////////////////////////////////////////
- /// \class SetRelationMixin<Derived>
+ /// \class SetRelationMixin
/// \brief Provide set relation methods based on Derived::setRelationMixinCompare
/// A class using this mixin must provide:
/// \code
--- /dev/null
+/*---------------------------------------------------------------------\
+| ____ _ __ __ ___ |
+| |__ / \ / / . \ . \ |
+| / / \ V /| _/ _/ |
+| / /__ | | | | | | |
+| /_____||_| |_| |_| |
+| |
+\---------------------------------------------------------------------*/
+/** \file zypp/base/SetTracker.h
+ */
+#ifndef ZYPP_BASE_SETTRACKER_H
+#define ZYPP_BASE_SETTRACKER_H
+
+#include <iosfwd>
+#include <utility>
+#include <algorithm>
+
+///////////////////////////////////////////////////////////////////
+namespace zypp
+{
+ ///////////////////////////////////////////////////////////////////
+ namespace base
+ {
+ ///////////////////////////////////////////////////////////////////
+ /// \class SetTracker
+ /// \brief Track added/removed set items based on an initial set.
+ ///
+ /// The class maintains the \ref current set of items and also records
+ /// the changes compared to the initial set (\ref added and \ref removed
+ /// items) if you use the tracking API.
+ ///
+ /// It is also possible to directly manipulate the three sets.
+ ///
+ /// \note The tracking API expects the template arg to have set semantic.
+ ///////////////////////////////////////////////////////////////////
+ template <class _Set>
+ struct SetTracker
+ {
+ typedef _Set set_type;
+ typedef typename _Set::key_type key_type;
+ typedef typename _Set::value_type value_type;
+
+ /** Default Ctor: empty set */
+ SetTracker()
+ {}
+
+ /** Ctor taking an initial set */
+ SetTracker( set_type initial_r )
+ : _current( std::move(initial_r) )
+ {}
+
+ /// \name Tracking API
+ //@{
+ /** (Re-)Start tracking the current set (discards previously tracked changes).
+ * \return \c False (set did not change)
+ */
+ bool setInitial()
+ { _added.clear(); _removed.clear(); return false; }
+
+ /** Start tracking a new set (discards previously tracked changes).
+ * \return Whether the set did change (new!=current)
+ */
+ bool setInitial( set_type new_r )
+ {
+ setInitial();
+ bool changed = ( new_r != _current );
+ if ( changed )
+ {
+ _current = std::move(new_r);
+ }
+ return changed;
+ }
+
+
+ /** Set a \a new_r set and track changes.
+ * \return Whether the set has changed
+ */
+ bool set( set_type new_r )
+ {
+ bool changed = ( new_r != _current );
+ if ( changed )
+ {
+ setInitial(); // clear added/removed
+ if ( new_r.empty() )
+ {
+ _removed.swap( _current );
+ }
+ else if ( _current.empty() )
+ {
+ _added.swap( _current );
+ }
+ else
+ {
+ setDifference( new_r, _current, _added );
+ setDifference( _current, new_r, _removed );
+ _current = std::move(new_r);
+ }
+ }
+ return changed;
+ }
+
+ /** Add an element to the set and track changes.
+ * \return Whether the set has changed
+ */
+ bool add( const value_type & val_r )
+ {
+ bool done = _current.insert( val_r ).second;
+ if ( done )
+ {
+ _added.insert( val_r );
+ _removed.erase( val_r );
+ }
+ return done;
+ }
+
+ /** Remove an element from the set and track changes.
+ * \return Whether the set has changed
+ */
+ bool remove( const value_type & val_r )
+ {
+ bool done = _current.erase( val_r );
+ if ( done )
+ {
+ _added.erase( val_r );
+ _removed.insert( val_r );
+ }
+ return done;
+ }
+ //@}
+
+ /// \name Query and retrieval
+ //@{
+ /** Whether \a val_r is in the set. */
+ bool contains( const key_type & key_r ) const { return find( _current, key_r ); }
+
+ /** Whether \a val_r is tracked as added. */
+ bool wasAdded( const key_type & key_r ) const { return find( _added, key_r ); }
+
+ /** Whether \a val_r is tracked as removed. */
+ bool wasRemoved( const key_type & key_r ) const { return find( _removed, key_r ); }
+
+
+ /** Return the current set. */
+ const set_type & current() const { return _current; }
+
+ /** Return the set of added items. */
+ const set_type & added() const { return _added; }
+
+ /** Return the set of removed items. */
+ const set_type & removed() const { return _removed; }
+ //@}
+
+ /// \name Direct manipulation
+ //@{
+ /** Return the current set. */
+ set_type & current() { return _current; }
+
+ /** Return the set of added items. */
+ set_type & added() { return _added; }
+
+ /** Return the set of removed items. */
+ set_type & removed() { return _removed; }
+ //@}
+
+ private:
+ static bool find( const set_type & set_r, const key_type & key_r )
+ { return set_r.find( key_r ) != set_r.end(); }
+
+ template <class _ORDERED_SET, typename enable_if = typename _ORDERED_SET::key_compare>
+ static void setDifference( const _ORDERED_SET & lhs, const _ORDERED_SET & rhs, _ORDERED_SET & result_r )
+ {
+ // std::set_difference requires ordered sets!
+ std::set_difference( lhs.begin(), lhs.end(), rhs.begin(), rhs.end(),
+ std::inserter( result_r, result_r.end() ),
+ typename _ORDERED_SET::key_compare() );
+ }
+
+ template <class _UNORDERED_SET, typename enable_if = typename _UNORDERED_SET::hasher, typename = void>
+ static void setDifference( const _UNORDERED_SET & lhs, const _UNORDERED_SET & rhs, _UNORDERED_SET & result_r )
+ {
+ // std::set_difference requires ordered sets!
+ for ( const auto & l : lhs )
+ { if ( rhs.find( l ) == rhs.end() ) result_r.insert( l ); }
+ }
+
+ private:
+ set_type _current;
+ set_type _added;
+ set_type _removed;
+ };
+
+ /** \relates SetTracker Stream output */
+ template <class _Set>
+ std::ostream & operator<<( std::ostream & str, const SetTracker<_Set> & obj )
+ { return str << "set(" << obj.current().size() << "|+" << obj.added().size() << "|-" << obj.removed().size() << ')'; }
+
+ } // namespace base
+ ///////////////////////////////////////////////////////////////////
+} // namespace zypp
+///////////////////////////////////////////////////////////////////
+#endif // ZYPP_BASE_SETTRACKER_H
+++ /dev/null
-/*---------------------------------------------------------------------\
-| ____ _ __ __ ___ |
-| |__ / \ / / . \ . \ |
-| / / \ V /| _/ _/ |
-| / /__ | | | | | | |
-| /_____||_| |_| |_| |
-| |
-\---------------------------------------------------------------------*/
-/** \file zypp/base/Tr1hash.h
- *
-*/
-#ifndef ZYPP_BASE_TR1HASH_H
-#define ZYPP_BASE_TR1HASH_H
-
-#include <iosfwd>
-#include <tr1/unordered_set>
-#include <tr1/unordered_map>
-
-/** Define hash function for id based classes.
- * Class has to provide a method \c id() retuning a unique number.
- * \code
- * // in global namespace define:
- * ZYPP_DEFINE_ID_HASHABLE( ::zypp::sat::Sovable )
- * \endcode
- */
-#define ZYPP_DEFINE_ID_HASHABLE(C) \
-namespace std { namespace tr1 { \
- template<class _Tp> struct hash; \
- template<> struct hash<C> \
- { \
- size_t operator()( const C & __s ) const \
- { return __s.id(); } \
- }; \
-}}
-
-///////////////////////////////////////////////////////////////////
-namespace std
-{ /////////////////////////////////////////////////////////////////
- ///////////////////////////////////////////////////////////////////
- namespace tr1
- { /////////////////////////////////////////////////////////////////
-
- /** clone function for RW_pointer */
- template<class _D>
- inline unordered_set<_D> * rwcowClone( const std::tr1::unordered_set<_D> * rhs )
- { return new std::tr1::unordered_set<_D>( *rhs ); }
-
- /** clone function for RW_pointer */
- template<class _K, class _V>
- inline std::tr1::unordered_map<_K,_V> * rwcowClone( const std::tr1::unordered_map<_K,_V> * rhs )
- { return new std::tr1::unordered_map<_K,_V>( *rhs ); }
-
- /////////////////////////////////////////////////////////////////
- } // namespace tr1
- ///////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////
-} // namespace std
-///////////////////////////////////////////////////////////////////
-#endif // ZYPP_BASE_TR1HASH_H
namespace base
{
///////////////////////////////////////////////////////////////////
- /// \class ValueTransform<_Tp,_UnaryFunction>
+ /// \class ValueTransform
/// \brief Helper managing raw values with transformed representation
///
- /// This helper enforces to explicitly state wheter you are using
+ /// This helper enforces to explicitly state whether you are using
/// the raw or the variable replaced value. Usually you set \c raw
- /// and get \c transformed (uness writing \c raw to some config file).
+ /// and get \c transformed (unless writing \c raw to some config file).
///
/// Used e.g. vor variable replaced config strings.
///////////////////////////////////////////////////////////////////
};
///////////////////////////////////////////////////////////////////
- /// \class ContainerTransform<_Container,_UnaryFunction>
+ /// \class ContainerTransform
/// \brief Helper managing a container of raw values with transformed representation
///
/// This helper enforces to explicitly state wheter you are using
#include "zypp/base/PtrTypes.h"
#include "zypp/base/Function.h"
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/base/String.h"
#include "zypp/base/DefaultIntegral.h"
}
private:
- std::tr1::unordered_map<std::string, std::vector<AssignerRef> > _attr;
+ std::unordered_map<std::string, std::vector<AssignerRef> > _attr;
std::vector<AssignerRef> _text;
function<void ( const Node & )> _pre;
function<void ( const Node & )> _post;
// Now diff to the pool collecting names only.
// Thus added and removed locks are not necessarily
// disjoint. Added locks win.
- typedef std::tr1::unordered_set<IdString> IdentSet;
+ typedef std::unordered_set<IdString> IdentSet;
IdentSet addedLocks;
IdentSet removedLocks;
for_( it, begin(), end() )
#include <vector>
#include "zypp/base/Iterator.h"
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/PoolItem.h"
#include "zypp/pool/ByIdent.h"
typedef ItemContainerT::size_type size_type;
/** ident index */
- typedef std::tr1::unordered_multimap<sat::detail::IdType, PoolItem>
+ typedef std::unordered_multimap<sat::detail::IdType, PoolItem>
Id2ItemT;
typedef P_Select2nd<Id2ItemT::value_type> Id2ItemValueSelector;
typedef transform_iterator<Id2ItemValueSelector, Id2ItemT::const_iterator>
// check whether to download more package translations:
{
auto fnc_checkTransaltions( [&]( const Locale & locale_r ) {
- for ( Locale toGet( locale_r ); toGet != Locale::noCode; toGet = toGet.fallback() )
+ for ( Locale toGet( locale_r ); toGet; toGet = toGet.fallback() )
{
auto it( availablePackageTranslations.find( toGet.code() ) );
if ( it != availablePackageTranslations.end() )
bool Pool::isRequestedLocale( const Locale & locale_r ) const
{ return myPool().isRequestedLocale( locale_r ); }
+ void Pool::initRequestedLocales( const LocaleSet & locales_r ) { myPool().initRequestedLocales( locales_r ); }
+ const LocaleSet & Pool::getAddedRequestedLocales() const { return myPool().getAddedRequestedLocales(); }
+ const LocaleSet & Pool::getRemovedRequestedLocales() const { return myPool().getRemovedRequestedLocales(); }
+
const LocaleSet & Pool::getAvailableLocales() const
{ return myPool().getAvailableLocales(); }
/** Whether this \ref Locale is in the set of requested locales. */
bool isRequestedLocale( const Locale & locale_r ) const;
+
+ /** Start tracking changes based on this \a locales_r. */
+ void initRequestedLocales( const LocaleSet & locales_r );
+
+ /** Added since last initRequestedLocales. */
+ const LocaleSet & getAddedRequestedLocales() const;
+
+ /** Removed since last initRequestedLocales.*/
+ const LocaleSet & getRemovedRequestedLocales() const;
+
+
/** Get the set of available locales.
* This is computed from the package data so it actually
* represents all locales packages claim to support.
#include "zypp/base/PtrTypes.h"
#include "zypp/base/Iterator.h"
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/sat/Solvable.h"
{
bool operator()( const Solvable & solv_r ) const;
- typedef std::tr1::unordered_set<unsigned> Uset;
+ typedef std::unordered_set<unsigned> Uset;
UnifyByIdent()
: _uset( new Uset )
{}
{
NO_SOLVABLE_RETURN( std::string() );
const char * s = 0;
- if ( lang_r == Locale::noCode )
+ if ( !lang_r )
{
s = ::solvable_lookup_str_poollang( _solvable, attr.id() );
}
else
{
- for ( Locale l( lang_r ); l != Locale::noCode; l = l.fallback() )
- if ( (s = ::solvable_lookup_str_lang( _solvable, attr.id(), l.code().c_str(), 0 )) )
+ for ( Locale l( lang_r ); l; l = l.fallback() )
+ if ( (s = ::solvable_lookup_str_lang( _solvable, attr.id(), l.c_str(), 0 )) )
return s;
// here: no matching locale, so use default
s = ::solvable_lookup_str_lang( _solvable, attr.id(), 0, 0 );
#include <iosfwd>
#include "zypp/base/PtrTypes.h"
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/sat/Solvable.h"
#include "zypp/sat/SolvIterMixin.h"
//
/** Solvable set wrapper to allow adding additioanal convenience iterators.
*/
- class SolvableSet : public SolvIterMixin<SolvableSet,std::tr1::unordered_set<Solvable>::const_iterator>
+ class SolvableSet : public SolvIterMixin<SolvableSet,std::unordered_set<Solvable>::const_iterator>
{
friend std::ostream & operator<<( std::ostream & str, const SolvableSet & obj );
public:
- typedef std::tr1::unordered_set<Solvable> Container;
+ typedef std::unordered_set<Solvable> Container;
typedef Container::value_type value_type;
typedef Container::size_type size_type;
typedef Solvable_iterator const_iterator; // from SolvIterMixin
#include "zypp/base/SerialNumber.h"
#include "zypp/base/DefaultIntegral.h"
#include "zypp/base/NonCopyable.h"
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/sat/detail/PoolImpl.h"
#include "zypp/sat/Transaction.h"
friend std::ostream & operator<<( std::ostream & str, const Impl & obj );
public:
- typedef std::tr1::unordered_set<detail::IdType> set_type;
- typedef std::tr1::unordered_map<detail::IdType,detail::IdType> map_type;
+ typedef std::unordered_set<detail::IdType> set_type;
+ typedef std::unordered_map<detail::IdType,detail::IdType> map_type;
struct PostMortem
{
Edition _edition;
Arch _arch;
};
- typedef std::tr1::unordered_map<detail::IdType,PostMortem> pmmap_type;
+ typedef std::unordered_map<detail::IdType,PostMortem> pmmap_type;
public:
Impl()
#include <iostream>
#include "zypp/base/LogTools.h"
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/sat/WhatObsoletes.h"
#include "zypp/sat/detail/PoolImpl.h"
#include "zypp/PoolItem.h"
namespace
{ /////////////////////////////////////////////////////////////////
- typedef std::tr1::unordered_set<detail::IdType> set_type;
+ typedef std::unordered_set<detail::IdType> set_type;
typedef std::vector<sat::detail::IdType> vector_type;
/////////////////////////////////////////////////////////////////
: _offset( offset_r ), _private( 0 )
{}
- Impl( const std::tr1::unordered_set<detail::IdType> & ids_r )
+ Impl( const std::unordered_set<detail::IdType> & ids_r )
: _offset( 0 ), _private( 0 )
{
// use private data to store the result (incl. trailing NULL)
/** WhatProvides ctor helper collecting providers from Capabilies. */
template <class Iterator>
- void collectProviders( Iterator begin_r, Iterator end_r, std::tr1::unordered_set<detail::IdType> & collect_r )
+ void collectProviders( Iterator begin_r, Iterator end_r, std::unordered_set<detail::IdType> & collect_r )
{
for_( it, begin_r, end_r )
{
WhatProvides::WhatProvides( Capabilities caps_r )
{
- std::tr1::unordered_set<detail::IdType> ids;
+ std::unordered_set<detail::IdType> ids;
collectProviders( caps_r.begin(), caps_r.end(), ids );
if ( ! ids.empty() )
{
WhatProvides::WhatProvides( const CapabilitySet & caps_r )
{
- std::tr1::unordered_set<detail::IdType> ids;
+ std::unordered_set<detail::IdType> ids;
collectProviders( caps_r.begin(), caps_r.end(), ids );
if ( ! ids.empty() )
{
BOOST_MPL_ASSERT_RELATION( CapDetail::CAP_NAMESPACE, ==, REL_NAMESPACE );
BOOST_MPL_ASSERT_RELATION( CapDetail::CAP_ARCH, ==, REL_ARCH );
- /////////////////////////////////////////////////////////////////
+ BOOST_MPL_ASSERT_RELATION( namespaceModalias, ==, NAMESPACE_MODALIAS );
+ BOOST_MPL_ASSERT_RELATION( namespaceLanguage, ==, NAMESPACE_LANGUAGE );
+ BOOST_MPL_ASSERT_RELATION( namespaceFilesystem, ==, NAMESPACE_FILESYSTEM );
+
+ /////////////////////////////////////////////////////////////////
const std::string & PoolImpl::systemRepoAlias()
{
{
case NAMESPACE_LANGUAGE:
{
- static IdString en( "en" );
- const std::tr1::unordered_set<IdString> & locale2Solver( reinterpret_cast<PoolImpl*>(data)->_locale2Solver );
- if ( locale2Solver.empty() )
- {
- return rhs == en.id() ? RET_systemProperty : RET_unsupported;
- }
- return locale2Solver.find( IdString(rhs) ) != locale2Solver.end() ? RET_systemProperty : RET_unsupported;
+ const TrackedLocaleIds & localeIds( reinterpret_cast<PoolImpl*>(data)->trackedLocaleIds() );
+ return localeIds.contains( IdString(rhs) ) ? RET_systemProperty : RET_unsupported;
}
break;
_availableLocalesPtr.reset(); // available locales may change
_multiversionListPtr.reset(); // re-evaluate ZConfig::multiversionSpec.
- // invaldate dependency/namespace related indices:
- depSetDirty();
+ depSetDirty(); // invaldate dependency/namespace related indices
+ }
+
+ void PoolImpl::localeSetDirty( const char * a1, const char * a2, const char * a3 )
+ {
+ if ( a1 )
+ {
+ if ( a3 ) MIL << a1 << " " << a2 << " " << a3 << endl;
+ else if ( a2 ) MIL << a1 << " " << a2 << endl;
+ else MIL << a1 << endl;
+ }
+ _trackedLocaleIdsPtr.reset(); // requested locales changed
+ depSetDirty(); // invaldate dependency/namespace related indices
}
void PoolImpl::depSetDirty( const char * a1, const char * a2, const char * a3 )
::pool_freewhatprovides( _pool );
}
+
void PoolImpl::prepare() const
{
if ( _watcher.remember( _serial ) )
///////////////////////////////////////////////////////////////////
- // need on demand and id based Locale
- void _locale_hack( const LocaleSet & locales_r,
- std::tr1::unordered_set<IdString> & locale2Solver )
- {
- std::tr1::unordered_set<IdString>( 2*locales_r.size() ).swap( locale2Solver );
- for_( it, locales_r.begin(),locales_r.end() )
- {
- for ( Locale l( *it ); l != Locale::noCode; l = l.fallback() )
- locale2Solver.insert( IdString( l.code() ) );
- }
- MIL << "New Solver Locales: " << locale2Solver << endl;
- }
-
void PoolImpl::setTextLocale( const Locale & locale_r )
{
std::vector<std::string> fallbacklist;
- for ( Locale l( locale_r ); l != Locale::noCode; l = l.fallback() )
+ for ( Locale l( locale_r ); l; l = l.fallback() )
{
fallbacklist.push_back( l.code() );
}
::pool_set_languages( _pool, &fallbacklist_cstr.front(), fallbacklist_cstr.size() );
}
+ void PoolImpl::initRequestedLocales( const LocaleSet & locales_r )
+ {
+ if ( _requestedLocalesTracker.setInitial( locales_r ) )
+ {
+ localeSetDirty( "initRequestedLocales" );
+ MIL << "Init RequestedLocales: " << _requestedLocalesTracker << " =" << locales_r << endl;
+ }
+ }
+
void PoolImpl::setRequestedLocales( const LocaleSet & locales_r )
{
- depSetDirty( "setRequestedLocales" );
- _requestedLocales = locales_r;
- MIL << "New RequestedLocales: " << locales_r << endl;
- _locale_hack( _requestedLocales, _locale2Solver );
+ if ( _requestedLocalesTracker.set( locales_r ) )
+ {
+ localeSetDirty( "setRequestedLocales" );
+ MIL << "New RequestedLocales: " << _requestedLocalesTracker << " =" << locales_r << endl;
+ }
}
bool PoolImpl::addRequestedLocale( const Locale & locale_r )
{
- if ( _requestedLocales.insert( locale_r ).second )
+ bool done = _requestedLocalesTracker.add( locale_r );
+ if ( done )
{
- depSetDirty( "addRequestedLocale", locale_r.code().c_str() );
- _locale_hack( _requestedLocales, _locale2Solver );
- return true;
+ localeSetDirty( "addRequestedLocale", locale_r.code().c_str() );
+ MIL << "New RequestedLocales: " << _requestedLocalesTracker << " +" << locale_r << endl;
}
- return false;
+ return done;
}
bool PoolImpl::eraseRequestedLocale( const Locale & locale_r )
{
- if ( _requestedLocales.erase( locale_r ) )
+ bool done = _requestedLocalesTracker.remove( locale_r );
+ if ( done )
{
- depSetDirty( "addRequestedLocale", locale_r.code().c_str() );
- _locale_hack( _requestedLocales, _locale2Solver );
- return true;
+ localeSetDirty( "addRequestedLocale", locale_r.code().c_str() );
+ MIL << "New RequestedLocales: " << _requestedLocalesTracker << " -" << locale_r << endl;
}
- return false;
+ return done;
}
- static void _getLocaleDeps( Capability cap_r, std::tr1::unordered_set<sat::detail::IdType> & store_r )
+
+ const PoolImpl::TrackedLocaleIds & PoolImpl::trackedLocaleIds() const
+ {
+ if ( ! _trackedLocaleIdsPtr )
+ {
+ _trackedLocaleIdsPtr.reset( new TrackedLocaleIds );
+
+ const base::SetTracker<LocaleSet> & localesTracker( _requestedLocalesTracker );
+ TrackedLocaleIds & localeIds( *_trackedLocaleIdsPtr );
+
+ // Add current locales+fallback except for added ones
+ for ( Locale lang: localesTracker.current() )
+ {
+ if ( localesTracker.wasAdded( lang ) )
+ continue;
+ for ( ; lang; lang = lang.fallback() )
+ { localeIds.current().insert( IdString(lang) ); }
+ }
+
+ // Add added locales+fallback except they are already in current
+ for ( Locale lang: localesTracker.added() )
+ {
+ for ( ; lang && localeIds.current().insert( IdString(lang) ).second; lang = lang.fallback() )
+ { localeIds.added().insert( IdString(lang) ); }
+ }
+
+ // Add removed locales+fallback except they are still in current
+ for ( Locale lang: localesTracker.removed() )
+ {
+ for ( ; lang && ! localeIds.current().count( IdString(lang) ); lang = lang.fallback() )
+ { localeIds.removed().insert( IdString(lang) ); }
+ }
+
+ // Assert that TrackedLocaleIds::current is not empty.
+ // If, so fill in LanguageCode::enCode as last resort.
+ if ( localeIds.current().empty() )
+ { localeIds.current().insert( IdString(Locale::enCode) ); }
+ }
+ return *_trackedLocaleIdsPtr;
+ }
+
+
+ static void _getLocaleDeps( Capability cap_r, std::unordered_set<sat::detail::IdType> & store_r )
{
// Collect locales from any 'namespace:language(lang)' dependency
CapDetail detail( cap_r );
if ( !_availableLocalesPtr )
{
// Collect any 'namespace:language(ja)' dependencies
- std::tr1::unordered_set<sat::detail::IdType> tmp;
+ std::unordered_set<sat::detail::IdType> tmp;
Pool pool( Pool::instance() );
for_( it, pool.solvablesBegin(), pool.solvablesEnd() )
{
}
#include <iosfwd>
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/base/NonCopyable.h"
#include "zypp/base/SerialNumber.h"
+#include "zypp/base/SetTracker.h"
#include "zypp/sat/detail/PoolMember.h"
#include "zypp/sat/Queue.h"
#include "zypp/RepoInfo.h"
*/
void setDirty( const char * a1 = 0, const char * a2 = 0, const char * a3 = 0 );
+ /** Invalidate locale related housekeeping data.
+ */
+ void localeSetDirty( const char * a1 = 0, const char * a2 = 0, const char * a3 = 0 );
+
/** Invalidate housekeeping data (e.g. whatprovides) if dependencies changed.
*/
void depSetDirty( const char * a1 = 0, const char * a2 = 0, const char * a3 = 0 );
{ prepare(); return ::pool_whatprovides( _pool, cap_r.id() ); }
public:
- /** \name Requested locales. */
+ /// \name Requested locales.
+ /// The requested LocaleSets managed in _requestedLocalesTracker
+ /// are unexpanded; i.e. they contain just the pure user selection.
+ /// The resolver however uses expanded sets ('de_DE' will also
+ /// include its fallback locales 'de', (en); here in the namespace:
+ /// callback and in the Resolver itself).
//@{
+ /** */
void setTextLocale( const Locale & locale_r );
- void setRequestedLocales( const LocaleSet & locales_r );
- bool addRequestedLocale( const Locale & locale_r );
- bool eraseRequestedLocale( const Locale & locale_r );
+
+ /** Start tracking changes based on this \a locales_r.
+ * Usually called on TargetInit.
+ */
+ void initRequestedLocales( const LocaleSet & locales_r );
+
+ /** Added since last initRequestedLocales. */
+ const LocaleSet & getAddedRequestedLocales() const
+ { return _requestedLocalesTracker.added(); }
+
+ /** Removed since last initRequestedLocales. */
+ const LocaleSet & getRemovedRequestedLocales() const
+ { return _requestedLocalesTracker.removed(); }
+
+ /** Current set of requested Locales. */
const LocaleSet & getRequestedLocales() const
- { return _requestedLocales; }
+ { return _requestedLocalesTracker.current(); }
bool isRequestedLocale( const Locale & locale_r ) const
- {
- LocaleSet::const_iterator it( _requestedLocales.find( locale_r ) );
- return it != _requestedLocales.end();
- }
+ { return _requestedLocalesTracker.contains( locale_r ); }
+ /** User change (tracked). */
+ void setRequestedLocales( const LocaleSet & locales_r );
+ /** User change (tracked). */
+ bool addRequestedLocale( const Locale & locale_r );
+ /** User change (tracked). */
+ bool eraseRequestedLocale( const Locale & locale_r );
+
+ /** All Locales occurring in any repo. */
const LocaleSet & getAvailableLocales() const;
bool isAvailableLocale( const Locale & locale_r ) const
LocaleSet::const_iterator it( avl.find( locale_r ) );
return it != avl.end();
}
+
+ typedef base::SetTracker<IdStringSet> TrackedLocaleIds;
+
+ /** Expanded _requestedLocalesTracker for solver.*/
+ const TrackedLocaleIds & trackedLocaleIds() const;
//@}
public:
std::map<RepoIdType,RepoInfo> _repoinfos;
/** */
- LocaleSet _requestedLocales;
+ base::SetTracker<LocaleSet> _requestedLocalesTracker;
+ mutable scoped_ptr<TrackedLocaleIds> _trackedLocaleIdsPtr;
+
mutable scoped_ptr<LocaleSet> _availableLocalesPtr;
- mutable std::tr1::unordered_set<IdString> _locale2Solver;
/** */
void multiversionListInit() const;
#ifndef ZYPP_SAT_DETAIL_POOLMEMBER_H
#define ZYPP_SAT_DETAIL_POOLMEMBER_H
-#include "zypp/base/Tr1hash.h"
+#include "zypp/base/Hash.h"
#include "zypp/base/Iterator.h"
#include "zypp/base/String.h"
#include "zypp/base/Easy.h"
*/
static const IdType solvablePrereqMarker( 15 );
static const IdType solvableFileMarker ( 16 );
+
+ static const IdType namespaceModalias ( 18 );
+ static const IdType namespaceLanguage ( 20 );
+ static const IdType namespaceFilesystem ( 21 );
+
/** Test for internal ids satlib includes in dependencies. */
inline bool isDepMarkerId( IdType id_r )
{ return( id_r == solvablePrereqMarker || id_r == solvableFileMarker ); }
+++ /dev/null
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 4 -*- */
-/* Helper.cc
- *
- * Static helpers
- *
- * Copyright (C) 2000-2002 Ximian, Inc.
- * Copyright (C) 2005 SUSE Linux Products GmbH
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
- * 02111-1307, USA.
- */
-#include <sstream>
-
-#include "zypp/solver/detail/Helper.h"
-#include "zypp/Capabilities.h"
-#include "zypp/base/Logger.h"
-#include "zypp/base/String.h"
-#include "zypp/base/Gettext.h"
-#include "zypp/VendorAttr.h"
-#include "zypp/base/Algorithm.h"
-#include "zypp/ResPool.h"
-#include "zypp/ResFilters.h"
-#include "zypp/RepoInfo.h"
-
-using namespace std;
-
-/////////////////////////////////////////////////////////////////////////
-namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
- ///////////////////////////////////////////////////////////////////////
- namespace solver
- { /////////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////////
- namespace detail
- { ///////////////////////////////////////////////////////////////////
-
-ostream &
-operator<< (ostream & os, const PoolItemList & itemlist)
-{
- for (PoolItemList::const_iterator iter = itemlist.begin(); iter != itemlist.end(); ++iter) {
- if (iter != itemlist.begin())
- os << ", ";
- os << *iter;
- }
- return os;
-}
-
-
-class LookFor : public resfilter::PoolItemFilterFunctor
-{
- public:
- PoolItem item;
-
- bool operator()( PoolItem provider )
- {
- item = provider;
- return false; // stop here, we found it
- }
-};
-
-
-// just find installed item with same kind/name as item
-
-template<class _Iter>
-static PoolItem findInstalledByNameAndKind ( _Iter begin, _Iter end, const string & name, const Resolvable::Kind & kind)
-{
- LookFor info;
-
- invokeOnEach(begin, end,
- resfilter::ByInstalled (), // ByInstalled
- functor::functorRef<bool,PoolItem> (info) );
-
- _XDEBUG("Helper::findInstalledByNameAndKind (" << name << ", " << kind << ") => " << info.item);
- return info.item;
-
-}
-
-PoolItem Helper::findInstalledByNameAndKind (const ResPool & pool, const string & name, const Resolvable::Kind & kind)
-{ return detail::findInstalledByNameAndKind( pool.byIdentBegin( kind, name ), pool.byIdentEnd( kind, name ), name, kind ); }
-
-PoolItem Helper::findInstalledItem (const ResPool & pool, PoolItem item)
-{ return findInstalledByNameAndKind(pool, item->name(), item->kind() ); }
-
-PoolItem Helper::findInstalledItem( const std::vector<PoolItem> & pool, PoolItem item )
-{ return detail::findInstalledByNameAndKind( pool.begin(), pool.end(), item->name(), item->kind() ); }
-
-
-// just find uninstalled item with same kind/name as item
-
-PoolItem
-Helper::findUninstalledByNameAndKind (const ResPool & pool, const string & name, const Resolvable::Kind & kind)
-{
- LookFor info;
-
- invokeOnEach( pool.byIdentBegin( kind, name ),
- pool.byIdentEnd( kind, name ),
- resfilter::ByUninstalled(), // ByUninstalled
- functor::functorRef<bool,PoolItem> (info) );
-
- _XDEBUG("Helper::findUninstalledByNameAndKind (" << name << ", " << kind << ") => " << info.item);
- return info.item;
-}
-
-
-//----------------------------------------------------------------------------
-
-class LookForUpdate : public resfilter::PoolItemFilterFunctor
-{
- public:
- PoolItem uninstalled;
- PoolItem installed;
-
- bool operator()( PoolItem provider )
- {
- // is valid
- if ( ! provider.resolvable() )
- {
- WAR << "Warning: '" << provider << "' not valid" << endl;
- return true;
- }
-
- if ( installed.resolvable() )
- {
- if ( !VendorAttr::instance().equivalent( installed, provider ) )
- {
- MIL << "Discarding '" << provider << "' from vendor '"
- << provider->vendor() << "' different to uninstalled '"
- << installed->vendor() << "' vendor." << endl;
- return true;
- }
- }
-
- if ((!uninstalled // none yet
- || (uninstalled->edition().compare( provider->edition() ) < 0) // or a better edition
- || (uninstalled->arch().compare( provider->arch() ) < 0) ) // or a better architecture
- && !provider.status().isLocked() ) // is not locked
- {
- uninstalled = provider; // store
- }
- return true;
- }
-};
-
-
-// just find best (according to edition) uninstalled item with same kind/name as item
-// *DOES* check edition
-
-template<class _Iter>
-static PoolItem findUpdateItem( _Iter begin, _Iter end, PoolItem item )
-{
- LookForUpdate info;
- info.installed = item;
-
- invokeOnEach( begin, end,
- functor::chain (resfilter::ByUninstalled (), // ByUninstalled
- resfilter::byEdition<CompareByGT<Edition> >( item->edition() )), // only look at better editions
- functor::functorRef<bool,PoolItem> (info) );
-
- _XDEBUG("Helper::findUpdateItem(" << item << ") => " << info.uninstalled);
- return info.uninstalled;
-}
-
-PoolItem Helper::findUpdateItem (const ResPool & pool, PoolItem item)
-{ return detail::findUpdateItem( pool.byIdentBegin( item ), pool.byIdentEnd( item ), item ); }
-
-PoolItem Helper::findUpdateItem (const std::vector<PoolItem> & pool, PoolItem item)
-{ return detail::findUpdateItem( pool.begin(), pool.end(), item ); }
-
-
-//----------------------------------------------------------------------------
-
-class LookForReinstall : public resfilter::PoolItemFilterFunctor
-{
- public:
- PoolItem uninstalled;
-
- bool operator()( PoolItem provider )
- {
- if (provider.status().isLocked()) {
- return true; // search next
- } else {
- uninstalled = provider;
- return false; // stop here, we found it
- }
- }
-};
-
-
-PoolItem
-Helper::findReinstallItem (const ResPool & pool, PoolItem item)
-{
- LookForReinstall info;
-
- invokeOnEach( pool.byIdentBegin( item ),
- pool.byIdentEnd( item ),
- functor::chain (resfilter::ByUninstalled (), // ByUninstalled
- resfilter::byEdition<CompareByEQ<Edition> >( item->edition() )),
- functor::functorRef<bool,PoolItem> (info) );
-
- _XDEBUG("Helper::findReinstallItem(" << item << ") => " << info.uninstalled);
- return info.uninstalled;
-}
-
-//----------------------------------------------------------------------------
-
-class CheckIfBest : public resfilter::PoolItemFilterFunctor
-{
- public:
- PoolItem _item;
- bool is_best;
-
- CheckIfBest( PoolItem item )
- : _item( item )
- , is_best( true ) // assume we already have the best
- {}
-
- // check if provider is better. If yes, end the search.
-
- bool operator()( PoolItem provider )
- {
- int archcmp = _item->arch().compare( provider->arch() );
- if (((archcmp < 0) // provider has a better architecture
- || ((archcmp == 0)
- && (_item->edition().compare( provider->edition() ) < 0))) // or a better edition
- && !provider.status().isLocked()) // and is not locked
- {
- is_best = false;
- return false;
- }
- return true;
- }
-};
-
-
-// check if the given item is the best one of the pool
-
-bool
-Helper::isBestUninstalledItem (const ResPool & pool, PoolItem item)
-{
- CheckIfBest info( item );
-
- invokeOnEach( pool.byIdentBegin( item ),
- pool.byIdentEnd( item ),
- resfilter::ByUninstalled(), // ByUninstalled
- functor::functorRef<bool,PoolItem>( info ) );
-
- _XDEBUG("Helper::isBestUninstalledItem(" << item << ") => " << info.is_best);
- return info.is_best;
-}
-
-std::string
-Helper::itemToString (PoolItem item, bool shortVersion)
-{
- ostringstream os;
- if (!item) return "";
-
- if (item->kind() != ResKind::package)
- os << item->kind() << ':';
- os << item->name();
- if (!shortVersion) {
- os << '-' << item->edition();
- if (item->arch() != "") {
- os << '.' << item->arch();
- }
-
- string alias = item->repoInfo().alias();
- if (!alias.empty()
- && alias != "@System")
- {
- os << '[' << alias << ']';
- }
- }
- return os.str();
-}
-
-std::string
-Helper::capToString (const Capability & capability)
-{
- ostringstream os;
- os << capability.asString();
- return os.str();
-}
-
-
-///////////////////////////////////////////////////////////////////
- };// namespace detail
- /////////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////////
- };// namespace solver
- ///////////////////////////////////////////////////////////////////////
- ///////////////////////////////////////////////////////////////////////
-};// namespace zypp
-/////////////////////////////////////////////////////////////////////////
-
+++ /dev/null
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 4 -*- */
-/* Helper.h
- *
- * Static helpers
- *
- * Copyright (C) 2000-2002 Ximian, Inc.
- * Copyright (C) 2005 SUSE Linux Products GmbH
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
- * 02111-1307, USA.
- */
-
-#ifndef ZYPP_SOLVER_DETAIL_HELPER_H
-#define ZYPP_SOLVER_DETAIL_HELPER_H
-
-#include <iosfwd>
-
-#include "zypp/ResPool.h"
-#include "zypp/PoolItem.h"
-#include "zypp/Capabilities.h"
-#include "zypp/base/String.h"
-#include "zypp/solver/detail/Types.h"
-
-/////////////////////////////////////////////////////////////////////////
-namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
- ///////////////////////////////////////////////////////////////////////
- namespace solver
- { /////////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////////
- namespace detail
- { ///////////////////////////////////////////////////////////////////
-
-///////////////////////////////////////////////////////////////////
-//
-// CLASS NAME : Helper
-
-class Helper {
- public:
-
- // for name, find installed item which has same name
- // does *NOT* check edition
- // FIXME: should probably take provides/obsoletes into account for
- // renamed upgrades
- static PoolItem findInstalledByNameAndKind (const ResPool & pool, const std::string & name, const Resolvable::Kind & kind);
-
- // for name, find uninstalled item which has same name
- static PoolItem findUninstalledByNameAndKind (const ResPool & pool, const std::string & name, const Resolvable::Kind & kind);
-
- // for item, find installed item which has same name -> calls findInstalledByNameAndKind()
- // does *NOT* check edition
- // FIXME: should probably take provides/obsoletes into account for
- // renamed upgrades
- static PoolItem findInstalledItem (const ResPool & pool, PoolItem item);
- /** \overload Using ident cache entry. */
- static PoolItem findInstalledItem (const std::vector<PoolItem> & pool, PoolItem item);
-
- // for item, find uninstalled item which has same name and higher edition
- static PoolItem findUninstalledItem (const ResPool & pool, PoolItem item);
-
- // for item, find uninstalled item which has same name and equal edition
- static PoolItem findReinstallItem (const ResPool & pool, PoolItem item);
-
- static PoolItem findUpdateItem (const ResPool & pool, PoolItem item);
- /** \overload Using ident cache entry. */
- static PoolItem findUpdateItem (const std::vector<PoolItem> & pool, PoolItem item);
-
- // for item, check if this is the 'best' uninstalled (best arch, best version) item
- static bool isBestUninstalledItem (const ResPool & pool, PoolItem item);
-
- // Human readable item
- static std::string itemToString (PoolItem item, bool shortVersion=false);
- static std::string capToString (const Capability & capability);
-
- friend std::ostream& operator<<(std::ostream&, const PoolItemList & itemlist);
-
-};
-
-///////////////////////////////////////////////////////////////////
- };// namespace detail
- /////////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////////
- };// namespace solver
- ///////////////////////////////////////////////////////////////////////
- ///////////////////////////////////////////////////////////////////////
-};// namespace zypp
-/////////////////////////////////////////////////////////////////////////
-
-#endif // ZYPP_SOLVER_DETAIL_HELPER_H
--- /dev/null
+/*---------------------------------------------------------------------\
+| ____ _ __ __ ___ |
+| |__ / \ / / . \ . \ |
+| / / \ V /| _/ _/ |
+| / /__ | | | | | | |
+| /_____||_| |_| |_| |
+| |
+\---------------------------------------------------------------------*/
+/** \file zypp/solver/detail/ItemCapKind.h
+ *
+*/
+
+#ifndef ZYPP_SOLVER_DETAIL_ITEMCAPKIND_H
+#define ZYPP_SOLVER_DETAIL_ITEMCAPKIND_H
+#ifndef ZYPP_USE_RESOLVER_INTERNALS
+#error Do not directly include this file!
+#else
+
+///////////////////////////////////////////////////////////////////
+namespace zypp
+{
+ ///////////////////////////////////////////////////////////////////
+ namespace solver
+ {
+ ///////////////////////////////////////////////////////////////////
+ namespace detail
+ {
+ ///////////////////////////////////////////////////////////////////
+ /// \class ItemCapKind
+ ///////////////////////////////////////////////////////////////////
+ struct ItemCapKind
+ {
+ public:
+ ItemCapKind() : _pimpl( new Impl ) {}
+
+ ItemCapKind( PoolItem i, Capability c, Dep k, bool initial ) : _pimpl( new Impl( i, c, k, initial ) ) {}
+
+ /** Capability which has triggerd this selection */
+ Capability cap() const
+ { return _pimpl->_cap; }
+
+ /** Kind of that capability */
+ Dep capKind() const
+ { return _pimpl->_capKind; }
+
+ /** Item which has triggered this selection */
+ PoolItem item() const
+ { return _pimpl->_item; }
+
+ /** This item has triggered the installation (Not already fullfilled requierement only). */
+ bool initialInstallation() const
+ { return _pimpl->_initialInstallation; }
+
+ private:
+ struct Impl
+ {
+ Impl()
+ : _capKind( Dep::PROVIDES )
+ , _initialInstallation( false )
+ {}
+
+ Impl( PoolItem i, Capability c, Dep k, bool initial )
+ : _cap( c )
+ , _capKind( k )
+ , _item( i )
+ , _initialInstallation( initial )
+ {}
+
+ Capability _cap;
+ Dep _capKind;
+ PoolItem _item;
+ bool _initialInstallation;
+
+ private:
+ friend Impl * rwcowClone<Impl>( const Impl * rhs );
+ /** clone for RWCOW_pointer */
+ Impl * clone() const
+ { return new Impl( *this ); }
+ };
+ RWCOW_pointer<Impl> _pimpl;
+ };
+
+ typedef std::multimap<PoolItem,ItemCapKind> ItemCapKindMap;
+ typedef std::list<ItemCapKind> ItemCapKindList;
+
+ } // namespace detail
+ ///////////////////////////////////////////////////////////////////
+ } // namespace solver
+ ///////////////////////////////////////////////////////////////////
+} // namespace zypp
+///////////////////////////////////////////////////////////////////
+#endif // ZYPP_USE_RESOLVER_INTERNALS
+#endif // ZYPP_SOLVER_DETAIL_ITEMCAPKIND_H
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
* 02111-1307, USA.
*/
-
-#include <sstream>
-
-#include "zypp/base/String.h"
-#include "zypp/base/Gettext.h"
+#define ZYPP_USE_RESOLVER_INTERNALS
#include "zypp/solver/detail/ProblemSolutionCombi.h"
/////////////////////////////////////////////////////////////////////////
namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
+{
///////////////////////////////////////////////////////////////////////
namespace solver
- { /////////////////////////////////////////////////////////////////////
+ {
/////////////////////////////////////////////////////////////////////
namespace detail
- { ///////////////////////////////////////////////////////////////////
-
-IMPL_PTR_TYPE(ProblemSolutionCombi);
-
-//---------------------------------------------------------------------------
-
-ProblemSolutionCombi::ProblemSolutionCombi( ResolverProblem_Ptr parent)
- : ProblemSolution (parent, "", "")
- , actNumber(0)
-{
- _description = "";
- _details = "";
-}
-
-void ProblemSolutionCombi::addSingleAction( Capability capability, const TransactionKind action)
-{
- addAction (new TransactionSolutionAction(capability, action));
- actNumber++;
-}
-
-void ProblemSolutionCombi::addSingleAction( PoolItem item, const TransactionKind action)
-{
- addAction (new TransactionSolutionAction(item, action));
- actNumber++;
-}
+ {
+ ProblemSolutionCombi::ProblemSolutionCombi()
+ {}
-void ProblemSolutionCombi::addSingleAction( SolverQueueItem_Ptr item, const TransactionKind action)
-{
- addAction (new TransactionSolutionAction(item, action));
- actNumber++;
-}
+ void ProblemSolutionCombi::addSingleAction( Capability capability, TransactionKind action)
+ { addAction( new TransactionSolutionAction( capability, action ) ); }
-void ProblemSolutionCombi::addDescription( const std::string description)
-{
- if ( _description.size() == 0
- && _details.size() == 0) {
- // first entry
- _description = description;
- } else {
- if ( _description.size() > 0
- && _details.size() == 0) {
- // second entry
- _details = _description;
- _description = _("Following actions will be done:");
- }
- // all other
- _details += "\n";
- _details += description;
- }
-}
+ void ProblemSolutionCombi::addSingleAction( PoolItem item, TransactionKind action )
+ { addAction( new TransactionSolutionAction( item, action ) ); }
-void ProblemSolutionCombi::addFrontDescription( const std::string & description )
-{
- if ( _description.size() == 0
- && _details.size() == 0) {
- // first entry
- _description = description;
- } else {
- if ( _description.size() > 0
- && _details.size() == 0) {
- // second entry
- _details = _description;
- _description = _("Following actions will be done:");
- }
- // all other
- std::string tmp( _details );
- _details = description;
- _details += "\n";
- _details += tmp;
- }
-}
+ void ProblemSolutionCombi::addSingleAction( SolverQueueItem_Ptr item, TransactionKind action )
+ { addAction( new TransactionSolutionAction( item, action ) ); }
- ///////////////////////////////////////////////////////////////////
- };// namespace detail
+ } // namespace detail
/////////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////////
- };// namespace solver
- ///////////////////////////////////////////////////////////////////////
+ } // namespace solver
///////////////////////////////////////////////////////////////////////
-};// namespace zypp
+} // namespace zypp
/////////////////////////////////////////////////////////////////////////
#ifndef ZYPP_SOLVER_DETAIL_PROBLEMSOLUTIONINSTALL_H
#define ZYPP_SOLVER_DETAIL_PROBLEMSOLUTIONINSTALL_H
+#ifndef ZYPP_USE_RESOLVER_INTERNALS
+#error Do not directly include this file!
+#else
#include <string>
+
#include "zypp/ProblemSolution.h"
-#include "zypp/solver/detail/Types.h"
-#include "zypp/solver/detail/SolverQueueItem.h"
+#include "zypp/solver/detail/SolutionAction.h" // TransactionKind
/////////////////////////////////////////////////////////////////////////
namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
+{
///////////////////////////////////////////////////////////////////////
namespace solver
- { /////////////////////////////////////////////////////////////////////
+ {
/////////////////////////////////////////////////////////////////////
namespace detail
- { ///////////////////////////////////////////////////////////////////
+ {
+ /////////////////////////////////////////////////////////////////////////
+ /// \class ProblemSolutionCombi
+ /// \brief Class representing one possible solution to one problem found during resolving.
+ ///
+ /// This problem solution is a combination of different actions,
+ /// e.G. install, delete, keep different resolvables.
+ /////////////////////////////////////////////////////////////////////////
+ class ProblemSolutionCombi : public ProblemSolution
+ {
+ public:
+ /** Constructor. */
+ ProblemSolutionCombi();
/**
- * Class representing one possible solution to one problem found during resolving
- * This problem solution is a combination of different actions.
- * e.G. install, delete, keep different resolvables.
- *
- **/
- class ProblemSolutionCombi : public ProblemSolution
- {
- protected:
- int actNumber; // number of actions
- public:
-
- /**
- * Constructor.
- **/
- ProblemSolutionCombi( ResolverProblem_Ptr parent );
- /**
- * Add a single action of an item
- */
- void addSingleAction( PoolItem item, const TransactionKind action);
+ * Add a single action of an item
+ */
+ void addSingleAction( PoolItem item, TransactionKind action );
- /**
- * Add a single action of a capability
- */
- void addSingleAction( Capability capability, const TransactionKind action);
+ /**
+ * Add a single action of a capability
+ */
+ void addSingleAction( Capability capability, TransactionKind action );
- /**
- * Add a single action of a SolverQueueItem
- */
- void addSingleAction( SolverQueueItem_Ptr item, const TransactionKind action);
+ /**
+ * Add a single action of a SolverQueueItem
+ */
+ void addSingleAction( SolverQueueItem_Ptr item, TransactionKind action );
- /**
- * returns the number of actions
- */
- int actionCount() { return actNumber;}
+ /**
+ * returns the number of actions
+ */
+ size_t actionCount()
+ { return actions().size(); }
- /**
- * Set description text (append)
- */
- void addDescription( const std::string description);
+ /**
+ * Set description text (append)
+ */
+ void addDescription( std::string description )
+ { pushDescriptionDetail( std::move(description) ); }
- /**
- * Set description text (prepend)
- */
- void addFrontDescription( const std::string & description );
- };
+ /**
+ * Set description text (prepend)
+ */
+ void addFrontDescription( std::string description )
+ { pushDescriptionDetail( std::move(description), /*front*/true ); }
+ };
- ///////////////////////////////////////////////////////////////////
- };// namespace detail
- /////////////////////////////////////////////////////////////////////
+ } // namespace detail
/////////////////////////////////////////////////////////////////////
- };// namespace solver
+ } // namespace solver
///////////////////////////////////////////////////////////////////////
- ///////////////////////////////////////////////////////////////////////
-};// namespace zypp
+} // namespace zypp
/////////////////////////////////////////////////////////////////////////
-
+#endif // ZYPP_USE_RESOLVER_INTERNALS
#endif // ZYPP_SOLVER_DETAIL_PROBLEMSOLUTIONAINSTALL_H
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
* 02111-1307, USA.
*/
+#define ZYPP_USE_RESOLVER_INTERNALS
#include "zypp/base/String.h"
#include "zypp/base/Gettext.h"
-#include "zypp/base/Logger.h"
#include "zypp/solver/detail/ProblemSolutionIgnore.h"
-#include "zypp/solver/detail/Helper.h"
-
-using namespace std;
+#include "zypp/solver/detail/SolutionAction.h"
/////////////////////////////////////////////////////////////////////////
namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
+{
///////////////////////////////////////////////////////////////////////
namespace solver
- { /////////////////////////////////////////////////////////////////////
+ {
/////////////////////////////////////////////////////////////////////
namespace detail
- { ///////////////////////////////////////////////////////////////////
-
-IMPL_PTR_TYPE(ProblemSolutionIgnore);
-
-//---------------------------------------------------------------------------
-
-ProblemSolutionIgnore::ProblemSolutionIgnore( ResolverProblem_Ptr parent,
- PoolItem item )
- : ProblemSolution (parent, "", "")
-{
- // TranslatorExplanation %s = name of package, patch, selection ...
- _description = str::form (_("break %s by ignoring some of its dependencies"), item.satSolvable().asString().c_str() );
-
- addAction ( new InjectSolutionAction (item, WEAK));
-}
-
-ProblemSolutionIgnore::ProblemSolutionIgnore( ResolverProblem_Ptr parent,
- PoolItemList itemList )
- : ProblemSolution (parent, "", "")
-{
- _description = _("generally ignore of some dependecies");
- for (PoolItemList::const_iterator iter = itemList.begin();
- iter != itemList.end(); iter++) {
- addAction ( new InjectSolutionAction (*iter, WEAK));
- }
-}
-
- ///////////////////////////////////////////////////////////////////
- };// namespace detail
- /////////////////////////////////////////////////////////////////////
+ {
+ ProblemSolutionIgnore::ProblemSolutionIgnore( PoolItem item )
+ // TranslatorExplanation %s = name of package, patch, selection ...
+ : ProblemSolution( str::form(_("break %s by ignoring some of its dependencies"), item.satSolvable().asString().c_str() ) )
+ {
+ addAction( new InjectSolutionAction( item, WEAK ) );
+ }
+
+ ProblemSolutionIgnore::ProblemSolutionIgnore( PoolItemList itemList )
+ : ProblemSolution( _("generally ignore of some dependencies") )
+ {
+ for ( const auto & item : itemList)
+ { addAction( new InjectSolutionAction( item, WEAK ) ); }
+ }
+
+ } // namespace detail
/////////////////////////////////////////////////////////////////////
- };// namespace solver
- ///////////////////////////////////////////////////////////////////////
+ } // namespace solver
///////////////////////////////////////////////////////////////////////
-};// namespace zypp
+} // namespace zypp
/////////////////////////////////////////////////////////////////////////
#ifndef ZYPP_SOLVER_DETAIL_PROBLEMSOLUTIONIGNORE_H
#define ZYPP_SOLVER_DETAIL_PROBLEMSOLUTIONIGNORE_H
+#ifndef ZYPP_USE_RESOLVER_INTERNALS
+#error Do not directly include this file!
+#else
+
+#include <list>
-#include "zypp/solver/detail/Types.h"
#include "zypp/ProblemSolution.h"
+#include "zypp/PoolItem.h"
/////////////////////////////////////////////////////////////////////////
namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
+{
///////////////////////////////////////////////////////////////////////
namespace solver
- { /////////////////////////////////////////////////////////////////////
+ {
/////////////////////////////////////////////////////////////////////
namespace detail
- { ///////////////////////////////////////////////////////////////////
-
- /**
- * Class representing one possible solution to one problem found during resolving
- * This problem solution ignores one or more items by setting his dependencies
- * to weak
- **/
- class ProblemSolutionIgnore : public ProblemSolution
- {
- public:
+ {
+ /////////////////////////////////////////////////////////////////////////
+ /// \class ProblemSolutionIgnore
+ /// \brief Class representing one possible solution to one problem found during resolving.
+ ///
+ /// This problem solution ignores one or more items by setting their
+ /// dependencies to weak
+ /////////////////////////////////////////////////////////////////////////
+ class ProblemSolutionIgnore : public ProblemSolution
+ {
+ public:
+ typedef std::list<PoolItem> PoolItemList;
- /**
- * Constructor.
- **/
- ProblemSolutionIgnore( ResolverProblem_Ptr parent,
- PoolItem item );
- ProblemSolutionIgnore( ResolverProblem_Ptr parent,
- PoolItemList itemList);
- };
+ ProblemSolutionIgnore( PoolItem item );
+ ProblemSolutionIgnore( PoolItemList itemList );
+ };
-
-
- ///////////////////////////////////////////////////////////////////
- };// namespace detail
- /////////////////////////////////////////////////////////////////////
+ } // namespace detail
/////////////////////////////////////////////////////////////////////
- };// namespace solver
+ } // namespace solver
///////////////////////////////////////////////////////////////////////
- ///////////////////////////////////////////////////////////////////////
-};// namespace zypp
+} // namespace zypp
/////////////////////////////////////////////////////////////////////////
-
+#endif // ZYPP_USE_RESOLVER_INTERNALS
#endif // ZYPP_SOLVER_DETAIL_PROBLEMSOLUTIONIGNORE_H
-
*/
#include <boost/static_assert.hpp>
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/solver/detail/Resolver.h"
-#include "zypp/solver/detail/Helper.h"
#include "zypp/solver/detail/Testcase.h"
#include "zypp/solver/detail/SATResolver.h"
+#include "zypp/solver/detail/ItemCapKind.h"
+#include "zypp/solver/detail/SolutionAction.h"
+#include "zypp/solver/detail/SolverQueueItem.h"
#include "zypp/Capabilities.h"
#include "zypp/ZConfig.h"
#define MAXSOLVERRUNS 5
+using std::endl;
+using std::make_pair;
+
/////////////////////////////////////////////////////////////////////////
namespace zypp
{ ///////////////////////////////////////////////////////////////////////
namespace detail
{ ///////////////////////////////////////////////////////////////////
-using namespace std;
-
-IMPL_PTR_TYPE(Resolver);
-
+ //using namespace std;
//---------------------------------------------------------------------------
{
UndoTransact resetting (ResStatus::APPL_HIGH);
- _DEBUG ("Resolver::verifySystem() ");
+ DBG << "Resolver::verifySystem()" << endl;
_verifying = true;
void Resolver::applySolutions( const ProblemSolutionList & solutions )
{
- for_( iter, solutions.begin(), solutions.end() )
+ for ( ProblemSolution_Ptr solution : solutions )
{
- ProblemSolution_Ptr solution = *iter;
- if ( !solution->apply( *this ) )
+ if ( ! applySolution( *solution ) )
break;
}
}
+bool Resolver::applySolution( const ProblemSolution & solution )
+{
+ bool ret = true;
+ DBG << "apply solution " << solution << endl;
+ for ( SolutionAction_Ptr action : solution.actions() )
+ {
+ if ( ! action->execute( *this ) )
+ {
+ WAR << "apply solution action failed: " << action << endl;
+ ret = false;
+ break;
+ }
+ }
+ return ret;
+}
+
+//----------------------------------------------------------------------------
+
void Resolver::collectResolverInfo()
{
if ( _satResolver
&& !found) {
alreadySetForInstallation = true;
ItemCapKind capKind = pos->second;
- if (capKind.item == *instIter) found = true;
+ if (capKind.item() == *instIter) found = true;
pos++;
}
&& !found) {
alreadySetForInstallation = true;
ItemCapKind capKind = pos->second;
- if (capKind.item == *instIter) found = true;
+ if (capKind.item() == *instIter) found = true;
pos++;
}
&& !found) {
alreadySetForInstallation = true;
ItemCapKind capKind = pos->second;
- if (capKind.item == provider) found = true;
+ if (capKind.item() == provider) found = true;
pos++;
}
#ifndef ZYPP_SOLVER_DETAIL_RESOLVER_H
#define ZYPP_SOLVER_DETAIL_RESOLVER_H
+#ifndef ZYPP_USE_RESOLVER_INTERNALS
+#error Do not directly include this file!
+#else
#include <iosfwd>
+#include <string>
#include <list>
#include <map>
-#include <string>
-
-#include "zypp/base/ReferenceCounted.h"
-#include "zypp/base/PtrTypes.h"
#include "zypp/ResPool.h"
#include "zypp/TriBool.h"
#include "zypp/base/SerialNumber.h"
-
-#include "zypp/solver/detail/Types.h"
-#include "zypp/solver/detail/SolverQueueItem.h"
+#include "zypp/base/NonCopyable.h"
#include "zypp/ProblemTypes.h"
#include "zypp/ResolverProblem.h"
#include "zypp/Capabilities.h"
#include "zypp/Capability.h"
-
/////////////////////////////////////////////////////////////////////////
namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
-
+{
namespace sat
{
class Transaction;
}
-
///////////////////////////////////////////////////////////////////////
namespace solver
- { /////////////////////////////////////////////////////////////////////
+ {
/////////////////////////////////////////////////////////////////////
namespace detail
- { ///////////////////////////////////////////////////////////////////
-
- class SATResolver;
-
- ///////////////////////////////////////////////////////////////////
- //
- // CLASS NAME : ItemCapKind
- //
- /** */
- struct ItemCapKind
{
- public:
- Capability cap; //Capability which has triggerd this selection
- Dep capKind; //Kind of that capability
- PoolItem item; //Item which has triggered this selection
- bool initialInstallation; //This item has triggered the installation
- //Not already fullfilled requierement only.
-
- ItemCapKind() : capKind(Dep::PROVIDES) {}
- ItemCapKind( PoolItem i, Capability c, Dep k, bool initial)
- : cap( c )
- , capKind( k )
- , item( i )
- , initialInstallation( initial )
- { }
- };
- typedef std::multimap<PoolItem,ItemCapKind> ItemCapKindMap;
- typedef std::list<ItemCapKind> ItemCapKindList;
-
+ class SATResolver;
+ typedef std::list<PoolItem> PoolItemList;
+ typedef std::set<PoolItem> PoolItemSet;
///////////////////////////////////////////////////////////////////
//
* all the solver logic and problem handling goes here; or completely merge
* both classes.
*/
-class Resolver : public base::ReferenceCounted, private base::NonCopyable {
-
+class Resolver : private base::NonCopyable
+{
+ typedef std::multimap<PoolItem,ItemCapKind> ItemCapKindMap;
private:
ResPool _pool;
SATResolver *_satResolver;
// ---------------------------------- I/O
- virtual std::ostream & dumpOn( std::ostream & str ) const;
+ std::ostream & dumpOn( std::ostream & str ) const;
+
friend std::ostream& operator<<( std::ostream& str, const Resolver & obj )
{ return obj.dumpOn (str); }
#undef ZOLV_FLAG_TRIBOOL
ResolverProblemList problems() const;
+
void applySolutions( const ProblemSolutionList & solutions );
+ bool applySolution( const ProblemSolution & solution );
// Return the Transaction computed by the last solver run.
sat::Transaction getTransaction();
///////////////////////////////////////////////////////////////////////
};// namespace zypp
/////////////////////////////////////////////////////////////////////////
-
+#endif // ZYPP_USE_RESOLVER_INTERNALS
#endif // ZYPP_SOLVER_DETAIL_RESOLVER_H
#include <solv/queue.h>
}
-#include "zypp/solver/detail/Helper.h"
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/base/String.h"
#include "zypp/Product.h"
#include "zypp/Capability.h"
#include "zypp/sat/Pool.h"
#include "zypp/sat/WhatProvides.h"
#include "zypp/sat/WhatObsoletes.h"
+#include "zypp/solver/detail/Resolver.h"
#include "zypp/solver/detail/SATResolver.h"
#include "zypp/solver/detail/ProblemSolutionCombi.h"
#include "zypp/solver/detail/ProblemSolutionIgnore.h"
#include "zypp/solver/detail/SolverQueueItemInstall.h"
#include "zypp/solver/detail/SolverQueueItemDelete.h"
#include "zypp/solver/detail/SystemCheck.h"
+#include "zypp/solver/detail/SolutionAction.h"
+#include "zypp/solver/detail/SolverQueueItem.h"
#include "zypp/sat/Transaction.h"
#include "zypp/sat/Queue.h"
+#include "zypp/sat/detail/PoolImpl.h"
+
+#define _XDEBUG(x) do { if (base::logger::isExcessive()) XXX << x << std::endl;} while (0)
+
/////////////////////////////////////////////////////////////////////////
namespace zypp
{ ///////////////////////////////////////////////////////////////////////
, _allowarchchange(false)
, _allowvendorchange(ZConfig::instance().solver_allowVendorChange())
, _allowuninstall(false)
- , _dup_allowdowngrade( true )
- , _dup_allownamechange( true )
- , _dup_allowarchchange( true )
- , _dup_allowvendorchange( true )
, _updatesystem(false)
, _noupdateprovide(false)
, _dosplitprovides(true)
, _ignorealreadyrecommended(true)
, _distupgrade(false)
, _distupgrade_removeunsupported(false)
+ , _dup_allowdowngrade( true )
+ , _dup_allownamechange( true )
+ , _dup_allowarchchange( true )
+ , _dup_allowvendorchange( true )
, _solveSrcPackages(false)
, _cleandepsOnRemove(ZConfig::instance().solver_cleandepsOnRemove())
{
queue_push( &(_jobQueue), id );
}
+ // Ad rules for changed requestedLocales
+ const auto & trackedLocaleIds( myPool().trackedLocaleIds() );
+ for ( const auto & locale : trackedLocaleIds.added() )
+ {
+ queue_push( &(_jobQueue), SOLVER_INSTALL | SOLVER_SOLVABLE_PROVIDES );
+ queue_push( &(_jobQueue), Capability( ResolverNamespace::language, IdString(locale) ).id() );
+ }
+
+ for ( const auto & locale : trackedLocaleIds.removed() )
+ {
+ queue_push( &(_jobQueue), SOLVER_ERASE | SOLVER_SOLVABLE_PROVIDES | SOLVER_CLEANDEPS ); // needs uncond. SOLVER_CLEANDEPS!
+ queue_push( &(_jobQueue), Capability( ResolverNamespace::language, IdString(locale) ).id() );
+ }
+
// Add rules for parallel installable resolvables with different versions
for_( it, sat::Pool::instance().multiversionBegin(), sat::Pool::instance().multiversionEnd() )
{
solution = 0;
while ((solution = solver_next_solution(_solv, problem, solution)) != 0) {
element = 0;
- ProblemSolutionCombi *problemSolution = new ProblemSolutionCombi(resolverProblem);
+ ProblemSolutionCombi *problemSolution = new ProblemSolutionCombi;
while ((element = solver_next_solutionelement(_solv, problem, solution, element, &p, &rp)) != 0) {
if (p == SOLVER_SOLUTION_JOB) {
/* job, rp is index into job queue */
if (ignoreId > 0) {
// There is a possibility to ignore this error by setting weak dependencies
PoolItem item = _pool.find (sat::Solvable(ignoreId));
- ProblemSolutionIgnore *problemSolution = new ProblemSolutionIgnore(resolverProblem, item);
+ ProblemSolutionIgnore *problemSolution = new ProblemSolutionIgnore(item);
resolverProblem->addSolution (problemSolution,
false); // Solutions will be shown at the end
MIL << "ignore some dependencies of " << item << endl;
return resolverProblems;
}
-void
-SATResolver::applySolutions (const ProblemSolutionList & solutions)
-{
- for (ProblemSolutionList::const_iterator iter = solutions.begin();
- iter != solutions.end(); ++iter) {
- ProblemSolution_Ptr solution = *iter;
- Resolver dummyResolver(_pool);
- if (!solution->apply (dummyResolver))
- break;
- }
-}
+void SATResolver::applySolutions( const ProblemSolutionList & solutions )
+{ Resolver( _pool ).applySolutions( solutions ); }
void SATResolver::setLocks()
{
#ifndef ZYPP_SOLVER_DETAIL_SAT_RESOLVER_H
#define ZYPP_SOLVER_DETAIL_SAT_RESOLVER_H
-
+#ifndef ZYPP_USE_RESOLVER_INTERNALS
+#error Do not directly include this file!
+#else
extern "C"
{
#include <solv/solver.h>
#include "zypp/Capability.h"
#include "zypp/solver/detail/SolverQueueItem.h"
+#include "zypp/sat/detail/PoolMember.h"
+
/////////////////////////////////////////////////////////////////////////
namespace zypp
{ ///////////////////////////////////////////////////////////////////////
* via solver::detail::Resolver to SATResolver is pedestrian and error prone.
* Introdce a dedicated solver option structure which is passed down as a whole.
*/
-class SATResolver : public base::ReferenceCounted, private base::NonCopyable {
+class SATResolver : public base::ReferenceCounted, private base::NonCopyable, private sat::detail::PoolMember
+{
private:
ResPool _pool;
///////////////////////////////////////////////////////////////////////
};// namespace zypp
/////////////////////////////////////////////////////////////////////////
-
+#endif // ZYPP_USE_RESOLVER_INTERNALS
#endif // ZYPP_SOLVER_DETAIL_SAT_RESOLVER_H
* 02111-1307, USA.
*/
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/solver/detail/Resolver.h"
#include "zypp/solver/detail/SolutionAction.h"
+#include "zypp/solver/detail/SolverQueueItem.h"
#include "zypp/Capabilities.h"
#include "zypp/base/Logger.h"
using namespace std;
IMPL_PTR_TYPE(SolutionAction);
-IMPL_PTR_TYPE(TransactionSolutionAction);
-IMPL_PTR_TYPE(InjectSolutionAction);
//---------------------------------------------------------------------------
return os;
}
-
-ostream&
-operator<<( ostream& os, const CSolutionActionList & actionlist)
-{
- for (CSolutionActionList::const_iterator iter = actionlist.begin(); iter != actionlist.end(); ++iter) {
- os << *(*iter);
- os << endl;
- }
- return os;
-}
-
//---------------------------------------------------------------------------
ostream &
bool
-TransactionSolutionAction::execute(Resolver & resolver) const
+TransactionSolutionAction::execute(ResolverInternal & resolver) const
{
bool ret = true;
switch (action()) {
}
bool
-InjectSolutionAction::execute(Resolver & resolver) const
+InjectSolutionAction::execute(ResolverInternal & resolver) const
{
switch (_kind) {
case WEAK:
#ifndef ZYPP_SOLVER_DETAIL_SOLUTIONACTION_H
#define ZYPP_SOLVER_DETAIL_SOLUTIONACTION_H
+#ifndef ZYPP_USE_RESOLVER_INTERNALS
+#error Do not directly include this file!
+#else
#include <list>
#include <string>
#include "zypp/base/ReferenceCounted.h"
#include "zypp/base/PtrTypes.h"
-#include "zypp/Dep.h"
-#include "zypp/Capability.h"
-
-#include "zypp/solver/detail/Types.h"
-#include "zypp/solver/detail/Resolver.h"
-#include "zypp/solver/detail/SolverQueueItem.h"
+#include "zypp/PoolItem.h"
/////////////////////////////////////////////////////////////////////////
namespace zypp
namespace detail
{ ///////////////////////////////////////////////////////////////////
+ class Resolver;
+
+ DEFINE_PTR_TYPE(SolverQueueItem);
+
+ DEFINE_PTR_TYPE(SolutionAction);
+ typedef std::list<SolutionAction_Ptr> SolutionActionList;
+
/**
* Abstract base class for one action of a problem solution.
**/
class SolutionAction : public base::ReferenceCounted
{
protected:
+ typedef Resolver ResolverInternal;
SolutionAction ();
public:
virtual ~SolutionAction();
friend std::ostream& operator<<(std::ostream & str, const SolutionAction & action)
{ return action.dumpOn (str); }
friend std::ostream& operator<<(std::ostream & str, const SolutionActionList & actionlist);
- friend std::ostream& operator<<(std::ostream & str, const CSolutionActionList & actionlist);
// ---------------------------------- methods
/**
* Execute this action.
* Returns 'true' on success, 'false' on error.
**/
- virtual bool execute (Resolver & resolver) const = 0;
+ virtual bool execute (ResolverInternal & resolver) const = 0;
};
TransactionKind action() const { return _action; }
// ---------------------------------- methods
- virtual bool execute(Resolver & resolver) const;
+ virtual bool execute(ResolverInternal & resolver) const;
protected:
const PoolItem item() const { return _item; }
// ---------------------------------- methods
- virtual bool execute(Resolver & resolver) const;
+ virtual bool execute(ResolverInternal & resolver) const;
protected:
PoolItem _item;
///////////////////////////////////////////////////////////////////////
};// namespace zypp
/////////////////////////////////////////////////////////////////////////
-
+#endif // ZYPP_USE_RESOLVER_INTERNALS
#endif // ZYPP_SOLVER_DETAIL_SOLUTIONACTION_H
#include <solv/solver.h>
}
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/base/Logger.h"
#include "zypp/solver/detail/SolverQueueItem.h"
#ifndef ZYPP_SOLVER_DETAIL_QUEUEITEM_H
#define ZYPP_SOLVER_DETAIL_QUEUEITEM_H
+#ifndef ZYPP_USE_RESOLVER_INTERNALS
+#error Do not directly include this file!
+#else
#include <iosfwd>
#include <list>
#include <string>
-#include "zypp/solver/detail/Types.h"
#include "zypp/base/ReferenceCounted.h"
#include "zypp/base/NonCopyable.h"
#include "zypp/base/PtrTypes.h"
struct _Queue;
}
-
/////////////////////////////////////////////////////////////////////////
namespace zypp
{ ///////////////////////////////////////////////////////////////////////
namespace detail
{ ///////////////////////////////////////////////////////////////////
+DEFINE_PTR_TYPE(SolverQueueItem);
+
+DEFINE_PTR_TYPE(SolverQueueItemUpdate);
+DEFINE_PTR_TYPE(SolverQueueItemDelete);
+DEFINE_PTR_TYPE(SolverQueueItemInstall);
+DEFINE_PTR_TYPE(SolverQueueItemInstallOneOf);
+DEFINE_PTR_TYPE(SolverQueueItemLock);
+
+
typedef enum {
QUEUE_ITEM_TYPE_UNKNOWN = 0,
QUEUE_ITEM_TYPE_UPDATE,
///////////////////////////////////////////////////////////////////////
};// namespace zypp
/////////////////////////////////////////////////////////////////////////
-
+#endif // ZYPP_USE_RESOLVER_INTERNALS
#endif // ZYPP_SOLVER_DETAIL_QUEUEITEM_H
#include <solv/solver.h>
}
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/base/Logger.h"
#include "zypp/IdString.h"
#include "zypp/Resolver.h"
#include <solv/solver.h>
}
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/base/Logger.h"
#include "zypp/IdString.h"
#include "zypp/IdStringType.h"
#include <solv/solver.h>
}
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/base/Logger.h"
#include "zypp/solver/detail/SolverQueueItemInstallOneOf.h"
#include "zypp/sat/Pool.h"
#include <solv/solver.h>
}
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/base/Logger.h"
#include "zypp/solver/detail/SolverQueueItemLock.h"
#include <solv/solver.h>
}
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/base/Logger.h"
#include "zypp/solver/detail/SolverQueueItemUpdate.h"
#include <fstream>
#include <vector>
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/base/LogTools.h"
#include "zypp/base/IOStream.h"
#include "zypp/base/String.h"
*/
#ifndef ZYPP_TARGET_SYSTEMCHECK_H
#define ZYPP_TARGET_SYSTEMCHECK_H
+#ifndef ZYPP_USE_RESOLVER_INTERNALS
+#error Do not directly include this file!
+#else
#include <iosfwd>
/////////////////////////////////////////////////////////////////
} // namespace zypp
///////////////////////////////////////////////////////////////////
+#endif // ZYPP_USE_RESOLVER_INTERNALS
#endif // ZYPP_TARGET_SYSTEMCHECK_H
#include <sstream>
#include <streambuf>
+#define ZYPP_USE_RESOLVER_INTERNALS
+
#include "zypp/solver/detail/Testcase.h"
#include "zypp/base/Logger.h"
#include "zypp/base/LogControl.h"
#include "zypp/target/modalias/Modalias.h"
#include "zypp/sat/detail/PoolImpl.h"
+#include "zypp/solver/detail/Resolver.h"
#include "zypp/solver/detail/SystemCheck.h"
/////////////////////////////////////////////////////////////////////////
HelixControl (const std::string & controlPath,
const RepositoryTable & sourceTable,
const Arch & systemArchitecture,
- const LocaleSet &languages,
const target::Modalias::ModaliasList & modaliasList,
const std::set<std::string> & multiversionSpec,
const std::string & systemPath,
HelixControl::HelixControl(const std::string & controlPath,
const RepositoryTable & repoTable,
const Arch & systemArchitecture,
- const LocaleSet &languages,
const target::Modalias::ModaliasList & modaliasList,
const std::set<std::string> & multiversionSpec,
const std::string & systemPath,
<< "\" />" << endl << endl;
}
- for (LocaleSet::const_iterator iter = languages.begin(); iter != languages.end(); iter++) {
- *file << TAB << "<locale name=\"" << iter->code()
- << "\" />" << endl;
+ // HACK: directly access sat::pool
+ const sat::Pool & satpool( sat::Pool::instance() );
+
+ // RequestedLocales
+ const LocaleSet & addedLocales( satpool.getAddedRequestedLocales() );
+ const LocaleSet & removedLocales( satpool.getRemovedRequestedLocales() );
+ const LocaleSet & requestedLocales( satpool.getRequestedLocales() );
+
+ for ( Locale l : requestedLocales )
+ {
+ const char * fate = ( addedLocales.count(l) ? "\" fate=\"added" : "" );
+ *file << TAB << "<locale name=\"" << l << fate << "\" />" << endl;
+ }
+ for ( Locale l : removedLocales )
+ {
+ *file << TAB << "<locale name=\"" << l << "\" fate=\"removed\" />" << endl;
+ }
+
+ // AutoInstalled
+ for ( IdString::IdType n : satpool.autoInstalled() )
+ {
+ *file << TAB << "<autoinst name=\"" << IdString(n) << "\" />" << endl;
}
+
+
for_( it, modaliasList.begin(), modaliasList.end() ) {
*file << TAB << "<modalias name=\"" << *it
<< "\" />" << endl;
HelixControl control (dumpPath + "/solver-test.xml",
repoTable,
ZConfig::instance().systemArchitecture(),
- pool.getRequestedLocales(),
target::Modalias::instance().modaliasList(),
ZConfig::instance().multiversionSpec(),
"solver-system.xml.gz",
#ifndef ZYPP_SOLVER_DETAIL_TESTCASE_H
#define ZYPP_SOLVER_DETAIL_TESTCASE_H
+#ifndef ZYPP_USE_RESOLVER_INTERNALS
+#error Do not directly include this file!
+#else
#include <string>
-#include "zypp/solver/detail/Resolver.h"
/////////////////////////////////////////////////////////////////////////
namespace zypp
namespace detail
{ ///////////////////////////////////////////////////////////////////
+ class Resolver;
+
///////////////////////////////////////////////////////////////////
//
// CLASS NAME : Testcase
///////////////////////////////////////////////////////////////////////
};// namespace zypp
/////////////////////////////////////////////////////////////////////////
-
+#endif // ZYPP_USE_RESOLVER_INTERNALS
#endif // ZYPP_SOLVER_DETAIL_TESTCASE_H
#ifndef ZYPP_SOLVER_DETAIL_TYPES_H
#define ZYPP_SOLVER_DETAIL_TYPES_H
-#include <iosfwd>
#include <list>
-#include <set>
-#include <map>
-#include <string>
-
-#include "zypp/base/ReferenceCounted.h"
-#include "zypp/base/NonCopyable.h"
#include "zypp/base/PtrTypes.h"
-#include "zypp/base/Functional.h"
-
-#include "zypp/PoolItem.h"
-
-#define _DEBUG(x) DBG << x << std::endl;
-#define _XDEBUG(x) do { if (base::logger::isExcessive()) XXX << x << std::endl;} while (0)
-//#define _DEBUG(x)
/////////////////////////////////////////////////////////////////////////
namespace zypp
-{ ///////////////////////////////////////////////////////////////////////
+{
///////////////////////////////////////////////////////////////////////
namespace solver
- { /////////////////////////////////////////////////////////////////////
+ {
/////////////////////////////////////////////////////////////////////
namespace detail
- { ///////////////////////////////////////////////////////////////////
+ {
+ // A few type names exposed in the public API
+ //
+ class Resolver;
+ typedef Resolver ResolverInternal; ///< Preferred name in API
-typedef std::list<PoolItem> PoolItemList;
-typedef std::set<PoolItem> PoolItemSet;
-
-DEFINE_PTR_TYPE(Resolver);
+ class ItemCapKind;
+ typedef std::list<ItemCapKind> ItemCapKindList;
-DEFINE_PTR_TYPE(SolutionAction);
-typedef std::list<SolutionAction_Ptr> SolutionActionList;
-typedef std::list<SolutionAction_constPtr> CSolutionActionList;
-DEFINE_PTR_TYPE(TransactionSolutionAction);
-DEFINE_PTR_TYPE(InjectSolutionAction);
-DEFINE_PTR_TYPE(SolverQueueItem);
-DEFINE_PTR_TYPE(SolverQueueItemUpdate);
-DEFINE_PTR_TYPE(SolverQueueItemDelete);
-DEFINE_PTR_TYPE(SolverQueueItemInstall);
-DEFINE_PTR_TYPE(SolverQueueItemInstallOneOf);
-DEFINE_PTR_TYPE(SolverQueueItemLock);
-
- ///////////////////////////////////////////////////////////////////
- };// namespace detail
- /////////////////////////////////////////////////////////////////////
+ DEFINE_PTR_TYPE(SolverQueueItem);
+ typedef std::list<SolverQueueItem_Ptr> SolverQueueItemList;
+
+ DEFINE_PTR_TYPE(SolutionAction);
+ typedef std::list<SolutionAction_Ptr> SolutionActionList;
+
+ } // namespace detail
/////////////////////////////////////////////////////////////////////
- };// namespace solver
+ } // namespace solver
///////////////////////////////////////////////////////////////////////
- ///////////////////////////////////////////////////////////////////////
-};// namespace zypp
+} // namespace zypp
/////////////////////////////////////////////////////////////////////////
-
#endif // ZYPP_SOLVER_DETAIL_TYPES_H
+++ /dev/null
-/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 4 -*- */
-/* libzypp.h
- * Copyright (C) 2000-2002 Ximian, Inc.
- * Copyright (C) 2005 SUSE Linux Products GmbH
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
- * 02111-1307, USA.
- */
-
-#ifndef ZYPP_SOLVER_DETAIL_LIBZYPP_H
-#define ZYPP_SOLVER_DETAIL_LIBZYPP_H
-
-#include "zypp/solver/detail/Resolver.h"
-#include "zypp/solver/detail/ResolverContext.h"
-#include "zypp/solver/detail/ResolverProblem.h"
-#include "zypp/solver/detail/ProblemSolution.h"
-#include "zypp/solver/detail/SolutionAction.h"
-
-#endif // ZYPP_SOLVER_DETAIL_LIBZYPP_H
{
friend std::ostream & operator<<( std::ostream & str, const SolvIdentFile & obj );
public:
- typedef std::tr1::unordered_set<IdString> Data;
+ typedef std::unordered_set<IdString> Data;
public:
/** Ctor taking the file to read/write. */
#include "zypp/target/RpmPostTransCollector.h"
#include "zypp/parser/ProductFileReader.h"
-
-#include "zypp/solver/detail/Testcase.h"
-
#include "zypp/repo/SrcPackageProvider.h"
#include "zypp/sat/Pool.h"
system.addSolv( rpmsolv );
}
- sat::Pool::instance().rootDir( _root );
+ satpool.rootDir( _root );
// (Re)Load the requested locales et al.
// If the requested locales are empty, we leave the pool untouched
const LocaleSet & requestedLocales( _requestedLocalesFile.locales() );
if ( ! requestedLocales.empty() )
{
- satpool.setRequestedLocales( requestedLocales );
+ satpool.initRequestedLocales( requestedLocales );
}
}
{
#include "zypp/base/String.h"
#include "zypp/zypp_detail/ZYppImpl.h"
-#include "zypp/solver/detail/Helper.h"
#include "zypp/target/TargetImpl.h"
#include "zypp/ZYpp.h"
#include "zypp/DiskUsageCounter.h"