View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *   https://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  
20  package org.apache.commons.exec;
21  
22  import java.io.File;
23  import java.util.Locale;
24  
25  /**
26   * Condition that tests the OS type.
27   * <p>
28   * Copied and adapted from Apache Ant 1.9.6 from {@code org.apache.tools.ant.taskdefs.condition.OS}.
29   * </p>
30   */
31  public final class OS {
32  
33      /**
34       * OS family name to test: {@value}
35       */
36      public static final String FAMILY_9X = "win9x";
37  
38      /**
39       * OS family name to test: {@value}
40       */
41      public static final String FAMILY_DOS = "dos";
42  
43      /**
44       * OS family name to test: {@value}
45       */
46      public static final String FAMILY_MAC = "mac";
47  
48      /**
49       * OS family name to test: {@value}
50       */
51      public static final String FAMILY_NETWARE = "netware";
52  
53      /**
54       * OS family name to test: {@value}
55       */
56      public static final String FAMILY_NT = "winnt";
57  
58      /**
59       * OS family name to test: {@value}
60       */
61      public static final String FAMILY_OS2 = "os/2";
62  
63      /**
64       * OS family name to test: {@value}
65       */
66      public static final String FAMILY_OS400 = "os/400";
67  
68      /**
69       * OS family name to test: {@value}
70       */
71      public static final String FAMILY_TANDEM = "tandem";
72  
73      /**
74       * OS family name to test: {@value}
75       */
76      public static final String FAMILY_UNIX = "unix";
77  
78      /**
79       * OS family name to test: {@value}
80       */
81      public static final String FAMILY_VMS = "openvms";
82  
83      /**
84       * OS family name to test: {@value}
85       */
86      public static final String FAMILY_WINDOWS = "windows";
87  
88      /**
89       * OS family name to test: {@value}
90       */
91      public static final String FAMILY_ZOS = "z/os";
92  
93      /**
94       * Apple Darwin string: {@value}
95       */
96      private static final String DARWIN = "darwin";
97  
98      /**
99       * The OS name.
100      */
101     private static final String OS_NAME = System.getProperty("os.name").toLowerCase(Locale.ROOT);
102 
103     /**
104      * The OS architecture.
105      */
106     private static final String OS_ARCH = System.getProperty("os.arch").toLowerCase(Locale.ROOT);
107 
108     /**
109      * The OS version.
110      */
111     private static final String OS_VERSION = System.getProperty("os.version").toLowerCase(Locale.ROOT);
112 
113     /**
114      * Tests whether the OS on which commons-exec is executing matches the given OS architecture.
115      *
116      * @param arch the OS architecture to check for.
117      * @return whether if the OS matches.
118      */
119     public static boolean isArch(final String arch) {
120         return isOs(null, null, arch, null);
121     }
122 
123     /**
124      * Tests whether the OS on which commons-exec is executing matches the given OS family.
125      *
126      * @param family the family to check for.
127      * @return whether if the OS matches.
128      */
129     private static boolean isFamily(final String family) {
130         return isOs(family, null, null, null);
131     }
132 
133     /**
134      * Tests whether the OS is in the DOS family.
135      *
136      * @return whether the OS is in the DOS family.
137      */
138     public static boolean isFamilyDOS() {
139         return isFamily(FAMILY_DOS);
140     }
141 
142     /**
143      * Tests whether the OS is in the Mac family.
144      *
145      * @return whether the OS is in the Mac family.
146      */
147     public static boolean isFamilyMac() {
148         return isFamily(FAMILY_MAC);
149     }
150 
151     /**
152      * Tests whether the OS is in the Netware family.
153      *
154      * @return whether the OS is in the Netware family.
155      */
156     public static boolean isFamilyNetware() {
157         return isFamily(FAMILY_NETWARE);
158     }
159 
160     /**
161      * Tests whether the OS is in the OpenVMS family.
162      *
163      * @return whether the OS is in the OpenVMS family.
164      */
165     public static boolean isFamilyOpenVms() {
166         return isFamily(FAMILY_VMS);
167     }
168 
169     /**
170      * Tests whether the OS is in the OS/2 family.
171      *
172      * @return whether the OS is in the OS/2 family.
173      */
174     public static boolean isFamilyOS2() {
175         return isFamily(FAMILY_OS2);
176     }
177 
178     /**
179      * Tests whether the OS is in the OS/400 family.
180      *
181      * @return whether the OS is in the OS/400 family.
182      */
183     public static boolean isFamilyOS400() {
184         return isFamily(FAMILY_OS400);
185     }
186 
187     /**
188      * Tests whether the OS is in the Tandem family.
189      *
190      * @return whether the OS is in the Tandem family.
191      */
192     public static boolean isFamilyTandem() {
193         return isFamily(FAMILY_TANDEM);
194     }
195 
196     /**
197      * Tests whether the OS is in the Unix family.
198      *
199      * @return whether the OS is in the Unix family.
200      */
201     public static boolean isFamilyUnix() {
202         return isFamily(FAMILY_UNIX);
203     }
204 
205     /**
206      * Tests whether the OS is in the Windows 9x family.
207      *
208      * @return whether the OS is in the Windows 9x family.
209      */
210     public static boolean isFamilyWin9x() {
211         return isFamily(FAMILY_9X);
212     }
213 
214     /**
215      * Tests whether the OS is in the Windows family.
216      *
217      * @return whether the OS is in the Windows family.
218      */
219     public static boolean isFamilyWindows() {
220         return isFamily(FAMILY_WINDOWS);
221     }
222 
223     /**
224      * Tests whether the OS is in the Windows NT family.
225      *
226      * @return whether the OS is in the Windows NT family.
227      */
228     public static boolean isFamilyWinNT() {
229         return isFamily(FAMILY_NT);
230     }
231 
232     /**
233      * Tests whether the OS is in the z/OS family.
234      *
235      * @return whether the OS is in the z/OS family.
236      */
237     public static boolean isFamilyZOS() {
238         return isFamily(FAMILY_ZOS);
239     }
240 
241     /**
242      * Tests whether if the OS on which commons-exec is executing matches the given OS name.
243      *
244      * @param name the OS name to check for.
245      * @return whether the OS matches.
246      */
247     public static boolean isName(final String name) {
248         return isOs(null, name, null, null);
249     }
250 
251     /**
252      * Tests whether the OS on which commons-exec is executing matches the given OS family, name, architecture and version.
253      *
254      * @param family  The OS family.
255      * @param name    The OS name.
256      * @param arch    The OS architecture.
257      * @param version The OS version.
258      * @return whether the OS matches.
259      */
260     public static boolean isOs(final String family, final String name, final String arch, final String version) {
261         boolean retValue = false;
262         if (family != null || name != null || arch != null || version != null) {
263             boolean isFamily = true;
264             boolean isName = true;
265             boolean isArch = true;
266             boolean isVersion = true;
267             if (family != null) {
268                 // Windows probing logic relies on the word 'windows' in the OS
269                 final boolean isWindows = OS_NAME.contains(FAMILY_WINDOWS);
270                 boolean is9x = false;
271                 boolean isNT = false;
272                 if (isWindows) {
273                     // there are only four 9x platforms that we look for
274                     is9x = OS_NAME.contains("95") || OS_NAME.contains("98") || OS_NAME.contains("me")
275                     // Windows CE isn't really 9x, but crippled enough to
276                     // be a muchness. Ant doesn't run on CE, anyway.
277                             || OS_NAME.contains("ce");
278                     isNT = !is9x;
279                 }
280                 switch (family) {
281                 case FAMILY_WINDOWS:
282                     isFamily = isWindows;
283                     break;
284                 case FAMILY_9X:
285                     isFamily = isWindows && is9x;
286                     break;
287                 case FAMILY_NT:
288                     isFamily = isWindows && isNT;
289                     break;
290                 case FAMILY_OS2:
291                     isFamily = OS_NAME.contains(FAMILY_OS2);
292                     break;
293                 case FAMILY_NETWARE:
294                     isFamily = OS_NAME.contains(FAMILY_NETWARE);
295                     break;
296                 case FAMILY_DOS:
297                     isFamily = File.pathSeparator.equals(";") && !isFamily(FAMILY_NETWARE);
298                     break;
299                 case FAMILY_MAC:
300                     isFamily = OS_NAME.contains(FAMILY_MAC) || OS_NAME.contains(DARWIN);
301                     break;
302                 case FAMILY_TANDEM:
303                     isFamily = OS_NAME.contains("nonstop_kernel");
304                     break;
305                 case FAMILY_UNIX:
306                     isFamily = File.pathSeparator.equals(":") && !isFamily(FAMILY_VMS)
307                             && (!isFamily(FAMILY_MAC) || OS_NAME.endsWith("x") || OS_NAME.contains(DARWIN));
308                     break;
309                 case FAMILY_ZOS:
310                     isFamily = OS_NAME.contains(FAMILY_ZOS) || OS_NAME.contains("os/390");
311                     break;
312                 case FAMILY_OS400:
313                     isFamily = OS_NAME.contains(FAMILY_OS400);
314                     break;
315                 case FAMILY_VMS:
316                     isFamily = OS_NAME.contains(FAMILY_VMS);
317                     break;
318                 default:
319                     throw new IllegalArgumentException("Don\'t know how to detect OS family \"" + family + "\"");
320                 }
321             }
322             if (name != null) {
323                 isName = name.equals(OS_NAME);
324             }
325             if (arch != null) {
326                 isArch = arch.equals(OS_ARCH);
327             }
328             if (version != null) {
329                 isVersion = version.equals(OS_VERSION);
330             }
331             retValue = isFamily && isName && isArch && isVersion;
332         }
333         return retValue;
334     }
335 
336     /**
337      * Tests whether the OS on which commons-exec is executing matches the given OS version.
338      *
339      * @param version the OS version to check for.
340      * @return whether if the OS matches.
341      */
342     public static boolean isVersion(final String version) {
343         return isOs(null, null, null, version);
344     }
345 
346     /**
347      * Avoids instances.
348      */
349     private OS() {
350     }
351 }