Imported Upstream version 15.0.0
[platform/upstream/libzypp.git] / zypp / Arch.h
1 /*---------------------------------------------------------------------\
2 |                          ____ _   __ __ ___                          |
3 |                         |__  / \ / / . \ . \                         |
4 |                           / / \ V /|  _/  _/                         |
5 |                          / /__ | | | | | |                           |
6 |                         /_____||_| |_| |_|                           |
7 |                                                                      |
8 \---------------------------------------------------------------------*/
9 /** \file zypp/Arch.h
10  *
11 */
12 #ifndef ZYPP_ARCH_H
13 #define ZYPP_ARCH_H
14
15 #include <iosfwd>
16 #include <functional>
17 #include <set>
18 #include <string>
19
20 #include "zypp/base/String.h"
21 #include "zypp/base/Iterator.h"
22
23 #include "zypp/IdStringType.h"
24 #include "zypp/RelCompare.h"
25
26 ///////////////////////////////////////////////////////////////////
27 namespace zypp
28 { /////////////////////////////////////////////////////////////////
29
30   ///////////////////////////////////////////////////////////////////
31   //
32   //    CLASS NAME : Arch
33   //
34   /** Architecture.
35   */
36   class Arch
37   {
38   public:
39     /** Default ctor \ref Arc_noarch. */
40     Arch();
41
42     /** Ctor taking Arch as string. */
43     explicit Arch( IdString::IdType id_r );
44     explicit Arch( const IdString & idstr_r );
45     explicit Arch( const std::string & str_r );
46     explicit Arch( const char * cstr_r );
47
48   public:
49     /** \name IdStringType like interface.
50      * We can't use the complete \ref IdStringType mixin until
51      * _doCompare can be redefined on any level, not just as char*.
52     */
53     //@{
54     /** String representation of Arch. */
55     IdString idStr() const;
56      /** \overload */
57     const std::string & asString() const;
58     /** \overload */
59     const char * c_str() const
60     { return asString().c_str(); }
61
62     /** Test for an empty Arch (this is \ref Arch_epmty, not \ref Arch_noarch ). */
63     bool empty() const
64     { return asString().empty(); }
65
66     /** Size of the string representation. */
67     unsigned size() const
68     { return asString().size(); }
69
70     /** Expert backdoor. */
71     IdString::IdType id() const
72     { return idStr().id(); }
73     //@}
74
75   public:
76     /** Whether this is a buitin (or known) architecture.
77      * Used e.g. in \ref Capability to determine whether
78      * some trailing \c ".string" is part ot the name or
79      * restriction to an architecture.
80     */
81     bool isBuiltIn() const;
82
83   public:
84     /** Compatibility relation.
85      * \return \c True iff \c this is compatible with \a targetArch_r.
86      * \code
87      * Arch_noarch.compatibleWith( ... )       ==> always true;
88      * Arch_i686.compatibleWith( Arch_x86_64 ) ==> true;
89      * Arch_x86_64.compatibleWith( Arch_i686 ) ==> false;
90      * \endcode
91     */
92     bool compatibleWith( const Arch & targetArch_r ) const;
93
94     /**
95      * \return the arch before noarch if it's not a multilib arch
96      * (e.g. x86_64,sparc64v,sparc64,ppc64,s390x).
97     */
98     Arch baseArch() const;
99
100     /** \overload static version. */
101     static Arch baseArch( const Arch & targetArch_r )
102     { return targetArch_r.baseArch(); }
103
104     /** Arch comparison.
105      * Compatible architectures are treated as \c less (i.e. <tt>i686>i386>noarch</tt>).
106      * So \c Arch_noarch is the least Arch. Equivalent architectures
107      * (compatible in both directions) are ordered arbitrary.
108      */
109     int compare( const Arch & rhs ) const;
110
111     /** Arch comparison (static version). */
112     static int compare( const Arch & lhs, const Arch & rhs )
113     { return lhs.compare( rhs ); }
114
115   public:
116     /** Reversed arch order, best Arch first. */
117     typedef std::set<Arch,CompareByGT<Arch> > CompatSet;
118
119     /** Return a set of all Arch's \ref compatibleWith a \a targetArch_r.
120      * \note The set is ordered according to compare, thus iterating
121      * will start at \a targetArch_r and end with \c Arch_noarch.
122      * \code
123      * Arch::CompatSet cset( Arch::compatSet( Arch_x86_64 ) );
124      *
125      * cout << str::join( make_transform_iterator( cset.begin(), std::mem_fun_ref(&Arch::asString) ),
126      *                    make_transform_iterator( cset.end(), std::mem_fun_ref(&Arch::asString) ) )
127      *      << endl;
128      *
129      * // Prints: x86_64 athlon i686 i586 i486 i386 noarch
130      * \endcode
131     */
132     static CompatSet compatSet( const Arch & targetArch_r );
133
134     /** */
135     static std::string asString( const CompatSet & cset )
136     {
137       return str::join( make_transform_iterator( cset.begin(), std::mem_fun_ref(&Arch::asString) ),
138                         make_transform_iterator( cset.end(), std::mem_fun_ref(&Arch::asString) ) );
139     }
140
141   public:
142     struct CompatEntry;
143   private:
144     Arch( const CompatEntry & );
145     const CompatEntry * _entry;
146   };
147   ///////////////////////////////////////////////////////////////////
148
149   /** \name Builtin architecture constants.
150    *
151    * Defined outside Arch as e.g. \c Arch_i386, because some names,
152    * like \c i388, are used as \c #define, thus unusable as identifier
153    * like \c Arch::i386.
154   */
155   //@{
156   /** \relates Arch
157    * This is an empty \ref Arch represented by an empty string.
158    * Sometimes used to indicate an any or an unknown Arch. Don't
159    * confuse this with \ref Arch_noarch, which is in fact an
160    * architecture.
161   */
162   extern const Arch Arch_empty;
163
164   /** \relates Arch */
165   extern const Arch Arch_noarch;
166
167   /** \relates Arch */
168   extern const Arch Arch_pentium4;
169   /** \relates Arch */
170   extern const Arch Arch_pentium3;
171
172   /** \relates Arch */
173   extern const Arch Arch_x86_64;
174   /** \relates Arch */
175   extern const Arch Arch_athlon;
176   /** \relates Arch */
177   extern const Arch Arch_i686;
178   /** \relates Arch */
179   extern const Arch Arch_i586;
180   /** \relates Arch */
181   extern const Arch Arch_i486;
182   /** \relates Arch */
183   extern const Arch Arch_i386;
184
185   /** \relates Arch */
186   extern const Arch Arch_s390x;
187   /** \relates Arch */
188   extern const Arch Arch_s390;
189
190   /** \relates Arch */
191   extern const Arch Arch_ppc64le;
192
193   /** \relates Arch */
194   extern const Arch Arch_ppc64p7;
195   /** \relates Arch */
196   extern const Arch Arch_ppc64;
197   /** \relates Arch */
198   extern const Arch Arch_ppc;
199
200   /** \relates Arch */
201   extern const Arch Arch_ia64;
202
203   /** \relates Arch */
204   extern const Arch Arch_alphaev67;
205   /** \relates Arch */
206   extern const Arch Arch_alphaev6;
207   /** \relates Arch */
208   extern const Arch Arch_alphapca56;
209   /** \relates Arch */
210   extern const Arch Arch_alphaev56;
211   /** \relates Arch */
212   extern const Arch Arch_alphaev5;
213   /** \relates Arch */
214   extern const Arch Arch_alpha;
215
216    /** \relates Arch */
217   extern const Arch Arch_sparc64v;
218   /** \relates Arch */
219   extern const Arch Arch_sparc64;
220   /** \relates Arch */
221   extern const Arch Arch_sparcv9v;
222   /** \relates Arch */
223   extern const Arch Arch_sparcv9;
224   /** \relates Arch */
225   extern const Arch Arch_sparcv8;
226   /** \relates Arch */
227   extern const Arch Arch_sparc;
228
229   /** \relates Arch */
230   extern const Arch Arch_aarch64;
231   /** \relates Arch */
232   extern const Arch Arch_armv7tnhl;
233   /** \relates Arch */
234   extern const Arch Arch_armv7thl;
235   /** \relates Arch */
236   extern const Arch Arch_armv7nhl;
237   /** \relates Arch */
238   extern const Arch Arch_armv7hl;
239   /** \relates Arch */
240   extern const Arch Arch_armv7l;
241   /** \relates Arch */
242   extern const Arch Arch_armv6hl;
243   /** \relates Arch */
244   extern const Arch Arch_armv6l;
245   /** \relates Arch */
246   extern const Arch Arch_armv5tejl;
247   /** \relates Arch */
248   extern const Arch Arch_armv5tel;
249   /** \relates Arch */
250   extern const Arch Arch_armv5l;
251   /** \relates Arch */
252   extern const Arch Arch_armv4tl;
253   /** \relates Arch */
254   extern const Arch Arch_armv4l;
255   /** \relates Arch */
256   extern const Arch Arch_armv3l;
257
258    /** \relates Arch */
259   extern const Arch Arch_sh3;
260
261   /** \relates Arch */
262   extern const Arch Arch_sh4;
263   /** \relates Arch */
264   extern const Arch Arch_sh4a;
265
266   /** \relates Arch */
267   extern const Arch Arch_m68k;
268   //@}
269
270   ///////////////////////////////////////////////////////////////////
271
272   /** \relates Arch stream output. */
273   inline std::ostream & operator<<( std::ostream & str, const Arch & obj )
274   { return str << obj.asString(); }
275
276   /** \relates Arch XML output. */
277   inline std::ostream & dumpAsXmlOn( std::ostream & str, const Arch & obj )
278   { return str << "<arch>" << obj <<  "</arch>"; }
279
280   /** \name Equality based on string value. */
281   //@{
282   /** \relates Arch */
283   inline bool operator==( const Arch & lhs, const Arch & rhs )
284   { return lhs.asString() == rhs.asString(); }
285
286   /** \relates Arch */
287   inline bool operator==( const Arch & lhs, const std::string & rhs )
288   { return lhs.asString() == rhs; }
289
290   /** \relates Arch */
291   inline bool operator==( const std::string & lhs, const Arch & rhs )
292   { return lhs == rhs.asString(); }
293
294   /** \relates Arch */
295   inline bool operator!=( const Arch & lhs, const Arch & rhs )
296   { return !( lhs == rhs ); }
297
298   /** \relates Arch */
299   inline bool operator!=( const Arch & lhs, const std::string & rhs )
300   { return !( lhs == rhs ); }
301
302   /** \relates Arch */
303   inline bool operator!=( const std::string & lhs, const Arch & rhs )
304   { return !( lhs == rhs ); }
305   //@}
306
307   ///////////////////////////////////////////////////////////////////
308
309   /** Functor finding compatible architectures.
310    * \see Arch::compatibleWith
311   */
312   struct ArchCompatibleWith : public std::unary_function<Arch,bool>
313   {
314     /** The target architecture */
315     Arch _targetArch;
316     /** Ctor taking the target architecture */
317     ArchCompatibleWith( const Arch & targetArch_r )
318     : _targetArch( targetArch_r )
319     {}
320     /** Call Arch::compatibleWith ( \c _targetArch ) on \a rhs. */
321     bool operator()( const Arch & rhs ) const
322     { return rhs.compatibleWith( _targetArch ); }
323   };
324
325   /////////////////////////////////////////////////////////////////
326 } // namespace zypp
327 ///////////////////////////////////////////////////////////////////
328
329 ///////////////////////////////////////////////////////////////////
330 namespace std
331 { /////////////////////////////////////////////////////////////////
332   /** \relates zypp::Arch Default order for std::container based Arch::compare.*/
333   template<>
334     inline bool less<zypp::Arch>::operator()( const zypp::Arch & lhs, const zypp::Arch & rhs ) const
335     { return lhs.compare( rhs ) < 0; }
336   /////////////////////////////////////////////////////////////////
337 } // namespace zypp
338 ///////////////////////////////////////////////////////////////////
339 #endif // ZYPP_ARCH_H