1 7 8 44 45 package java.lang; 46 47 import java.io.*; 48 import java.util.*; 49 50 final class ProcessEnvironment extends HashMap<String ,String > 51 { 52 private static String validateName(String name) { 53 if (name.indexOf('=', 1) != -1 || 55 name.indexOf('\u0000') != -1) 56 throw new IllegalArgumentException 57 ("Invalid environment variable name: \"" + name + "\""); 58 return name; 59 } 60 61 private static String validateValue(String value) { 62 if (value.indexOf('\u0000') != -1) 63 throw new IllegalArgumentException 64 ("Invalid environment variable value: \"" + value + "\""); 65 return value; 66 } 67 68 private static String nonNullString(Object o) { 69 if (o == null) 70 throw new NullPointerException (); 71 return (String ) o; 72 } 73 74 public String put(String key, String value) { 75 return super.put(validateName(key), validateValue(value)); 76 } 77 78 public String get(Object key) { 79 return super.get(nonNullString(key)); 80 } 81 82 public boolean containsKey(Object key) { 83 return super.containsKey(nonNullString(key)); 84 } 85 86 public boolean containsValue(Object value) { 87 return super.containsValue(nonNullString(value)); 88 } 89 90 public String remove(Object key) { 91 return super.remove(nonNullString(key)); 92 } 93 94 private static class CheckedEntry 95 implements Map.Entry<String ,String > 96 { 97 private final Map.Entry<String ,String > e; 98 public CheckedEntry(Map.Entry<String ,String > e) {this.e = e;} 99 public String getKey() { return e.getKey();} 100 public String getValue() { return e.getValue();} 101 public String setValue(String value) { 102 return e.setValue(validateValue(value)); 103 } 104 public String toString() { return getKey() + "=" + getValue();} 105 public boolean equals(Object o) {return e.equals(o);} 106 public int hashCode() {return e.hashCode();} 107 } 108 109 private static class CheckedEntrySet 110 extends AbstractSet<Map.Entry<String ,String >> 111 { 112 private final Set<Map.Entry<String ,String >> s; 113 public CheckedEntrySet(Set<Map.Entry<String ,String >> s) {this.s = s;} 114 public int size() {return s.size();} 115 public boolean isEmpty() {return s.isEmpty();} 116 public void clear() { s.clear();} 117 public Iterator<Map.Entry<String ,String >> iterator() { 118 return new Iterator<Map.Entry<String ,String >>() { 119 Iterator<Map.Entry<String ,String >> i = s.iterator(); 120 public boolean hasNext() { return i.hasNext();} 121 public Map.Entry<String ,String > next() { 122 return new CheckedEntry(i.next()); 123 } 124 public void remove() { i.remove();} 125 }; 126 } 127 private static Map.Entry<String ,String > checkedEntry (Object o) { 128 Map.Entry<String ,String > e = (Map.Entry<String ,String >) o; 129 nonNullString(e.getKey()); 130 nonNullString(e.getValue()); 131 return e; 132 } 133 public boolean contains(Object o) {return s.contains(checkedEntry(o));} 134 public boolean remove(Object o) {return s.remove(checkedEntry(o));} 135 } 136 137 private static class CheckedValues extends AbstractCollection<String > { 138 private final Collection<String > c; 139 public CheckedValues(Collection<String > c) {this.c = c;} 140 public int size() {return c.size();} 141 public boolean isEmpty() {return c.isEmpty();} 142 public void clear() { c.clear();} 143 public Iterator<String > iterator() {return c.iterator();} 144 public boolean contains(Object o) {return c.contains(nonNullString(o));} 145 public boolean remove(Object o) {return c.remove(nonNullString(o));} 146 } 147 148 private static class CheckedKeySet extends AbstractSet<String > { 149 private final Set<String > s; 150 public CheckedKeySet(Set<String > s) {this.s = s;} 151 public int size() {return s.size();} 152 public boolean isEmpty() {return s.isEmpty();} 153 public void clear() { s.clear();} 154 public Iterator<String > iterator() {return s.iterator();} 155 public boolean contains(Object o) {return s.contains(nonNullString(o));} 156 public boolean remove(Object o) {return s.remove(nonNullString(o));} 157 } 158 159 public Set<String > keySet() { 160 return new CheckedKeySet(super.keySet()); 161 } 162 163 public Collection<String > values() { 164 return new CheckedValues(super.values()); 165 } 166 167 public Set<Map.Entry<String ,String >> entrySet() { 168 return new CheckedEntrySet(super.entrySet()); 169 } 170 171 172 private static final class NameComparator 173 implements Comparator<String > { 174 public int compare(String s1, String s2) { 175 int n1 = s1.length(); 180 int n2 = s2.length(); 181 int min = Math.min(n1, n2); 182 for (int i = 0; i < min; i++) { 183 char c1 = s1.charAt(i); 184 char c2 = s2.charAt(i); 185 if (c1 != c2) { 186 c1 = Character.toUpperCase(c1); 187 c2 = Character.toUpperCase(c2); 188 if (c1 != c2) 189 return c1 - c2; 190 } 191 } 192 return n1 - n2; 193 } 194 } 195 196 private static final class EntryComparator 197 implements Comparator<Map.Entry<String ,String >> { 198 public int compare(Map.Entry<String ,String > e1, 199 Map.Entry<String ,String > e2) { 200 return nameComparator.compare(e1.getKey(), e2.getKey()); 201 } 202 } 203 204 static final int MIN_NAME_LENGTH = 1; 206 207 private static final NameComparator nameComparator; 208 private static final EntryComparator entryComparator; 209 private static final ProcessEnvironment theEnvironment; 210 private static final Map<String ,String > theUnmodifiableEnvironment; 211 private static final Map<String ,String > theCaseInsensitiveEnvironment; 212 213 static { 214 nameComparator = new NameComparator(); 215 entryComparator = new EntryComparator(); 216 theEnvironment = new ProcessEnvironment (); 217 theUnmodifiableEnvironment 218 = Collections.unmodifiableMap(theEnvironment); 219 220 String envblock = environmentBlock(); 221 int beg, end, eql; 222 for (beg = 0; 223 ((end = envblock.indexOf('\u0000', beg )) != -1 && 224 (eql = envblock.indexOf('=' , beg+1)) != -1); 226 beg = end + 1) { 227 if (eql < end) 229 theEnvironment.put(envblock.substring(beg, eql), 230 envblock.substring(eql+1,end)); 231 } 232 233 theCaseInsensitiveEnvironment 234 = new TreeMap<String ,String >(nameComparator); 235 theCaseInsensitiveEnvironment.putAll(theEnvironment); 236 } 237 238 private ProcessEnvironment() { 239 super(); 240 } 241 242 private ProcessEnvironment(int capacity) { 243 super(capacity); 244 } 245 246 static String getenv(String name) { 248 return theCaseInsensitiveEnvironment.get(name); 257 } 258 259 static Map<String ,String > getenv() { 261 return theUnmodifiableEnvironment; 262 } 263 264 static Map<String ,String > environment() { 266 return (Map<String ,String >) theEnvironment.clone(); 267 } 268 269 static Map<String ,String > emptyEnvironment(int capacity) { 271 return new ProcessEnvironment (capacity); 272 } 273 274 private static native String environmentBlock(); 275 276 String toEnvironmentBlock() { 278 List<Map.Entry<String ,String >> list 280 = new ArrayList<Map.Entry<String ,String >>(entrySet()); 281 Collections.sort(list, entryComparator); 282 283 StringBuilder sb = new StringBuilder (size()*30); 284 for (Map.Entry<String ,String > e : list) 285 sb.append(e.getKey()) 286 .append('=') 287 .append(e.getValue()) 288 .append('\u0000'); 289 if (sb.length() == 0) 292 sb.append('\u0000'); 293 sb.append('\u0000'); 294 return sb.toString(); 295 } 296 297 static String toEnvironmentBlock(Map<String ,String > map) { 298 return map == null ? null : 299 ((ProcessEnvironment )map).toEnvironmentBlock(); 300 } 301 } 302 | Popular Tags |