#
SET(LIBZYPP_MAJOR "15")
SET(LIBZYPP_COMPATMINOR "14")
-SET(LIBZYPP_MINOR "15")
+SET(LIBZYPP_MINOR "16")
SET(LIBZYPP_PATCH "0")
#
-# LAST RELEASED: 15.15.0 (14)
+# LAST RELEASED: 15.16.0 (14)
# (The number in parenthesis is LIBZYPP_COMPATMINOR)
#=======
-------------------------------------------------------------------
+Mon Sep 14 12:21:30 CEST 2015 - ma@suse.de
+
+- Reload multiversion setting from the target zypp.conf (bnc#906096)
+- version 15.16.0 (14)
+
+-------------------------------------------------------------------
+Sun Sep 13 01:15:26 CEST 2015 - ma@suse.de
+
+- Update sle-zypp-po.tar.bz2
+
+-------------------------------------------------------------------
+Sun Sep 13 01:13:30 CEST 2015 - ma@suse.de
+
+- Update zypp-po.tar.bz2
+
+-------------------------------------------------------------------
+Thu Sep 10 01:16:00 CEST 2015 - ma@suse.de
+
+- Update sle-zypp-po.tar.bz2
+
+-------------------------------------------------------------------
Fri Sep 4 13:49:33 CEST 2015 - ma@suse.de
- Don't cache repo releasever (bnc#943563)
assert( impl_r );
}
- Target_Ptr Target::_nullimpl;
-
- /** Null implementation */
- Target_Ptr Target::nullimpl()
- {
- if (! _nullimpl)
- {
- _nullimpl = new Target(target::TargetImpl::nullimpl());
- }
- return _nullimpl;
- }
-
std::ostream & operator<<( std::ostream & str, const Target::DistributionLabel & obj )
{
str << "summary=" << obj.summary << endl;
*/
void unload();
- /** Null implementation */
- static Target_Ptr nullimpl();
-
/** Refference to the RPM database */
target::rpm::RpmDb & rpmDb();
/** Pointer to implementation */
RW_pointer<Impl,rw_pointer::Intrusive<Impl> > _pimpl;
-
- static Target_Ptr _nullimpl;
};
///////////////////////////////////////////////////////////////////
/// \class UserData
/// \brief Typesafe passing of user data via callbacks
///
- /// Basically a <tt>std::map<std::string,boost::any></tt> plus
+ /// Basically a <tt>std::map<std::string,AnyType></tt> plus
/// associated \ref ContentType.
///
/// Constness protects non-empty values from being modified.
///////////////////////////////////////////////////////////////////
class UserData
{
- typedef std::map<std::string,boost::any> DataType;
- typedef DataType::size_type size_type;
- typedef DataType::key_type key_type;
- typedef DataType::value_type value_type;
- typedef DataType::const_iterator const_iterator;
public:
- typedef zypp::ContentType ContentType;
+ typedef boost::any AnyType;
+ typedef boost::bad_any_cast bad_AnyType_cast;
+
+ typedef std::map<std::string,AnyType> DataType;
+ typedef DataType::size_type size_type;
+ typedef DataType::key_type key_type;
+ typedef DataType::value_type value_type;
+ typedef DataType::const_iterator const_iterator;
+
+ typedef zypp::ContentType ContentType;
+
public:
/** Default ctor. */
UserData()
/** Set the value for key (nonconst version always returns true).
* Const version is allowed to set empty values or to add new ones only.
*/
- bool set( const std::string & key_r, boost::any val_r )
+ bool set( const std::string & key_r, AnyType val_r )
{ dataRef()[key_r] = std::move(val_r); return true; }
/** \overload const version */
- bool set( const std::string & key_r, boost::any val_r ) const
+ bool set( const std::string & key_r, AnyType val_r ) const
{
bool ret = false;
- boost::any & val( dataRef()[key_r] );
+ AnyType & val( dataRef()[key_r] );
if ( val.empty() )
{
val = std::move(val_r);
/** Set an empty value for \a key_r (if possible). */
bool reset( const std::string & key_r )
- { return set( key_r, boost::any() ); }
+ { return set( key_r, AnyType() ); }
/** \overload const version */
bool reset( const std::string & key_r ) const
- { return set( key_r, boost::any() ); }
+ { return set( key_r, AnyType() ); }
/** Remove key from data.*/
void erase( const std::string & key_r )
{ if ( _dataP ) _dataP->erase( key_r ); }
- /** Return the keys boost::any value or an empty value if key does not exist. */
- const boost::any & getvalue( const std::string & key_r ) const
+ /** \ref get helper returning the keys AnyType value or an empty value if key does not exist. */
+ const AnyType & getvalue( const std::string & key_r ) const
{
if ( _dataP )
{
return it->second;
}
}
- static const boost::any none;
+ static const AnyType none;
return none;
}
/** Pass back a <tt>const Tp &</tt> reference to \a key_r value.
- * \throws boost::bad_any_cast if key is not set or value is not of appropriate type
+ * \throws bad_AnyType_cast if key is not set or value is not of appropriate type
* \code
* UserData data;
* std::string value( "defaultvalue" );
* {
* value = data.get<std::string>( "mykey" );
* }
- * catch ( const boost::bad_any_cast & )
+ * catch ( const UserData::bad_AnyType_cast & )
* {
* // no "mykey" or not a std::sting
* }
{ return boost::any_cast<const Tp &>( getvalue( key_r ) ); }
/** Pass back a \a Tp copy of \a key_r value.
- * \throws boost::bad_any_cast if key is not set or value is not of appropriate type
+ * \throws bad_AnyType_cast if key is not set or value is not of appropriate type
* \code
* UserData data;
* std::string value = data.get<std::string>( "mykey", "defaultvalue" );
}
#include <iostream>
#include <fstream>
-#include "zypp/base/Logger.h"
+#include "zypp/base/LogTools.h"
#include "zypp/base/IOStream.h"
#include "zypp/base/InputStream.h"
#include "zypp/base/String.h"
+#include "zypp/base/Regex.h"
#include "zypp/ZConfig.h"
#include "zypp/ZYppFactory.h"
#include "zypp/parser/IniDict.h"
#include "zypp/sat/Pool.h"
+#include "zypp/sat/detail/PoolImpl.h"
using namespace std;
using namespace zypp::filesystem;
return ret;
}
+
+ inline Pathname _autodetectSystemRoot()
+ {
+ Target_Ptr target( getZYpp()->getTarget() );
+ return target ? target->root() : Pathname();
+ }
+
+ inline Pathname _autodetectZyppConfPath()
+ {
+ const char *env_confpath = getenv( "ZYPP_CONF" );
+ return env_confpath ? env_confpath : "/etc/zypp/zypp.conf";
+ }
+
/////////////////////////////////////////////////////////////////
} // namespace zypp
///////////////////////////////////////////////////////////////////
*/
class ZConfig::Impl
{
+ typedef std::set<std::string> MultiversionSpec;
+
public:
Impl( const Pathname & override_r = Pathname() )
: _parsedZyppConf ( override_r )
// ZYPP_CONF might override /etc/zypp/zypp.conf
if ( _parsedZyppConf.empty() )
{
- const char *env_confpath = getenv( "ZYPP_CONF" );
- _parsedZyppConf = env_confpath ? env_confpath : "/etc/zypp/zypp.conf";
+ _parsedZyppConf = _autodetectZyppConfPath();
}
else
{
}
else if ( entry == "multiversion" )
{
- str::splitEscaped( value, inserter( _multiversion, _multiversion.end() ), ", \t" );
+ MultiversionSpec & defSpec( _multiversionMap.getDefaultSpec() );
+ str::splitEscaped( value, std::inserter( defSpec, defSpec.end() ), ", \t" );
}
else if ( entry == "locksfile.path" )
{
}
}
}
+ //
+
}
else
{
Pathname solver_checkSystemFile;
Pathname solver_checkSystemFileDir;
- std::set<std::string> & multiversion() { return getMultiversion(); }
- const std::set<std::string> & multiversion() const { return getMultiversion(); }
+ MultiversionSpec & multiversion() { return getMultiversion(); }
+ const MultiversionSpec & multiversion() const { return getMultiversion(); }
bool apply_locks_file;
Option<Pathname> pluginsPath;
private:
- std::set<std::string> & getMultiversion() const
+ // HACK for bnc#906096: let pool re-evaluate multiversion spec
+ // if target root changes. ZConfig returns data sensitive to
+ // current target root.
+ // TODO Actually we'd need to scan the target systems zypp.conf and
+ // overlay all system specific values.
+ struct MultiversionMap
{
- if ( ! _multiversionInitialized )
+ typedef std::map<Pathname,MultiversionSpec> SpecMap;
+
+ MultiversionSpec & getSpec( Pathname root_r, const Impl & zConfImpl_r ) // from system at root
+ {
+ // _specMap[] - the plain zypp.conf value
+ // _specMap[/] - combine [] and multiversion.d scan
+ // _specMap[root] - scan root/zypp.conf and root/multiversion.d
+
+ if ( root_r.empty() )
+ root_r == "/";
+ bool cacheHit = _specMap.count( root_r );
+ MultiversionSpec & ret( _specMap[root_r] ); // creates new entry on the fly
+
+ if ( ! cacheHit )
+ {
+ if ( root_r == "/" )
+ ret.swap( _specMap[Pathname()] ); // original zypp.conf
+ else
+ scanConfAt( root_r, ret, zConfImpl_r ); // scan zypp.conf at root_r
+ scanDirAt( root_r, ret, zConfImpl_r ); // add multiversion.d at root_r
+ using zypp::operator<<;
+ MIL << "MultiversionSpec '" << root_r << "' = " << ret << endl;
+ }
+ return ret;
+ }
+
+ MultiversionSpec & getDefaultSpec() // Spec from zypp.conf parsing; called before any getSpec
+ { return _specMap[Pathname()]; }
+
+ private:
+ void scanConfAt( const Pathname root_r, MultiversionSpec & spec_r, const Impl & zConfImpl_r )
{
- Pathname multiversionDir( cfg_multiversion_path );
+ static const str::regex rx( "^multiversion *= *(.*)" );
+ str::smatch what;
+ iostr::simpleParseFile( InputStream( Pathname::assertprefix( root_r, _autodetectZyppConfPath() ) ),
+ [&]( int num_r, std::string line_r )->bool
+ {
+ if ( line_r[0] == 'm' && str::regex_match( line_r, what, rx ) )
+ {
+ str::splitEscaped( what[1], std::inserter( spec_r, spec_r.end() ), ", \t" );
+ return false; // stop after match
+ }
+ return true;
+ } );
+ }
+
+ void scanDirAt( const Pathname root_r, MultiversionSpec & spec_r, const Impl & zConfImpl_r )
+ {
+ // NOTE: Actually we'd need to scan and use the root_r! zypp.conf values.
+ Pathname multiversionDir( zConfImpl_r.cfg_multiversion_path );
if ( multiversionDir.empty() )
- multiversionDir = ( cfg_config_path.empty() ? Pathname("/etc/zypp") : cfg_config_path ) / "multiversion.d";
+ multiversionDir = ( zConfImpl_r.cfg_config_path.empty()
+ ? Pathname("/etc/zypp")
+ : zConfImpl_r.cfg_config_path ) / "multiversion.d";
- filesystem::dirForEach( multiversionDir,
- [this]( const Pathname & dir_r, const char *const & name_r )->bool
+ filesystem::dirForEach( Pathname::assertprefix( root_r, multiversionDir ),
+ [&spec_r]( const Pathname & dir_r, const char *const & name_r )->bool
{
MIL << "Parsing " << dir_r/name_r << endl;
iostr::simpleParseFile( InputStream( dir_r/name_r ),
- [this]( int num_r, std::string line_r )->bool
+ [&spec_r]( int num_r, std::string line_r )->bool
{
DBG << " found " << line_r << endl;
- _multiversion.insert( line_r );
+ spec_r.insert( std::move(line_r) );
return true;
} );
return true;
} );
- _multiversionInitialized = true;
}
- return _multiversion;
- }
- mutable std::set<std::string> _multiversion;
- mutable DefaultIntegral<bool,false> _multiversionInitialized;
+
+ private:
+ SpecMap _specMap;
+ };
+
+ MultiversionSpec & getMultiversion() const
+ { return _multiversionMap.getSpec( _autodetectSystemRoot(), *this ); }
+
+ mutable MultiversionMap _multiversionMap;
};
///////////////////////////////////////////////////////////////////
{}
Pathname ZConfig::systemRoot() const
- {
- Target_Ptr target( getZYpp()->getTarget() );
- return target ? target->root() : Pathname();
- }
+ { return _autodetectSystemRoot(); }
///////////////////////////////////////////////////////////////////
//
void ZConfig::setSolverUpgradeRemoveDroppedPackages( bool val_r ) { _pimpl->solverUpgradeRemoveDroppedPackages.set( val_r ); }
void ZConfig::resetSolverUpgradeRemoveDroppedPackages() { _pimpl->solverUpgradeRemoveDroppedPackages.restoreToDefault(); }
+ namespace
+ {
+ inline void sigMultiversionSpecChanged()
+ {
+ sat::detail::PoolMember::myPool().multiversionSpecChanged();
+ }
+ }
+
const std::set<std::string> & ZConfig::multiversionSpec() const { return _pimpl->multiversion(); }
- void ZConfig::multiversionSpec( std::set<std::string> new_r ) { _pimpl->multiversion().swap( new_r ); }
- void ZConfig::clearMultiversionSpec() { _pimpl->multiversion().clear(); }
- void ZConfig::addMultiversionSpec( const std::string & name_r ) { _pimpl->multiversion().insert( name_r ); }
- void ZConfig::removeMultiversionSpec( const std::string & name_r ) { _pimpl->multiversion().erase( name_r ); }
+ void ZConfig::multiversionSpec( std::set<std::string> new_r ) { _pimpl->multiversion().swap( new_r ); sigMultiversionSpecChanged(); }
+ void ZConfig::clearMultiversionSpec() { _pimpl->multiversion().clear(); sigMultiversionSpecChanged(); }
+ void ZConfig::addMultiversionSpec( const std::string & name_r ) { _pimpl->multiversion().insert( name_r ); sigMultiversionSpecChanged(); }
+ void ZConfig::removeMultiversionSpec( const std::string & name_r ) { _pimpl->multiversion().erase( name_r ); sigMultiversionSpecChanged(); }
bool ZConfig::apply_locks_file() const
{ return _pimpl->apply_locks_file; }
return *_availableLocalesPtr;
}
+ ///////////////////////////////////////////////////////////////////
void PoolImpl::multiversionListInit() const
{
}
}
+ void PoolImpl::multiversionSpecChanged()
+ { _multiversionListPtr.reset(); }
+
const PoolImpl::MultiversionList & PoolImpl::multiversionList() const
{
if ( ! _multiversionListPtr )
bool PoolImpl::isMultiversion( const Solvable & solv_r ) const
{ return multiversionList().contains( solv_r ); }
+ ///////////////////////////////////////////////////////////////////
const std::set<std::string> & PoolImpl::requiredFilesystems() const
{
const MultiversionList & multiversionList() const;
bool isMultiversion( const Solvable & solv_r ) const;
+
+ void multiversionSpecChanged();
//@}
public:
#include "zypp/repo/SrcPackageProvider.h"
#include "zypp/sat/Pool.h"
+#include "zypp/sat/detail/PoolImpl.h"
#include "zypp/sat/Transaction.h"
#include "zypp/PluginScript.h"
///////////////////////////////////////////////////////////////////
namespace zypp
-{ /////////////////////////////////////////////////////////////////
+{
+ /////////////////////////////////////////////////////////////////
+ namespace
+ {
+ // HACK for bnc#906096: let pool re-evaluate multiversion spec
+ // if target root changes. ZConfig returns data sensitive to
+ // current target root.
+ inline void sigMultiversionSpecChanged()
+ {
+ sat::detail::PoolMember::myPool().multiversionSpecChanged();
+ }
+ } //namespace
+ /////////////////////////////////////////////////////////////////
+
///////////////////////////////////////////////////////////////////
namespace json
{
IMPL_PTR_TYPE(TargetImpl);
- TargetImpl_Ptr TargetImpl::_nullimpl;
-
- /** Null implementation */
- TargetImpl_Ptr TargetImpl::nullimpl()
- {
- if (_nullimpl == 0)
- _nullimpl = new TargetImpl;
- return _nullimpl;
- }
-
///////////////////////////////////////////////////////////////////
//
// METHOD NAME : TargetImpl::TargetImpl
HistoryLog::setRoot(_root);
createAnonymousId();
-
+ sigMultiversionSpecChanged(); // HACK: see sigMultiversionSpecChanged
MIL << "Initialized target on " << _root << endl;
}
TargetImpl::~TargetImpl()
{
_rpm.closeDatabase();
+ sigMultiversionSpecChanged(); // HACK: see sigMultiversionSpecChanged
MIL << "Targets closed" << endl;
}
/** Dtor. */
virtual ~TargetImpl();
- /** Null implementation */
- static TargetImpl_Ptr nullimpl();
-
/**
* generates the unique anonymous id which is called
* when creating the target
HardLocksFile _hardLocksFile;
/** Cache distributionVersion */
mutable std::string _distributionVersion;
-
- private:
- /** Null implementation */
- static TargetImpl_Ptr _nullimpl;
};
///////////////////////////////////////////////////////////////////