/* * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License version 2 only, as * published by the Free Software Foundation. * * This code 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 * version 2 for more details (a copy is included in the LICENSE file that * accompanied this code). * * You should have received a copy of the GNU General Public License version * 2 along with this work; if not, write to the Free Software Foundation, * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. * * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA * or visit www.oracle.com if you need additional information or have any * questions. * */ package sun.jvm.hotspot; import java.util.Arrays; import java.util.List; public class SAGetopt { private String[] _argv; private int _optind; // index in arguments array private int _optopt; // index within an argument private String _optarg; // last option argument private boolean _optreset; // special handling of first call public SAGetopt(String[] args) { _argv = args.clone(); _optind = 0; _optopt = 1; _optarg = null; _optreset = true; } public String getOptarg() { return _optarg; } public int getOptind() { return _optind; } private void extractOptarg(String opt) { // Argument expected if (_optind > _argv.length) { throw new SAGetoptException("Not enough arguments for '" + opt + "'"); } if (! _argv[_optind].isEmpty() && _argv[_optind].charAt(0) == '-') { throw new SAGetoptException("Argument is expected for '" + opt + "'"); } _optarg = _argv[_optind]; _optind += 1; } private String processLongOptions(String carg, String[] longOptStr) { List<String> los = Arrays.asList(longOptStr); String[] ca = carg.split("=", 2); if (los.contains(ca[0])) { if (ca.length > 1) { throw new SAGetoptException("Argument is not expected for '" + ca[0] + "'"); } return carg; } if (los.contains(ca[0] + "=")) { if (ca.length > 1) { // GNU style options --file=name _optarg = ca[1]; } else { // Mixed style options --file name try { extractOptarg(ca[0]); } catch (ArrayIndexOutOfBoundsException e) { throw new SAGetoptException("Argument is expected for '" + ca[0] + "'"); } } return ca[0]; } throw new SAGetoptException("Invalid option '" + ca[0] + "'"); } public String next(String optStr, String[] longOptStr) { if (_optind >= _argv.length || _argv[_optind] == null) { // All arguments processed return null; } String carg = _argv[_optind]; _optarg = null; if (_optreset) { // End of option batch like '-abc' reached, expect option to start from '-' if (carg.isEmpty() || carg.charAt(0) != '-' || carg.equals("--")) { // Stop processing on -- or first non-option argument; return null; } if (carg.startsWith("--")) { // Handle long options, it can't be combined so it's simple if (longOptStr == null || longOptStr.length == 0) { // No long options expected, stop options processing return null; } ++ _optind; // at this point carg contains at least one character besides -- carg = carg.substring(2); return processLongOptions(carg, longOptStr); } if (optStr == null || optStr.length() == 0) { // No short options return null; } // At this point carg[0] contains '-' _optreset = false; _optopt = 1; } char ch = carg.charAt(_optopt); // adjust pointer to next character _optopt += 1; // Okay, ready to process options like // -abc -d bla -ef int chIndex = optStr.indexOf(ch); if (chIndex == -1) { throw new SAGetoptException("Invalid option '" + ch + "'"); } if (_optopt >= carg.length()) { _optind += 1; _optreset = true; } if (chIndex < optStr.length()-1 && optStr.charAt(chIndex+1) == ':') { // Argument expected extractOptarg(String.valueOf(ch)); } return String.valueOf(ch); } }